From 8648fbd5aa85356d48469593c15f204315269127 Mon Sep 17 00:00:00 2001 From: Tobias Koppers Date: Wed, 24 Nov 2021 10:53:20 +0100 Subject: [PATCH 1/4] remove CI hacks for watching --- .github/workflows/build_test_deploy.yml | 16 ---------------- .github/workflows/test_react_experimental.yml | 3 --- .github/workflows/test_react_next.yml | 3 --- 3 files changed, 22 deletions(-) diff --git a/.github/workflows/build_test_deploy.yml b/.github/workflows/build_test_deploy.yml index 805cc42edee5d..5a7edcfda889b 100644 --- a/.github/workflows/build_test_deploy.yml +++ b/.github/workflows/build_test_deploy.yml @@ -162,10 +162,6 @@ jobs: - run: npm i -g playwright-chromium@1.14.1 && npx playwright install-deps if: ${{needs.build.outputs.docsChange != 'docs only change'}} - # TODO: remove after we fix watchpack watching too much - - run: echo fs.inotify.max_user_watches=524288 | sudo tee -a /etc/sysctl.conf && sudo sysctl -p - if: ${{needs.build.outputs.docsChange != 'docs only change'}} - - run: node run-tests.js --type development name: Run test/development if: ${{needs.build.outputs.docsChange != 'docs only change'}} @@ -214,10 +210,6 @@ jobs: - run: npm i -g playwright-chromium@1.14.1 && npx playwright install-deps if: ${{needs.build.outputs.docsChange != 'docs only change'}} - # TODO: remove after we fix watchpack watching too much - - run: echo fs.inotify.max_user_watches=524288 | sudo tee -a /etc/sysctl.conf && sudo sysctl -p - if: ${{needs.build.outputs.docsChange != 'docs only change'}} - - run: node run-tests.js --type production name: Run test/production if: ${{needs.build.outputs.docsChange != 'docs only change'}} @@ -261,10 +253,6 @@ jobs: - run: npm i -g playwright-chromium@1.14.1 && npx playwright install-deps if: ${{needs.build.outputs.docsChange != 'docs only change'}} - # TODO: remove after we fix watchpack watching too much - - run: echo fs.inotify.max_user_watches=524288 | sudo tee -a /etc/sysctl.conf && sudo sysctl -p - if: ${{needs.build.outputs.docsChange != 'docs only change'}} - - run: xvfb-run node run-tests.js --timings -g ${{ matrix.group }}/6 if: ${{needs.build.outputs.docsChange != 'docs only change'}} @@ -300,10 +288,6 @@ jobs: name: next-swc-dev-binary path: packages/next-swc/native - # TODO: remove after we fix watchpack watching too much - - run: echo fs.inotify.max_user_watches=524288 | sudo tee -a /etc/sysctl.conf && sudo sysctl -p - if: ${{needs.build.outputs.docsChange != 'docs only change'}} - - run: cd test/integration/with-electron/app && yarn if: ${{needs.build.outputs.docsChange != 'docs only change'}} diff --git a/.github/workflows/test_react_experimental.yml b/.github/workflows/test_react_experimental.yml index 9073caf8fb414..8b56f79f4d9b3 100644 --- a/.github/workflows/test_react_experimental.yml +++ b/.github/workflows/test_react_experimental.yml @@ -44,9 +44,6 @@ jobs: path: ./* key: ${{ github.sha }}-react-experimental - # TODO: remove after we fix watchpack watching too much - - run: echo fs.inotify.max_user_watches=524288 | sudo tee -a /etc/sysctl.conf && sudo sysctl -p - - run: npm i -g playwright-chromium@1.14.1 && npx playwright install-deps - run: node run-tests.js --timings -g ${{ matrix.group }}/6 diff --git a/.github/workflows/test_react_next.yml b/.github/workflows/test_react_next.yml index efd8b3810a39e..4411c0a521a5d 100644 --- a/.github/workflows/test_react_next.yml +++ b/.github/workflows/test_react_next.yml @@ -44,9 +44,6 @@ jobs: path: ./* key: ${{ github.sha }}-react-next - # TODO: remove after we fix watchpack watching too much - - run: echo fs.inotify.max_user_watches=524288 | sudo tee -a /etc/sysctl.conf && sudo sysctl -p - - run: npm i -g playwright-chromium@1.14.1 && npx playwright install-deps - run: node run-tests.js --timings -g ${{ matrix.group }}/6 From 67c4c92e9641839c1c3a7fc2daecaabd9aff90d1 Mon Sep 17 00:00:00 2001 From: Tobias Koppers Date: Wed, 24 Nov 2021 10:56:14 +0100 Subject: [PATCH 2/4] fix next.js watching files twice --- packages/next/build/webpack-config.ts | 18 ++++++------------ 1 file changed, 6 insertions(+), 12 deletions(-) diff --git a/packages/next/build/webpack-config.ts b/packages/next/build/webpack-config.ts index 295dd9c65b8d4..36b04d85ebdc3 100644 --- a/packages/next/build/webpack-config.ts +++ b/packages/next/build/webpack-config.ts @@ -54,6 +54,11 @@ import { getRawPageExtensions } from './utils' import browserslist from 'browserslist' import loadJsConfig from './load-jsconfig' +const watchOptions = Object.freeze({ + aggregateTimeout: 5, + ignored: ['**/.git/**', '**/node_modules/**', '**/.next/**'], +}) + function getSupportedBrowsers( dir: string, isDevelopment: boolean @@ -941,8 +946,6 @@ export default async function getBaseWebpackConfig( // Default behavior: bundle the code! } - const emacsLockfilePattern = '**/.#*' - const codeCondition = { test: /\.(tsx|ts|js|cjs|mjs|jsx)$/, ...(config.experimental.externalDir @@ -1095,16 +1098,7 @@ export default async function getBaseWebpackConfig( ...entrypoints, } }, - watchOptions: { - aggregateTimeout: 5, - ignored: [ - '**/.git/**', - '**/node_modules/**', - '**/.next/**', - // can be removed after https://github.com/paulmillr/chokidar/issues/955 is released - emacsLockfilePattern, - ], - }, + watchOptions, output: { // we must set publicPath to an empty value to override the default of // auto which doesn't work in IE11 From b4f3a83ab2d4c19078b7fe0b506550e9f6bf3bce Mon Sep 17 00:00:00 2001 From: Tobias Koppers Date: Wed, 24 Nov 2021 19:15:36 +0100 Subject: [PATCH 3/4] update watchpack --- packages/next/package.json | 2 +- yarn.lock | 16 ++++------------ 2 files changed, 5 insertions(+), 13 deletions(-) diff --git a/packages/next/package.json b/packages/next/package.json index f986e6d6e4c1b..c2d903e3b0403 100644 --- a/packages/next/package.json +++ b/packages/next/package.json @@ -114,7 +114,7 @@ "use-subscription": "1.5.1", "util": "0.12.4", "vm-browserify": "1.1.2", - "watchpack": "2.1.1" + "watchpack": "2.3.0" }, "peerDependencies": { "fibers": ">= 3.1.0", diff --git a/yarn.lock b/yarn.lock index 188f4243088a7..e585904f107cf 100644 --- a/yarn.lock +++ b/yarn.lock @@ -19884,10 +19884,10 @@ watchpack-chokidar2@^2.0.0: dependencies: chokidar "^2.1.8" -watchpack@2.1.1: - version "2.1.1" - resolved "https://registry.yarnpkg.com/watchpack/-/watchpack-2.1.1.tgz#e99630550fca07df9f90a06056987baa40a689c7" - integrity sha512-Oo7LXCmc1eE1AjyuSBmtC3+Wy4HcV8PxWh2kP6fOl8yTlNS7r0K9l1ao2lrrUza7V39Y3D/BbJgY8VeSlc5JKw== +watchpack@2.3.0, watchpack@^2.2.0: + version "2.3.0" + resolved "https://registry.yarnpkg.com/watchpack/-/watchpack-2.3.0.tgz#a41bca3da6afaff31e92a433f4c856a0c25ea0c4" + integrity sha512-MnN0Q1OsvB/GGHETrFeZPQaOelWh/7O+EiFlj8sM9GPjtQkis7k01aAxrg/18kTfoIVcLL+haEVFlXDaSRwKRw== dependencies: glob-to-regexp "^0.4.1" graceful-fs "^4.1.2" @@ -19903,14 +19903,6 @@ watchpack@^1.7.4: chokidar "^3.4.1" watchpack-chokidar2 "^2.0.0" -watchpack@^2.2.0: - version "2.2.0" - resolved "https://registry.yarnpkg.com/watchpack/-/watchpack-2.2.0.tgz#47d78f5415fe550ecd740f99fe2882323a58b1ce" - integrity sha512-up4YAn/XHgZHIxFBVCdlMiWDj6WaLKpwVeGQk2I5thdYxF/KmF0aaz6TfJZ/hfl1h/XlcDr7k1KH7ThDagpFaA== - dependencies: - glob-to-regexp "^0.4.1" - graceful-fs "^4.1.2" - wcwidth@^1.0.0, wcwidth@^1.0.1: version "1.0.1" resolved "https://registry.yarnpkg.com/wcwidth/-/wcwidth-1.0.1.tgz#f0b0dcf915bc5ff1528afadb2c0e17b532da2fe8" From 7d26309b4e2e6bcce5764e549527521d9f663851 Mon Sep 17 00:00:00 2001 From: sokra Date: Wed, 24 Nov 2021 18:28:42 +0000 Subject: [PATCH 4/4] =?UTF-8?q?=E2=9A=99=20Update=20compiled=20files?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- packages/next/compiled/webpack/bundle5.js | 207993 ++++++++++--------- 1 file changed, 104008 insertions(+), 103985 deletions(-) diff --git a/packages/next/compiled/webpack/bundle5.js b/packages/next/compiled/webpack/bundle5.js index be607621676f6..3a07b86d8a697 100644 --- a/packages/next/compiled/webpack/bundle5.js +++ b/packages/next/compiled/webpack/bundle5.js @@ -22629,7 +22629,7 @@ var __classPrivateFieldSet; /***/ }), -/***/ 46806: +/***/ 76595: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; @@ -22639,802 +22639,788 @@ var __classPrivateFieldSet; */ +const EventEmitter = __webpack_require__(28614).EventEmitter; +const fs = __webpack_require__(82161); +const path = __webpack_require__(85622); -const RuntimeGlobals = __webpack_require__(49404); -const WebpackError = __webpack_require__(68422); -const ConstDependency = __webpack_require__(60864); -const BasicEvaluatedExpression = __webpack_require__(2412); -const { - toConstantDependency, - evaluateToString -} = __webpack_require__(28723); -const ChunkNameRuntimeModule = __webpack_require__(43818); -const GetFullHashRuntimeModule = __webpack_require__(28454); +const watchEventSource = __webpack_require__(72511); -/** @typedef {import("./Compiler")} Compiler */ -/** @typedef {import("./javascript/JavascriptParser")} JavascriptParser */ +const EXISTANCE_ONLY_TIME_ENTRY = Object.freeze({}); -/* eslint-disable camelcase */ -const REPLACEMENTS = { - __webpack_require__: { - expr: RuntimeGlobals.require, - req: [RuntimeGlobals.require], - type: "function", - assign: false - }, - __webpack_public_path__: { - expr: RuntimeGlobals.publicPath, - req: [RuntimeGlobals.publicPath], - type: "string", - assign: true - }, - __webpack_base_uri__: { - expr: RuntimeGlobals.baseURI, - req: [RuntimeGlobals.baseURI], - type: "string", - assign: true - }, - __webpack_modules__: { - expr: RuntimeGlobals.moduleFactories, - req: [RuntimeGlobals.moduleFactories], - type: "object", - assign: false - }, - __webpack_chunk_load__: { - expr: RuntimeGlobals.ensureChunk, - req: [RuntimeGlobals.ensureChunk], - type: "function", - assign: true - }, - __non_webpack_require__: { - expr: "require", - req: null, - type: undefined, // type is not known, depends on environment - assign: true - }, - __webpack_nonce__: { - expr: RuntimeGlobals.scriptNonce, - req: [RuntimeGlobals.scriptNonce], - type: "string", - assign: true - }, - __webpack_hash__: { - expr: `${RuntimeGlobals.getFullHash}()`, - req: [RuntimeGlobals.getFullHash], - type: "string", - assign: false - }, - __webpack_chunkname__: { - expr: RuntimeGlobals.chunkName, - req: [RuntimeGlobals.chunkName], - type: "string", - assign: false - }, - __webpack_get_script_filename__: { - expr: RuntimeGlobals.getChunkScriptFilename, - req: [RuntimeGlobals.getChunkScriptFilename], - type: "function", - assign: true - }, - __webpack_runtime_id__: { - expr: RuntimeGlobals.runtimeId, - req: [RuntimeGlobals.runtimeId], - assign: false - }, - "require.onError": { - expr: RuntimeGlobals.uncaughtErrorHandler, - req: [RuntimeGlobals.uncaughtErrorHandler], - type: undefined, // type is not known, could be function or undefined - assign: true // is never a pattern - }, - __system_context__: { - expr: RuntimeGlobals.systemContext, - req: [RuntimeGlobals.systemContext], - type: "object", - assign: false - }, - __webpack_share_scopes__: { - expr: RuntimeGlobals.shareScopeMap, - req: [RuntimeGlobals.shareScopeMap], - type: "object", - assign: false - }, - __webpack_init_sharing__: { - expr: RuntimeGlobals.initializeSharing, - req: [RuntimeGlobals.initializeSharing], - type: "function", - assign: true - } -}; -/* eslint-enable camelcase */ +let FS_ACCURACY = 1000; -class APIPlugin { - /** - * Apply the plugin - * @param {Compiler} compiler the compiler instance - * @returns {void} - */ - apply(compiler) { - compiler.hooks.compilation.tap( - "APIPlugin", - (compilation, { normalModuleFactory }) => { - compilation.dependencyTemplates.set( - ConstDependency, - new ConstDependency.Template() - ); +const IS_OSX = __webpack_require__(12087).platform() === "darwin"; +const WATCHPACK_POLLING = process.env.WATCHPACK_POLLING; +const FORCE_POLLING = + `${+WATCHPACK_POLLING}` === WATCHPACK_POLLING + ? +WATCHPACK_POLLING + : !!WATCHPACK_POLLING && WATCHPACK_POLLING !== "false"; - compilation.hooks.runtimeRequirementInTree - .for(RuntimeGlobals.chunkName) - .tap("APIPlugin", chunk => { - compilation.addRuntimeModule( - chunk, - new ChunkNameRuntimeModule(chunk.name) - ); - return true; - }); +function withoutCase(str) { + return str.toLowerCase(); +} - compilation.hooks.runtimeRequirementInTree - .for(RuntimeGlobals.getFullHash) - .tap("APIPlugin", (chunk, set) => { - compilation.addRuntimeModule(chunk, new GetFullHashRuntimeModule()); - return true; - }); +function needCalls(times, callback) { + return function() { + if (--times === 0) { + return callback(); + } + }; +} - /** - * @param {JavascriptParser} parser the parser - */ - const handler = parser => { - Object.keys(REPLACEMENTS).forEach(key => { - const info = REPLACEMENTS[key]; - parser.hooks.expression - .for(key) - .tap( - "APIPlugin", - toConstantDependency(parser, info.expr, info.req) - ); - if (info.assign === false) { - parser.hooks.assign.for(key).tap("APIPlugin", expr => { - const err = new WebpackError(`${key} must not be assigned`); - err.loc = expr.loc; - throw err; - }); - } - if (info.type) { - parser.hooks.evaluateTypeof - .for(key) - .tap("APIPlugin", evaluateToString(info.type)); - } - }); +class Watcher extends EventEmitter { + constructor(directoryWatcher, filePath, startTime) { + super(); + this.directoryWatcher = directoryWatcher; + this.path = filePath; + this.startTime = startTime && +startTime; + } - parser.hooks.expression - .for("__webpack_layer__") - .tap("APIPlugin", expr => { - const dep = new ConstDependency( - JSON.stringify(parser.state.module.layer), - expr.range - ); - dep.loc = expr.loc; - parser.state.module.addPresentationalDependency(dep); - return true; - }); - parser.hooks.evaluateIdentifier - .for("__webpack_layer__") - .tap("APIPlugin", expr => - (parser.state.module.layer === null - ? new BasicEvaluatedExpression().setNull() - : new BasicEvaluatedExpression().setString( - parser.state.module.layer - ) - ).setRange(expr.range) - ); - parser.hooks.evaluateTypeof - .for("__webpack_layer__") - .tap("APIPlugin", expr => - new BasicEvaluatedExpression() - .setString( - parser.state.module.layer === null ? "object" : "string" - ) - .setRange(expr.range) - ); - }; + checkStartTime(mtime, initial) { + const startTime = this.startTime; + if (typeof startTime !== "number") return !initial; + return startTime <= mtime; + } - normalModuleFactory.hooks.parser - .for("javascript/auto") - .tap("APIPlugin", handler); - normalModuleFactory.hooks.parser - .for("javascript/dynamic") - .tap("APIPlugin", handler); - normalModuleFactory.hooks.parser - .for("javascript/esm") - .tap("APIPlugin", handler); - } - ); + close() { + this.emit("closed"); } } -module.exports = APIPlugin; +class DirectoryWatcher extends EventEmitter { + constructor(watcherManager, directoryPath, options) { + super(); + if (FORCE_POLLING) { + options.poll = FORCE_POLLING; + } + this.watcherManager = watcherManager; + this.options = options; + this.path = directoryPath; + // safeTime is the point in time after which reading is safe to be unchanged + // timestamp is a value that should be compared with another timestamp (mtime) + /** @type {Map} */ + this.filesWithoutCase = new Map(); + this.directories = new Map(); + this.lastWatchEvent = 0; + this.initialScan = true; + this.ignored = options.ignored || (() => false); + this.nestedWatching = false; + this.polledWatching = + typeof options.poll === "number" + ? options.poll + : options.poll + ? 5007 + : false; + this.timeout = undefined; + this.initialScanRemoved = new Set(); + this.initialScanFinished = undefined; + /** @type {Map>} */ + this.watchers = new Map(); + this.parentWatcher = null; + this.refs = 0; + this._activeEvents = new Map(); + this.closed = false; + this.scanning = false; + this.scanAgain = false; + this.scanAgainInitial = false; + this.createWatcher(); + this.doScan(true); + } -/***/ }), + createWatcher() { + try { + if (this.polledWatching) { + this.watcher = { + close: () => { + if (this.timeout) { + clearTimeout(this.timeout); + this.timeout = undefined; + } + } + }; + } else { + if (IS_OSX) { + this.watchInParentDirectory(); + } + this.watcher = watchEventSource.watch(this.path); + this.watcher.on("change", this.onWatchEvent.bind(this)); + this.watcher.on("error", this.onWatcherError.bind(this)); + } + } catch (err) { + this.onWatcherError(err); + } + } -/***/ 570: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + forEachWatcher(path, fn) { + const watchers = this.watchers.get(withoutCase(path)); + if (watchers !== undefined) { + for (const w of watchers) { + fn(w); + } + } + } -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Ivan Kopeykin @vankop -*/ + setMissing(itemPath, initial, type) { + if (this.initialScan) { + this.initialScanRemoved.add(itemPath); + } + const oldDirectory = this.directories.get(itemPath); + if (oldDirectory) { + if (this.nestedWatching) oldDirectory.close(); + this.directories.delete(itemPath); + this.forEachWatcher(itemPath, w => w.emit("remove", type)); + if (!initial) { + this.forEachWatcher(this.path, w => + w.emit("change", itemPath, null, type, initial) + ); + } + } -const WebpackError = __webpack_require__(68422); -const CURRENT_METHOD_REGEXP = /at ([a-zA-Z0-9_.]*)/; + const oldFile = this.files.get(itemPath); + if (oldFile) { + this.files.delete(itemPath); + const key = withoutCase(itemPath); + const count = this.filesWithoutCase.get(key) - 1; + if (count <= 0) { + this.filesWithoutCase.delete(key); + this.forEachWatcher(itemPath, w => w.emit("remove", type)); + } else { + this.filesWithoutCase.set(key, count); + } -/** - * @param {string=} method method name - * @returns {string} message - */ -function createMessage(method) { - return `Abstract method${method ? " " + method : ""}. Must be overridden.`; -} + if (!initial) { + this.forEachWatcher(this.path, w => + w.emit("change", itemPath, null, type, initial) + ); + } + } + } -/** - * @constructor - */ -function Message() { - /** @type {string} */ - this.stack = undefined; - Error.captureStackTrace(this); - /** @type {RegExpMatchArray} */ - const match = this.stack.split("\n")[3].match(CURRENT_METHOD_REGEXP); + setFileTime(filePath, mtime, initial, ignoreWhenEqual, type) { + const now = Date.now(); - this.message = match && match[1] ? createMessage(match[1]) : createMessage(); -} + if (this.ignored(filePath)) return; -/** - * Error for abstract method - * @example - * class FooClass { - * abstractMethod() { - * throw new AbstractMethodError(); // error message: Abstract method FooClass.abstractMethod. Must be overridden. - * } - * } - * - */ -class AbstractMethodError extends WebpackError { - constructor() { - super(new Message().message); - this.name = "AbstractMethodError"; - } -} + const old = this.files.get(filePath); -module.exports = AbstractMethodError; + let safeTime, accuracy; + if (initial) { + safeTime = Math.min(now, mtime) + FS_ACCURACY; + accuracy = FS_ACCURACY; + } else { + safeTime = now; + accuracy = 0; + if (old && old.timestamp === mtime && mtime + FS_ACCURACY < now - 1000) { + // We are sure that mtime is untouched + // This can be caused by some file attribute change + // e. g. when access time has been changed + // but the file content is untouched + return; + } + } -/***/ }), + if (ignoreWhenEqual && old && old.timestamp === mtime) return; -/***/ 11315: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + this.files.set(filePath, { + safeTime, + accuracy, + timestamp: mtime + }); -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ + if (!old) { + const key = withoutCase(filePath); + const count = this.filesWithoutCase.get(key); + this.filesWithoutCase.set(key, (count || 0) + 1); + if (count !== undefined) { + // There is already a file with case-insensitive-equal name + // On a case-insensitive filesystem we may miss the renaming + // when only casing is changed. + // To be sure that our information is correct + // we trigger a rescan here + this.doScan(false); + } + this.forEachWatcher(filePath, w => { + if (!initial || w.checkStartTime(safeTime, initial)) { + w.emit("change", mtime, type); + } + }); + } else if (!initial) { + this.forEachWatcher(filePath, w => w.emit("change", mtime, type)); + } + this.forEachWatcher(this.path, w => { + if (!initial || w.checkStartTime(safeTime, initial)) { + w.emit("change", filePath, safeTime, type, initial); + } + }); + } + setDirectory(directoryPath, birthtime, initial, type) { + if (this.ignored(directoryPath)) return; + if (directoryPath === this.path) { + if (!initial) { + this.forEachWatcher(this.path, w => + w.emit("change", directoryPath, birthtime, type, initial) + ); + } + } else { + const old = this.directories.get(directoryPath); + if (!old) { + const now = Date.now(); -const DependenciesBlock = __webpack_require__(21484); -const makeSerializable = __webpack_require__(26522); + if (this.nestedWatching) { + this.createNestedWatcher(directoryPath); + } else { + this.directories.set(directoryPath, true); + } -/** @typedef {import("./ChunkGraph")} ChunkGraph */ -/** @typedef {import("./ChunkGroup")} ChunkGroup */ -/** @typedef {import("./ChunkGroup").ChunkGroupOptions} ChunkGroupOptions */ -/** @typedef {import("./Dependency").DependencyLocation} DependencyLocation */ -/** @typedef {import("./Dependency").UpdateHashContext} UpdateHashContext */ -/** @typedef {import("./Entrypoint").EntryOptions} EntryOptions */ -/** @typedef {import("./Module")} Module */ -/** @typedef {import("./util/Hash")} Hash */ + let safeTime; + if (initial) { + safeTime = Math.min(now, birthtime) + FS_ACCURACY; + } else { + safeTime = now; + } -class AsyncDependenciesBlock extends DependenciesBlock { - /** - * @param {ChunkGroupOptions & { entryOptions?: EntryOptions }} groupOptions options for the group - * @param {DependencyLocation=} loc the line of code - * @param {string=} request the request - */ - constructor(groupOptions, loc, request) { - super(); - if (typeof groupOptions === "string") { - groupOptions = { name: groupOptions }; - } else if (!groupOptions) { - groupOptions = { name: undefined }; + this.forEachWatcher(directoryPath, w => { + if (!initial || w.checkStartTime(safeTime, false)) { + w.emit("change", birthtime, type); + } + }); + this.forEachWatcher(this.path, w => { + if (!initial || w.checkStartTime(safeTime, initial)) { + w.emit("change", directoryPath, safeTime, type, initial); + } + }); + } } - this.groupOptions = groupOptions; - this.loc = loc; - this.request = request; - this._stringifiedGroupOptions = undefined; } - /** - * @returns {string} The name of the chunk - */ - get chunkName() { - return this.groupOptions.name; - } - - /** - * @param {string} value The new chunk name - * @returns {void} - */ - set chunkName(value) { - if (this.groupOptions.name !== value) { - this.groupOptions.name = value; - this._stringifiedGroupOptions = undefined; - } + createNestedWatcher(directoryPath) { + const watcher = this.watcherManager.watchDirectory(directoryPath, 1); + watcher.on("change", (filePath, mtime, type, initial) => { + this.forEachWatcher(this.path, w => { + if (!initial || w.checkStartTime(mtime, initial)) { + w.emit("change", filePath, mtime, type, initial); + } + }); + }); + this.directories.set(directoryPath, watcher); } - /** - * @param {Hash} hash the hash used to track dependencies - * @param {UpdateHashContext} context context - * @returns {void} - */ - updateHash(hash, context) { - const { chunkGraph } = context; - if (this._stringifiedGroupOptions === undefined) { - this._stringifiedGroupOptions = JSON.stringify(this.groupOptions); + setNestedWatching(flag) { + if (this.nestedWatching !== !!flag) { + this.nestedWatching = !!flag; + if (this.nestedWatching) { + for (const directory of this.directories.keys()) { + this.createNestedWatcher(directory); + } + } else { + for (const [directory, watcher] of this.directories) { + watcher.close(); + this.directories.set(directory, true); + } + } } - const chunkGroup = chunkGraph.getBlockChunkGroup(this); - hash.update( - `${this._stringifiedGroupOptions}${chunkGroup ? chunkGroup.id : ""}` - ); - super.updateHash(hash, context); - } - - serialize(context) { - const { write } = context; - write(this.groupOptions); - write(this.loc); - write(this.request); - super.serialize(context); - } - - deserialize(context) { - const { read } = context; - this.groupOptions = read(); - this.loc = read(); - this.request = read(); - super.deserialize(context); - } -} - -makeSerializable(AsyncDependenciesBlock, "webpack/lib/AsyncDependenciesBlock"); - -Object.defineProperty(AsyncDependenciesBlock.prototype, "module", { - get() { - throw new Error( - "module property was removed from AsyncDependenciesBlock (it's not needed)" - ); - }, - set() { - throw new Error( - "module property was removed from AsyncDependenciesBlock (it's not needed)" - ); - } -}); - -module.exports = AsyncDependenciesBlock; - - -/***/ }), - -/***/ 69073: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Sean Larkin @thelarkinn -*/ - - - -const WebpackError = __webpack_require__(68422); - -/** @typedef {import("./Dependency").DependencyLocation} DependencyLocation */ -/** @typedef {import("./Module")} Module */ - -class AsyncDependencyToInitialChunkError extends WebpackError { - /** - * Creates an instance of AsyncDependencyToInitialChunkError. - * @param {string} chunkName Name of Chunk - * @param {Module} module module tied to dependency - * @param {DependencyLocation} loc location of dependency - */ - constructor(chunkName, module, loc) { - super( - `It's not allowed to load an initial chunk on demand. The chunk name "${chunkName}" is already used by an entrypoint.` - ); - - this.name = "AsyncDependencyToInitialChunkError"; - this.module = module; - this.loc = loc; } -} - -module.exports = AsyncDependencyToInitialChunkError; - - -/***/ }), - -/***/ 51714: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ - - - -const asyncLib = __webpack_require__(36386); -const NormalModule = __webpack_require__(11026); -const PrefetchDependency = __webpack_require__(39986); -/** @typedef {import("./Compiler")} Compiler */ - -class AutomaticPrefetchPlugin { - /** - * Apply the plugin - * @param {Compiler} compiler the compiler instance - * @returns {void} - */ - apply(compiler) { - compiler.hooks.compilation.tap( - "AutomaticPrefetchPlugin", - (compilation, { normalModuleFactory }) => { - compilation.dependencyFactories.set( - PrefetchDependency, - normalModuleFactory - ); + watch(filePath, startTime) { + const key = withoutCase(filePath); + let watchers = this.watchers.get(key); + if (watchers === undefined) { + watchers = new Set(); + this.watchers.set(key, watchers); + } + this.refs++; + const watcher = new Watcher(this, filePath, startTime); + watcher.on("closed", () => { + if (--this.refs <= 0) { + this.close(); + return; } - ); - let lastModules = null; - compiler.hooks.afterCompile.tap("AutomaticPrefetchPlugin", compilation => { - lastModules = []; - - for (const m of compilation.modules) { - if (m instanceof NormalModule) { - lastModules.push({ - context: m.context, - request: m.request - }); - } + watchers.delete(watcher); + if (watchers.size === 0) { + this.watchers.delete(key); + if (this.path === filePath) this.setNestedWatching(false); } }); - compiler.hooks.make.tapAsync( - "AutomaticPrefetchPlugin", - (compilation, callback) => { - if (!lastModules) return callback(); - asyncLib.forEach( - lastModules, - (m, callback) => { - compilation.addModuleChain( - m.context || compiler.context, - new PrefetchDependency(`!!${m.request}`), - callback + watchers.add(watcher); + let safeTime; + if (filePath === this.path) { + this.setNestedWatching(true); + safeTime = this.lastWatchEvent; + for (const entry of this.files.values()) { + fixupEntryAccuracy(entry); + safeTime = Math.max(safeTime, entry.safeTime); + } + } else { + const entry = this.files.get(filePath); + if (entry) { + fixupEntryAccuracy(entry); + safeTime = entry.safeTime; + } else { + safeTime = 0; + } + } + if (safeTime) { + if (safeTime >= startTime) { + process.nextTick(() => { + if (this.closed) return; + if (filePath === this.path) { + watcher.emit( + "change", + filePath, + safeTime, + "watch (outdated on attach)", + true + ); + } else { + watcher.emit( + "change", + safeTime, + "watch (outdated on attach)", + true ); - }, - err => { - lastModules = null; - callback(err); } - ); + }); } - ); + } else if (this.initialScan) { + if (this.initialScanRemoved.has(filePath)) { + process.nextTick(() => { + if (this.closed) return; + watcher.emit("remove"); + }); + } + } else if ( + !this.directories.has(filePath) && + watcher.checkStartTime(this.initialScanFinished, false) + ) { + process.nextTick(() => { + if (this.closed) return; + watcher.emit("initial-missing", "watch (missing on attach)"); + }); + } + return watcher; } -} -module.exports = AutomaticPrefetchPlugin; - - -/***/ }), - -/***/ 45480: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ - - -const { ConcatSource } = __webpack_require__(96192); -const Compilation = __webpack_require__(59622); -const ModuleFilenameHelpers = __webpack_require__(80295); -const Template = __webpack_require__(92066); -const createSchemaValidation = __webpack_require__(77695); + onWatchEvent(eventType, filename) { + if (this.closed) return; + if (!filename) { + // In some cases no filename is provided + // This seem to happen on windows + // So some event happened but we don't know which file is affected + // We have to do a full scan of the directory + this.doScan(false); + return; + } -/** @typedef {import("../declarations/plugins/BannerPlugin").BannerPluginArgument} BannerPluginArgument */ -/** @typedef {import("../declarations/plugins/BannerPlugin").BannerPluginOptions} BannerPluginOptions */ -/** @typedef {import("./Compiler")} Compiler */ + const filePath = path.join(this.path, filename); + if (this.ignored(filePath)) return; -const validate = createSchemaValidation( - __webpack_require__(79456), - () => __webpack_require__(33946), - { - name: "Banner Plugin", - baseDataPath: "options" + if (this._activeEvents.get(filename) === undefined) { + this._activeEvents.set(filename, false); + const checkStats = () => { + if (this.closed) return; + this._activeEvents.set(filename, false); + fs.lstat(filePath, (err, stats) => { + if (this.closed) return; + if (this._activeEvents.get(filename) === true) { + process.nextTick(checkStats); + return; + } + this._activeEvents.delete(filename); + // ENOENT happens when the file/directory doesn't exist + // EPERM happens when the containing directory doesn't exist + if (err) { + if ( + err.code !== "ENOENT" && + err.code !== "EPERM" && + err.code !== "EBUSY" + ) { + this.onStatsError(err); + } else { + if (filename === path.basename(this.path)) { + // This may indicate that the directory itself was removed + if (!fs.existsSync(this.path)) { + this.onDirectoryRemoved("stat failed"); + } + } + } + } + this.lastWatchEvent = Date.now(); + if (!stats) { + this.setMissing(filePath, false, eventType); + } else if (stats.isDirectory()) { + this.setDirectory( + filePath, + +stats.birthtime || 1, + false, + eventType + ); + } else if (stats.isFile() || stats.isSymbolicLink()) { + if (stats.mtime) { + ensureFsAccuracy(stats.mtime); + } + this.setFileTime( + filePath, + +stats.mtime || +stats.ctime || 1, + false, + false, + eventType + ); + } + }); + }; + process.nextTick(checkStats); + } else { + this._activeEvents.set(filename, true); + } } -); -const wrapComment = str => { - if (!str.includes("\n")) { - return Template.toComment(str); + onWatcherError(err) { + if (this.closed) return; + if (err) { + if (err.code !== "EPERM" && err.code !== "ENOENT") { + console.error("Watchpack Error (watcher): " + err); + } + this.onDirectoryRemoved("watch error"); + } } - return `/*!\n * ${str - .replace(/\*\//g, "* /") - .split("\n") - .join("\n * ") - .replace(/\s+\n/g, "\n") - .trimRight()}\n */`; -}; -class BannerPlugin { - /** - * @param {BannerPluginArgument} options options object - */ - constructor(options) { - if (typeof options === "string" || typeof options === "function") { - options = { - banner: options - }; + onStatsError(err) { + if (err) { + console.error("Watchpack Error (stats): " + err); } + } - validate(options); - - this.options = options; - - const bannerOption = options.banner; - if (typeof bannerOption === "function") { - const getBanner = bannerOption; - this.banner = this.options.raw - ? getBanner - : data => wrapComment(getBanner(data)); - } else { - const banner = this.options.raw - ? bannerOption - : wrapComment(bannerOption); - this.banner = () => banner; + onScanError(err) { + if (err) { + console.error("Watchpack Error (initial scan): " + err); } + this.onScanFinished(); } - /** - * Apply the plugin - * @param {Compiler} compiler the compiler instance - * @returns {void} - */ - apply(compiler) { - const options = this.options; - const banner = this.banner; - const matchObject = ModuleFilenameHelpers.matchObject.bind( - undefined, - options - ); + onScanFinished() { + if (this.polledWatching) { + this.timeout = setTimeout(() => { + if (this.closed) return; + this.doScan(false); + }, this.polledWatching); + } + } - compiler.hooks.compilation.tap("BannerPlugin", compilation => { - compilation.hooks.processAssets.tap( - { - name: "BannerPlugin", - stage: Compilation.PROCESS_ASSETS_STAGE_ADDITIONS - }, - () => { - for (const chunk of compilation.chunks) { - if (options.entryOnly && !chunk.canBeInitial()) { - continue; - } + onDirectoryRemoved(reason) { + if (this.watcher) { + this.watcher.close(); + this.watcher = null; + } + this.watchInParentDirectory(); + const type = `directory-removed (${reason})`; + for (const directory of this.directories.keys()) { + this.setMissing(directory, null, type); + } + for (const file of this.files.keys()) { + this.setMissing(file, null, type); + } + } - for (const file of chunk.files) { - if (!matchObject(file)) { - continue; - } + watchInParentDirectory() { + if (!this.parentWatcher) { + const parentDir = path.dirname(this.path); + // avoid watching in the root directory + // removing directories in the root directory is not supported + if (path.dirname(parentDir) === parentDir) return; - const data = { - chunk, - filename: file - }; + this.parentWatcher = this.watcherManager.watchFile(this.path, 1); + this.parentWatcher.on("change", (mtime, type) => { + if (this.closed) return; - const comment = compilation.getPath(banner, data); + // On non-osx platforms we don't need this watcher to detect + // directory removal, as an EPERM error indicates that + if ((!IS_OSX || this.polledWatching) && this.parentWatcher) { + this.parentWatcher.close(); + this.parentWatcher = null; + } + // Try to create the watcher when parent directory is found + if (!this.watcher) { + this.createWatcher(); + this.doScan(false); - compilation.updateAsset( - file, - old => new ConcatSource(comment, "\n", old) - ); - } - } + // directory was created so we emit an event + this.forEachWatcher(this.path, w => + w.emit("change", this.path, mtime, type, false) + ); } - ); - }); + }); + this.parentWatcher.on("remove", () => { + this.onDirectoryRemoved("parent directory removed"); + }); + } } -} - -module.exports = BannerPlugin; - -/***/ }), - -/***/ 99453: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ - - - -const { AsyncParallelHook, AsyncSeriesBailHook, SyncHook } = __webpack_require__(34718); -const { - makeWebpackError, - makeWebpackErrorCallback -} = __webpack_require__(89935); - -/** @typedef {import("./WebpackError")} WebpackError */ - -/** - * @typedef {Object} Etag - * @property {function(): string} toString - */ - -/** - * @template T - * @callback CallbackCache - * @param {WebpackError=} err - * @param {T=} result - * @returns {void} - */ - -/** - * @callback GotHandler - * @param {any} result - * @param {function(Error=): void} callback - * @returns {void} - */ - -const needCalls = (times, callback) => { - return err => { - if (--times === 0) { - return callback(err); + doScan(initial) { + if (this.scanning) { + if (this.scanAgain) { + if (!initial) this.scanAgainInitial = false; + } else { + this.scanAgain = true; + this.scanAgainInitial = initial; + } + return; } - if (err && times > 0) { - times = 0; - return callback(err); + this.scanning = true; + if (this.timeout) { + clearTimeout(this.timeout); + this.timeout = undefined; } - }; -}; - -class Cache { - constructor() { - this.hooks = { - /** @type {AsyncSeriesBailHook<[string, Etag | null, GotHandler[]], any>} */ - get: new AsyncSeriesBailHook(["identifier", "etag", "gotHandlers"]), - /** @type {AsyncParallelHook<[string, Etag | null, any]>} */ - store: new AsyncParallelHook(["identifier", "etag", "data"]), - /** @type {AsyncParallelHook<[Iterable]>} */ - storeBuildDependencies: new AsyncParallelHook(["dependencies"]), - /** @type {SyncHook<[]>} */ - beginIdle: new SyncHook([]), - /** @type {AsyncParallelHook<[]>} */ - endIdle: new AsyncParallelHook([]), - /** @type {AsyncParallelHook<[]>} */ - shutdown: new AsyncParallelHook([]) - }; - } - - /** - * @template T - * @param {string} identifier the cache identifier - * @param {Etag | null} etag the etag - * @param {CallbackCache} callback signals when the value is retrieved - * @returns {void} - */ - get(identifier, etag, callback) { - const gotHandlers = []; - this.hooks.get.callAsync(identifier, etag, gotHandlers, (err, result) => { - if (err) { - callback(makeWebpackError(err, "Cache.hooks.get")); - return; - } - if (result === null) { - result = undefined; - } - if (gotHandlers.length > 1) { - const innerCallback = needCalls(gotHandlers.length, () => - callback(null, result) + process.nextTick(() => { + if (this.closed) return; + fs.readdir(this.path, (err, items) => { + if (this.closed) return; + if (err) { + if (err.code === "ENOENT" || err.code === "EPERM") { + this.onDirectoryRemoved("scan readdir failed"); + } else { + this.onScanError(err); + } + this.initialScan = false; + this.initialScanFinished = Date.now(); + if (initial) { + for (const watchers of this.watchers.values()) { + for (const watcher of watchers) { + if (watcher.checkStartTime(this.initialScanFinished, false)) { + watcher.emit( + "initial-missing", + "scan (parent directory missing in initial scan)" + ); + } + } + } + } + if (this.scanAgain) { + this.scanAgain = false; + this.doScan(this.scanAgainInitial); + } else { + this.scanning = false; + } + return; + } + const itemPaths = new Set( + items.map(item => path.join(this.path, item.normalize("NFC"))) ); - for (const gotHandler of gotHandlers) { - gotHandler(result, innerCallback); + for (const file of this.files.keys()) { + if (!itemPaths.has(file)) { + this.setMissing(file, initial, "scan (missing)"); + } } - } else if (gotHandlers.length === 1) { - gotHandlers[0](result, () => callback(null, result)); - } else { - callback(null, result); - } + for (const directory of this.directories.keys()) { + if (!itemPaths.has(directory)) { + this.setMissing(directory, initial, "scan (missing)"); + } + } + if (this.scanAgain) { + // Early repeat of scan + this.scanAgain = false; + this.doScan(initial); + return; + } + const itemFinished = needCalls(itemPaths.size + 1, () => { + if (this.closed) return; + this.initialScan = false; + this.initialScanRemoved = null; + this.initialScanFinished = Date.now(); + if (initial) { + const missingWatchers = new Map(this.watchers); + missingWatchers.delete(withoutCase(this.path)); + for (const item of itemPaths) { + missingWatchers.delete(withoutCase(item)); + } + for (const watchers of missingWatchers.values()) { + for (const watcher of watchers) { + if (watcher.checkStartTime(this.initialScanFinished, false)) { + watcher.emit( + "initial-missing", + "scan (missing in initial scan)" + ); + } + } + } + } + if (this.scanAgain) { + this.scanAgain = false; + this.doScan(this.scanAgainInitial); + } else { + this.scanning = false; + this.onScanFinished(); + } + }); + for (const itemPath of itemPaths) { + fs.lstat(itemPath, (err2, stats) => { + if (this.closed) return; + if (err2) { + if ( + err2.code === "ENOENT" || + err2.code === "EPERM" || + err2.code === "EACCES" || + err2.code === "EBUSY" + ) { + this.setMissing(itemPath, initial, "scan (" + err2.code + ")"); + } else { + this.onScanError(err2); + } + itemFinished(); + return; + } + if (stats.isFile() || stats.isSymbolicLink()) { + if (stats.mtime) { + ensureFsAccuracy(stats.mtime); + } + this.setFileTime( + itemPath, + +stats.mtime || +stats.ctime || 1, + initial, + true, + "scan (file)" + ); + } else if (stats.isDirectory()) { + if (!initial || !this.directories.has(itemPath)) + this.setDirectory( + itemPath, + +stats.birthtime || 1, + initial, + "scan (dir)" + ); + } + itemFinished(); + }); + } + itemFinished(); + }); }); } - /** - * @template T - * @param {string} identifier the cache identifier - * @param {Etag | null} etag the etag - * @param {T} data the value to store - * @param {CallbackCache} callback signals when the value is stored - * @returns {void} - */ - store(identifier, etag, data, callback) { - this.hooks.store.callAsync( - identifier, - etag, - data, - makeWebpackErrorCallback(callback, "Cache.hooks.store") - ); + getTimes() { + const obj = Object.create(null); + let safeTime = this.lastWatchEvent; + for (const [file, entry] of this.files) { + fixupEntryAccuracy(entry); + safeTime = Math.max(safeTime, entry.safeTime); + obj[file] = Math.max(entry.safeTime, entry.timestamp); + } + if (this.nestedWatching) { + for (const w of this.directories.values()) { + const times = w.directoryWatcher.getTimes(); + for (const file of Object.keys(times)) { + const time = times[file]; + safeTime = Math.max(safeTime, time); + obj[file] = time; + } + } + obj[this.path] = safeTime; + } + if (!this.initialScan) { + for (const watchers of this.watchers.values()) { + for (const watcher of watchers) { + const path = watcher.path; + if (!Object.prototype.hasOwnProperty.call(obj, path)) { + obj[path] = null; + } + } + } + } + return obj; } - /** - * After this method has succeeded the cache can only be restored when build dependencies are - * @param {Iterable} dependencies list of all build dependencies - * @param {CallbackCache} callback signals when the dependencies are stored - * @returns {void} - */ - storeBuildDependencies(dependencies, callback) { - this.hooks.storeBuildDependencies.callAsync( - dependencies, - makeWebpackErrorCallback(callback, "Cache.hooks.storeBuildDependencies") - ); + collectTimeInfoEntries(fileTimestamps, directoryTimestamps) { + let safeTime = this.lastWatchEvent; + for (const [file, entry] of this.files) { + fixupEntryAccuracy(entry); + safeTime = Math.max(safeTime, entry.safeTime); + fileTimestamps.set(file, entry); + } + if (this.nestedWatching) { + for (const w of this.directories.values()) { + safeTime = Math.max( + safeTime, + w.directoryWatcher.collectTimeInfoEntries( + fileTimestamps, + directoryTimestamps, + safeTime + ) + ); + } + fileTimestamps.set(this.path, EXISTANCE_ONLY_TIME_ENTRY); + directoryTimestamps.set(this.path, { + safeTime + }); + } else { + for (const dir of this.directories.keys()) { + // No additional info about this directory + directoryTimestamps.set(dir, EXISTANCE_ONLY_TIME_ENTRY); + } + fileTimestamps.set(this.path, EXISTANCE_ONLY_TIME_ENTRY); + directoryTimestamps.set(this.path, EXISTANCE_ONLY_TIME_ENTRY); + } + if (!this.initialScan) { + for (const watchers of this.watchers.values()) { + for (const watcher of watchers) { + const path = watcher.path; + if (!fileTimestamps.has(path)) { + fileTimestamps.set(path, null); + } + } + } + } + return safeTime; } - /** - * @returns {void} - */ - beginIdle() { - this.hooks.beginIdle.call(); + close() { + this.closed = true; + this.initialScan = false; + if (this.watcher) { + this.watcher.close(); + this.watcher = null; + } + if (this.nestedWatching) { + for (const w of this.directories.values()) { + w.close(); + } + this.directories.clear(); + } + if (this.parentWatcher) { + this.parentWatcher.close(); + this.parentWatcher = null; + } + this.emit("closed"); } +} - /** - * @param {CallbackCache} callback signals when the call finishes - * @returns {void} - */ - endIdle(callback) { - this.hooks.endIdle.callAsync( - makeWebpackErrorCallback(callback, "Cache.hooks.endIdle") - ); - } +module.exports = DirectoryWatcher; +module.exports.EXISTANCE_ONLY_TIME_ENTRY = EXISTANCE_ONLY_TIME_ENTRY; - /** - * @param {CallbackCache} callback signals when the call finishes - * @returns {void} - */ - shutdown(callback) { - this.hooks.shutdown.callAsync( - makeWebpackErrorCallback(callback, "Cache.hooks.shutdown") - ); +function fixupEntryAccuracy(entry) { + if (entry.accuracy > FS_ACCURACY) { + entry.safeTime = entry.safeTime - entry.accuracy + FS_ACCURACY; + entry.accuracy = FS_ACCURACY; } } -Cache.STAGE_MEMORY = -10; -Cache.STAGE_DEFAULT = 0; -Cache.STAGE_DISK = 10; -Cache.STAGE_NETWORK = 20; - -module.exports = Cache; +function ensureFsAccuracy(mtime) { + if (!mtime) return; + if (FS_ACCURACY > 1 && mtime % 1 !== 0) FS_ACCURACY = 1; + else if (FS_ACCURACY > 10 && mtime % 10 !== 0) FS_ACCURACY = 10; + else if (FS_ACCURACY > 100 && mtime % 100 !== 0) FS_ACCURACY = 100; +} /***/ }), -/***/ 67014: +/***/ 30417: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; @@ -23444,357 +23430,172 @@ module.exports = Cache; */ +const fs = __webpack_require__(35747); +const path = __webpack_require__(85622); -const asyncLib = __webpack_require__(36386); -const getLazyHashedEtag = __webpack_require__(12339); -const mergeEtags = __webpack_require__(53885); - -/** @typedef {import("./Cache")} Cache */ -/** @typedef {import("./Cache").Etag} Etag */ -/** @typedef {import("./WebpackError")} WebpackError */ -/** @typedef {import("./cache/getLazyHashedEtag").HashableObject} HashableObject */ -/** @typedef {typeof import("./util/Hash")} HashConstructor */ - -/** - * @template T - * @callback CallbackCache - * @param {WebpackError=} err - * @param {T=} result - * @returns {void} - */ - -/** - * @template T - * @callback CallbackNormalErrorCache - * @param {Error=} err - * @param {T=} result - * @returns {void} - */ - -class MultiItemCache { - /** - * @param {ItemCacheFacade[]} items item caches - */ - constructor(items) { - this._items = items; - if (items.length === 1) return /** @type {any} */ (items[0]); - } - - /** - * @template T - * @param {CallbackCache} callback signals when the value is retrieved - * @returns {void} - */ - get(callback) { - const next = i => { - this._items[i].get((err, result) => { - if (err) return callback(err); - if (result !== undefined) return callback(null, result); - if (++i >= this._items.length) return callback(); - next(i); - }); - }; - next(0); - } +// macOS, Linux, and Windows all rely on these errors +const EXPECTED_ERRORS = new Set(["EINVAL", "ENOENT"]); - /** - * @template T - * @returns {Promise} promise with the data - */ - getPromise() { - const next = i => { - return this._items[i].getPromise().then(result => { - if (result !== undefined) return result; - if (++i < this._items.length) return next(i); - }); - }; - return next(0); - } +// On Windows there is also this error in some cases +if (process.platform === "win32") EXPECTED_ERRORS.add("UNKNOWN"); - /** - * @template T - * @param {T} data the value to store - * @param {CallbackCache} callback signals when the value is stored - * @returns {void} - */ - store(data, callback) { - asyncLib.each( - this._items, - (item, callback) => item.store(data, callback), - callback - ); +class LinkResolver { + constructor() { + this.cache = new Map(); } /** - * @template T - * @param {T} data the value to store - * @returns {Promise} promise signals when the value is stored + * @param {string} file path to file or directory + * @returns {string[]} array of file and all symlinks contributed in the resolving process (first item is the resolved file) */ - storePromise(data) { - return Promise.all(this._items.map(item => item.storePromise(data))).then( - () => {} - ); - } -} + resolve(file) { + const cacheEntry = this.cache.get(file); + if (cacheEntry !== undefined) { + return cacheEntry; + } + const parent = path.dirname(file); + if (parent === file) { + // At root of filesystem there can't be a link + const result = Object.freeze([file]); + this.cache.set(file, result); + return result; + } + // resolve the parent directory to find links there and get the real path + const parentResolved = this.resolve(parent); + let realFile = file; -class ItemCacheFacade { - /** - * @param {Cache} cache the root cache - * @param {string} name the child cache item name - * @param {Etag | null} etag the etag - */ - constructor(cache, name, etag) { - this._cache = cache; - this._name = name; - this._etag = etag; - } + // is the parent directory really somewhere else? + if (parentResolved[0] !== parent) { + // get the real location of file + const basename = path.basename(file); + realFile = path.resolve(parentResolved[0], basename); + } + // try to read the link content + try { + const linkContent = fs.readlinkSync(realFile); - /** - * @template T - * @param {CallbackCache} callback signals when the value is retrieved - * @returns {void} - */ - get(callback) { - this._cache.get(this._name, this._etag, callback); - } + // resolve the link content relative to the parent directory + const resolvedLink = path.resolve(parentResolved[0], linkContent); - /** - * @template T - * @returns {Promise} promise with the data - */ - getPromise() { - return new Promise((resolve, reject) => { - this._cache.get(this._name, this._etag, (err, data) => { - if (err) { - reject(err); - } else { - resolve(data); - } - }); - }); - } + // recursive resolve the link content for more links in the structure + const linkResolved = this.resolve(resolvedLink); - /** - * @template T - * @param {T} data the value to store - * @param {CallbackCache} callback signals when the value is stored - * @returns {void} - */ - store(data, callback) { - this._cache.store(this._name, this._etag, data, callback); - } - - /** - * @template T - * @param {T} data the value to store - * @returns {Promise} promise signals when the value is stored - */ - storePromise(data) { - return new Promise((resolve, reject) => { - this._cache.store(this._name, this._etag, data, err => { - if (err) { - reject(err); - } else { - resolve(); + // merge parent and link resolve results + let result; + if (linkResolved.length > 1 && parentResolved.length > 1) { + // when both contain links we need to duplicate them with a Set + const resultSet = new Set(linkResolved); + // add the link + resultSet.add(realFile); + // add all symlinks of the parent + for (let i = 1; i < parentResolved.length; i++) { + resultSet.add(parentResolved[i]); } - }); - }); - } - - /** - * @template T - * @param {function(CallbackNormalErrorCache): void} computer function to compute the value if not cached - * @param {CallbackNormalErrorCache} callback signals when the value is retrieved - * @returns {void} - */ - provide(computer, callback) { - this.get((err, cacheEntry) => { - if (err) return callback(err); - if (cacheEntry !== undefined) return cacheEntry; - computer((err, result) => { - if (err) return callback(err); - this.store(result, err => { - if (err) return callback(err); - callback(null, result); - }); - }); - }); - } - - /** - * @template T - * @param {function(): Promise | T} computer function to compute the value if not cached - * @returns {Promise} promise with the data - */ - async providePromise(computer) { - const cacheEntry = await this.getPromise(); - if (cacheEntry !== undefined) return cacheEntry; - const result = await computer(); - await this.storePromise(result); - return result; + result = Object.freeze(Array.from(resultSet)); + } else if (parentResolved.length > 1) { + // we have links in the parent but not for the link content location + result = parentResolved.slice(); + result[0] = linkResolved[0]; + // add the link + result.push(realFile); + Object.freeze(result); + } else if (linkResolved.length > 1) { + // we can return the link content location result + result = linkResolved.slice(); + // add the link + result.push(realFile); + Object.freeze(result); + } else { + // neither link content location nor parent have links + // this link is the only link here + result = Object.freeze([ + // the resolve real location + linkResolved[0], + // add the link + realFile + ]); + } + this.cache.set(file, result); + return result; + } catch (e) { + if (!EXPECTED_ERRORS.has(e.code)) { + throw e; + } + // no link + const result = parentResolved.slice(); + result[0] = realFile; + Object.freeze(result); + this.cache.set(file, result); + return result; + } } } +module.exports = LinkResolver; -class CacheFacade { - /** - * @param {Cache} cache the root cache - * @param {string} name the child cache name - * @param {string | HashConstructor} hashFunction the hash function to use - */ - constructor(cache, name, hashFunction) { - this._cache = cache; - this._name = name; - this._hashFunction = hashFunction; - } - - /** - * @param {string} name the child cache name# - * @returns {CacheFacade} child cache - */ - getChildCache(name) { - return new CacheFacade( - this._cache, - `${this._name}|${name}`, - this._hashFunction - ); - } - /** - * @param {string} identifier the cache identifier - * @param {Etag | null} etag the etag - * @returns {ItemCacheFacade} item cache - */ - getItemCache(identifier, etag) { - return new ItemCacheFacade( - this._cache, - `${this._name}|${identifier}`, - etag - ); - } +/***/ }), - /** - * @param {HashableObject} obj an hashable object - * @returns {Etag} an etag that is lazy hashed - */ - getLazyHashedEtag(obj) { - return getLazyHashedEtag(obj, this._hashFunction); - } +/***/ 56001: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - /** - * @param {Etag} a an etag - * @param {Etag} b another etag - * @returns {Etag} an etag that represents both - */ - mergeEtags(a, b) { - return mergeEtags(a, b); - } +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ - /** - * @template T - * @param {string} identifier the cache identifier - * @param {Etag | null} etag the etag - * @param {CallbackCache} callback signals when the value is retrieved - * @returns {void} - */ - get(identifier, etag, callback) { - this._cache.get(`${this._name}|${identifier}`, etag, callback); - } - /** - * @template T - * @param {string} identifier the cache identifier - * @param {Etag | null} etag the etag - * @returns {Promise} promise with the data - */ - getPromise(identifier, etag) { - return new Promise((resolve, reject) => { - this._cache.get(`${this._name}|${identifier}`, etag, (err, data) => { - if (err) { - reject(err); - } else { - resolve(data); - } - }); - }); - } +const path = __webpack_require__(85622); +const DirectoryWatcher = __webpack_require__(76595); - /** - * @template T - * @param {string} identifier the cache identifier - * @param {Etag | null} etag the etag - * @param {T} data the value to store - * @param {CallbackCache} callback signals when the value is stored - * @returns {void} - */ - store(identifier, etag, data, callback) { - this._cache.store(`${this._name}|${identifier}`, etag, data, callback); +class WatcherManager { + constructor(options) { + this.options = options; + this.directoryWatchers = new Map(); } - /** - * @template T - * @param {string} identifier the cache identifier - * @param {Etag | null} etag the etag - * @param {T} data the value to store - * @returns {Promise} promise signals when the value is stored - */ - storePromise(identifier, etag, data) { - return new Promise((resolve, reject) => { - this._cache.store(`${this._name}|${identifier}`, etag, data, err => { - if (err) { - reject(err); - } else { - resolve(); - } + getDirectoryWatcher(directory) { + const watcher = this.directoryWatchers.get(directory); + if (watcher === undefined) { + const newWatcher = new DirectoryWatcher(this, directory, this.options); + this.directoryWatchers.set(directory, newWatcher); + newWatcher.on("closed", () => { + this.directoryWatchers.delete(directory); }); - }); + return newWatcher; + } + return watcher; } - /** - * @template T - * @param {string} identifier the cache identifier - * @param {Etag | null} etag the etag - * @param {function(CallbackNormalErrorCache): void} computer function to compute the value if not cached - * @param {CallbackNormalErrorCache} callback signals when the value is retrieved - * @returns {void} - */ - provide(identifier, etag, computer, callback) { - this.get(identifier, etag, (err, cacheEntry) => { - if (err) return callback(err); - if (cacheEntry !== undefined) return cacheEntry; - computer((err, result) => { - if (err) return callback(err); - this.store(identifier, etag, result, err => { - if (err) return callback(err); - callback(null, result); - }); - }); - }); + watchFile(p, startTime) { + const directory = path.dirname(p); + if (directory === p) return null; + return this.getDirectoryWatcher(directory).watch(p, startTime); } - /** - * @template T - * @param {string} identifier the cache identifier - * @param {Etag | null} etag the etag - * @param {function(): Promise | T} computer function to compute the value if not cached - * @returns {Promise} promise with the data - */ - async providePromise(identifier, etag, computer) { - const cacheEntry = await this.getPromise(identifier, etag); - if (cacheEntry !== undefined) return cacheEntry; - const result = await computer(); - await this.storePromise(identifier, etag, result); - return result; + watchDirectory(directory, startTime) { + return this.getDirectoryWatcher(directory).watch(directory, startTime); } } -module.exports = CacheFacade; -module.exports.ItemCacheFacade = ItemCacheFacade; -module.exports.MultiItemCache = MultiItemCache; +const watcherManagers = new WeakMap(); +/** + * @param {object} options options + * @returns {WatcherManager} the watcher manager + */ +module.exports = options => { + const watcherManager = watcherManagers.get(options); + if (watcherManager !== undefined) return watcherManager; + const newWatcherManager = new WatcherManager(options); + watcherManagers.set(options, newWatcherManager); + return newWatcherManager; +}; +module.exports.WatcherManager = WatcherManager; /***/ }), -/***/ 42444: +/***/ 93030: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; @@ -23804,77 +23605,144 @@ module.exports.MultiItemCache = MultiItemCache; */ - -const WebpackError = __webpack_require__(68422); - -/** @typedef {import("./Module")} Module */ -/** @typedef {import("./ModuleGraph")} ModuleGraph */ +const path = __webpack_require__(85622); /** - * @param {Module[]} modules the modules to be sorted - * @returns {Module[]} sorted version of original modules + * @template T + * @typedef {Object} TreeNode + * @property {string} filePath + * @property {TreeNode} parent + * @property {TreeNode[]} children + * @property {number} entries + * @property {boolean} active + * @property {T[] | T | undefined} value */ -const sortModules = modules => { - return modules.sort((a, b) => { - const aIdent = a.identifier(); - const bIdent = b.identifier(); - /* istanbul ignore next */ - if (aIdent < bIdent) return -1; - /* istanbul ignore next */ - if (aIdent > bIdent) return 1; - /* istanbul ignore next */ - return 0; - }); -}; /** - * @param {Module[]} modules each module from throw - * @param {ModuleGraph} moduleGraph the module graph - * @returns {string} each message from provided modules + * @template T + * @param {Map>} the new plan */ -const createModulesListMessage = (modules, moduleGraph) => { - return modules - .map(m => { - let message = `* ${m.identifier()}`; - const validReasons = Array.from( - moduleGraph.getIncomingConnectionsByOriginModule(m).keys() - ).filter(x => x); - - if (validReasons.length > 0) { - message += `\n Used by ${validReasons.length} module(s), i. e.`; - message += `\n ${validReasons[0].identifier()}`; +module.exports = (plan, limit) => { + const treeMap = new Map(); + // Convert to tree + for (const [filePath, value] of plan) { + treeMap.set(filePath, { + filePath, + parent: undefined, + children: undefined, + entries: 1, + active: true, + value + }); + } + let currentCount = treeMap.size; + // Create parents and calculate sum of entries + for (const node of treeMap.values()) { + const parentPath = path.dirname(node.filePath); + if (parentPath !== node.filePath) { + let parent = treeMap.get(parentPath); + if (parent === undefined) { + parent = { + filePath: parentPath, + parent: undefined, + children: [node], + entries: node.entries, + active: false, + value: undefined + }; + treeMap.set(parentPath, parent); + node.parent = parent; + } else { + node.parent = parent; + if (parent.children === undefined) { + parent.children = [node]; + } else { + parent.children.push(node); + } + do { + parent.entries += node.entries; + parent = parent.parent; + } while (parent); } - return message; - }) - .join("\n"); -}; - -class CaseSensitiveModulesWarning extends WebpackError { - /** - * Creates an instance of CaseSensitiveModulesWarning. - * @param {Iterable} modules modules that were detected - * @param {ModuleGraph} moduleGraph the module graph - */ - constructor(modules, moduleGraph) { - const sortedModules = sortModules(Array.from(modules)); - const modulesList = createModulesListMessage(sortedModules, moduleGraph); - super(`There are multiple modules with names that only differ in casing. -This can lead to unexpected behavior when compiling on a filesystem with other case-semantic. -Use equal casing. Compare these module identifiers: -${modulesList}`); - - this.name = "CaseSensitiveModulesWarning"; - this.module = sortedModules[0]; + } } -} - -module.exports = CaseSensitiveModulesWarning; + // Reduce until limit reached + while (currentCount > limit) { + // Select node that helps reaching the limit most effectively without overmerging + const overLimit = currentCount - limit; + let bestNode = undefined; + let bestCost = Infinity; + for (const node of treeMap.values()) { + if (node.entries <= 1 || !node.children || !node.parent) continue; + if (node.children.length === 0) continue; + if (node.children.length === 1 && !node.value) continue; + // Try to select the node with has just a bit more entries than we need to reduce + // When just a bit more is over 30% over the limit, + // also consider just a bit less entries then we need to reduce + const cost = + node.entries - 1 >= overLimit + ? node.entries - 1 - overLimit + : overLimit - node.entries + 1 + limit * 0.3; + if (cost < bestCost) { + bestNode = node; + bestCost = cost; + } + } + if (!bestNode) break; + // Merge all children + const reduction = bestNode.entries - 1; + bestNode.active = true; + bestNode.entries = 1; + currentCount -= reduction; + let parent = bestNode.parent; + while (parent) { + parent.entries -= reduction; + parent = parent.parent; + } + const queue = new Set(bestNode.children); + for (const node of queue) { + node.active = false; + node.entries = 0; + if (node.children) { + for (const child of node.children) queue.add(child); + } + } + } + // Write down new plan + const newPlan = new Map(); + for (const rootNode of treeMap.values()) { + if (!rootNode.active) continue; + const map = new Map(); + const queue = new Set([rootNode]); + for (const node of queue) { + if (node.active && node !== rootNode) continue; + if (node.value) { + if (Array.isArray(node.value)) { + for (const item of node.value) { + map.set(item, node.filePath); + } + } else { + map.set(node.value, node.filePath); + } + } + if (node.children) { + for (const child of node.children) { + queue.add(child); + } + } + } + newPlan.set(rootNode.filePath, map); + } + return newPlan; +}; /***/ }), -/***/ 65574: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { +/***/ 72511: +/***/ (function(__unused_webpack_module, exports, __webpack_require__) { "use strict"; /* @@ -23883,823 +23751,733 @@ module.exports = CaseSensitiveModulesWarning; */ +const fs = __webpack_require__(35747); +const path = __webpack_require__(85622); +const { EventEmitter } = __webpack_require__(28614); +const reducePlan = __webpack_require__(93030); -const ChunkGraph = __webpack_require__(97860); -const Entrypoint = __webpack_require__(86695); -const { intersect } = __webpack_require__(34715); -const SortableSet = __webpack_require__(67563); -const StringXor = __webpack_require__(23877); -const { - compareModulesByIdentifier, - compareChunkGroupsByIndex, - compareModulesById -} = __webpack_require__(26296); -const { createArrayToSetDeprecationSet } = __webpack_require__(2594); -const { mergeRuntime } = __webpack_require__(19655); +const IS_OSX = __webpack_require__(12087).platform() === "darwin"; +const IS_WIN = __webpack_require__(12087).platform() === "win32"; +const SUPPORTS_RECURSIVE_WATCHING = IS_OSX || IS_WIN; -/** @typedef {import("webpack-sources").Source} Source */ -/** @typedef {import("./ChunkGraph").ChunkFilterPredicate} ChunkFilterPredicate */ -/** @typedef {import("./ChunkGraph").ChunkSizeOptions} ChunkSizeOptions */ -/** @typedef {import("./ChunkGraph").ModuleFilterPredicate} ModuleFilterPredicate */ -/** @typedef {import("./ChunkGroup")} ChunkGroup */ -/** @typedef {import("./Compilation")} Compilation */ -/** @typedef {import("./Compilation").AssetInfo} AssetInfo */ -/** @typedef {import("./Compilation").PathData} PathData */ -/** @typedef {import("./Entrypoint").EntryOptions} EntryOptions */ -/** @typedef {import("./Module")} Module */ -/** @typedef {import("./ModuleGraph")} ModuleGraph */ -/** @typedef {import("./util/Hash")} Hash */ -/** @typedef {import("./util/runtime").RuntimeSpec} RuntimeSpec */ +const watcherLimit = + +process.env.WATCHPACK_WATCHER_LIMIT || (IS_OSX ? 2000 : 10000); -const ChunkFilesSet = createArrayToSetDeprecationSet("chunk.files"); +const recursiveWatcherLogging = !!process.env + .WATCHPACK_RECURSIVE_WATCHER_LOGGING; -/** - * @typedef {Object} WithId an object who has an id property * - * @property {string | number} id the id of the object - */ +let isBatch = false; +let watcherCount = 0; -/** - * @deprecated - * @typedef {Object} ChunkMaps - * @property {Record} hash - * @property {Record>} contentHash - * @property {Record} name - */ +/** @type {Map} */ +const pendingWatchers = new Map(); -/** - * @deprecated - * @typedef {Object} ChunkModuleMaps - * @property {Record} id - * @property {Record} hash - */ +/** @type {Map} */ +const recursiveWatchers = new Map(); -let debugId = 1000; +/** @type {Map} */ +const directWatchers = new Map(); -/** - * A Chunk is a unit of encapsulation for Modules. - * Chunks are "rendered" into bundles that get emitted when the build completes. - */ -class Chunk { - /** - * @param {string=} name of chunk being created, is optional (for subclasses) - * @param {boolean} backCompat enable backward-compatibility - */ - constructor(name, backCompat = true) { - /** @type {number | string | null} */ - this.id = null; - /** @type {(number|string)[] | null} */ - this.ids = null; - /** @type {number} */ - this.debugId = debugId++; - /** @type {string} */ - this.name = name; - /** @type {SortableSet} */ - this.idNameHints = new SortableSet(); - /** @type {boolean} */ - this.preventIntegration = false; - /** @type {(string | function(PathData, AssetInfo=): string)?} */ - this.filenameTemplate = undefined; - /** @private @type {SortableSet} */ - this._groups = new SortableSet(undefined, compareChunkGroupsByIndex); - /** @type {RuntimeSpec} */ - this.runtime = undefined; - /** @type {Set} */ - this.files = backCompat ? new ChunkFilesSet() : new Set(); - /** @type {Set} */ - this.auxiliaryFiles = new Set(); - /** @type {boolean} */ - this.rendered = false; - /** @type {string=} */ - this.hash = undefined; - /** @type {Record} */ - this.contentHash = Object.create(null); - /** @type {string=} */ - this.renderedHash = undefined; - /** @type {string=} */ - this.chunkReason = undefined; - /** @type {boolean} */ - this.extraAsync = false; - } +/** @type {Map} */ +const underlyingWatcher = new Map(); - // TODO remove in webpack 6 - // BACKWARD-COMPAT START - get entryModule() { - const entryModules = Array.from( - ChunkGraph.getChunkGraphForChunk( - this, - "Chunk.entryModule", - "DEP_WEBPACK_CHUNK_ENTRY_MODULE" - ).getChunkEntryModulesIterable(this) - ); - if (entryModules.length === 0) { - return undefined; - } else if (entryModules.length === 1) { - return entryModules[0]; - } else { - throw new Error( - "Module.entryModule: Multiple entry modules are not supported by the deprecated API (Use the new ChunkGroup API)" - ); +class DirectWatcher { + constructor(filePath) { + this.filePath = filePath; + this.watchers = new Set(); + this.watcher = undefined; + try { + const watcher = fs.watch(filePath); + this.watcher = watcher; + watcher.on("change", (type, filename) => { + for (const w of this.watchers) { + w.emit("change", type, filename); + } + }); + watcher.on("error", error => { + for (const w of this.watchers) { + w.emit("error", error); + } + }); + } catch (err) { + process.nextTick(() => { + for (const w of this.watchers) { + w.emit("error", err); + } + }); } + watcherCount++; } - /** - * @returns {boolean} true, if the chunk contains an entry module - */ - hasEntryModule() { - return ( - ChunkGraph.getChunkGraphForChunk( - this, - "Chunk.hasEntryModule", - "DEP_WEBPACK_CHUNK_HAS_ENTRY_MODULE" - ).getNumberOfEntryModules(this) > 0 - ); + add(watcher) { + underlyingWatcher.set(watcher, this); + this.watchers.add(watcher); } - /** - * @param {Module} module the module - * @returns {boolean} true, if the chunk could be added - */ - addModule(module) { - const chunkGraph = ChunkGraph.getChunkGraphForChunk( - this, - "Chunk.addModule", - "DEP_WEBPACK_CHUNK_ADD_MODULE" - ); - if (chunkGraph.isModuleInChunk(module, this)) return false; - chunkGraph.connectChunkAndModule(this, module); - return true; + remove(watcher) { + this.watchers.delete(watcher); + if (this.watchers.size === 0) { + directWatchers.delete(this.filePath); + watcherCount--; + if (this.watcher) this.watcher.close(); + } } - /** - * @param {Module} module the module - * @returns {void} - */ - removeModule(module) { - ChunkGraph.getChunkGraphForChunk( - this, - "Chunk.removeModule", - "DEP_WEBPACK_CHUNK_REMOVE_MODULE" - ).disconnectChunkAndModule(this, module); + getWatchers() { + return this.watchers; } +} - /** - * @returns {number} the number of module which are contained in this chunk - */ - getNumberOfModules() { - return ChunkGraph.getChunkGraphForChunk( - this, - "Chunk.getNumberOfModules", - "DEP_WEBPACK_CHUNK_GET_NUMBER_OF_MODULES" - ).getNumberOfChunkModules(this); +class RecursiveWatcher { + constructor(rootPath) { + this.rootPath = rootPath; + /** @type {Map} */ + this.mapWatcherToPath = new Map(); + /** @type {Map>} */ + this.mapPathToWatchers = new Map(); + this.watcher = undefined; + try { + const watcher = fs.watch(rootPath, { + recursive: true + }); + this.watcher = watcher; + watcher.on("change", (type, filename) => { + if (!filename) { + if (recursiveWatcherLogging) { + process.stderr.write( + `[watchpack] dispatch ${type} event in recursive watcher (${ + this.rootPath + }) to all watchers\n` + ); + } + for (const w of this.mapWatcherToPath.keys()) { + w.emit("change", type); + } + } else { + const dir = path.dirname(filename); + const watchers = this.mapPathToWatchers.get(dir); + if (recursiveWatcherLogging) { + process.stderr.write( + `[watchpack] dispatch ${type} event in recursive watcher (${ + this.rootPath + }) for '${filename}' to ${ + watchers ? watchers.size : 0 + } watchers\n` + ); + } + if (watchers === undefined) return; + for (const w of watchers) { + w.emit("change", type, path.basename(filename)); + } + } + }); + watcher.on("error", error => { + for (const w of this.mapWatcherToPath.keys()) { + w.emit("error", error); + } + }); + } catch (err) { + process.nextTick(() => { + for (const w of this.mapWatcherToPath.keys()) { + w.emit("error", err); + } + }); + } + watcherCount++; + if (recursiveWatcherLogging) { + process.stderr.write( + `[watchpack] created recursive watcher at ${rootPath}\n` + ); + } } - get modulesIterable() { - const chunkGraph = ChunkGraph.getChunkGraphForChunk( - this, - "Chunk.modulesIterable", - "DEP_WEBPACK_CHUNK_MODULES_ITERABLE" - ); - return chunkGraph.getOrderedChunkModulesIterable( - this, - compareModulesByIdentifier - ); + add(filePath, watcher) { + underlyingWatcher.set(watcher, this); + const subpath = filePath.slice(this.rootPath.length + 1) || "."; + this.mapWatcherToPath.set(watcher, subpath); + const set = this.mapPathToWatchers.get(subpath); + if (set === undefined) { + const newSet = new Set(); + newSet.add(watcher); + this.mapPathToWatchers.set(subpath, newSet); + } else { + set.add(watcher); + } } - /** - * @param {Chunk} otherChunk the chunk to compare with - * @returns {-1|0|1} the comparison result - */ - compareTo(otherChunk) { - const chunkGraph = ChunkGraph.getChunkGraphForChunk( - this, - "Chunk.compareTo", - "DEP_WEBPACK_CHUNK_COMPARE_TO" - ); - return chunkGraph.compareChunks(this, otherChunk); + remove(watcher) { + const subpath = this.mapWatcherToPath.get(watcher); + if (!subpath) return; + this.mapWatcherToPath.delete(watcher); + const set = this.mapPathToWatchers.get(subpath); + set.delete(watcher); + if (set.size === 0) { + this.mapPathToWatchers.delete(subpath); + } + if (this.mapWatcherToPath.size === 0) { + recursiveWatchers.delete(this.rootPath); + watcherCount--; + if (this.watcher) this.watcher.close(); + if (recursiveWatcherLogging) { + process.stderr.write( + `[watchpack] closed recursive watcher at ${this.rootPath}\n` + ); + } + } } - /** - * @param {Module} module the module - * @returns {boolean} true, if the chunk contains the module - */ - containsModule(module) { - return ChunkGraph.getChunkGraphForChunk( - this, - "Chunk.containsModule", - "DEP_WEBPACK_CHUNK_CONTAINS_MODULE" - ).isModuleInChunk(module, this); + getWatchers() { + return this.mapWatcherToPath; } +} - /** - * @returns {Module[]} the modules for this chunk - */ - getModules() { - return ChunkGraph.getChunkGraphForChunk( - this, - "Chunk.getModules", - "DEP_WEBPACK_CHUNK_GET_MODULES" - ).getChunkModules(this); +class Watcher extends EventEmitter { + close() { + if (pendingWatchers.has(this)) { + pendingWatchers.delete(this); + return; + } + const watcher = underlyingWatcher.get(this); + watcher.remove(this); + underlyingWatcher.delete(this); } +} - /** - * @returns {void} - */ - remove() { - const chunkGraph = ChunkGraph.getChunkGraphForChunk( - this, - "Chunk.remove", - "DEP_WEBPACK_CHUNK_REMOVE" - ); - chunkGraph.disconnectChunk(this); - this.disconnectFromGroups(); - } +const createDirectWatcher = filePath => { + const existing = directWatchers.get(filePath); + if (existing !== undefined) return existing; + const w = new DirectWatcher(filePath); + directWatchers.set(filePath, w); + return w; +}; - /** - * @param {Module} module the module - * @param {Chunk} otherChunk the target chunk - * @returns {void} - */ - moveModule(module, otherChunk) { - const chunkGraph = ChunkGraph.getChunkGraphForChunk( - this, - "Chunk.moveModule", - "DEP_WEBPACK_CHUNK_MOVE_MODULE" - ); - chunkGraph.disconnectChunkAndModule(this, module); - chunkGraph.connectChunkAndModule(otherChunk, module); - } +const createRecursiveWatcher = rootPath => { + const existing = recursiveWatchers.get(rootPath); + if (existing !== undefined) return existing; + const w = new RecursiveWatcher(rootPath); + recursiveWatchers.set(rootPath, w); + return w; +}; - /** - * @param {Chunk} otherChunk the other chunk - * @returns {boolean} true, if the specified chunk has been integrated - */ - integrate(otherChunk) { - const chunkGraph = ChunkGraph.getChunkGraphForChunk( - this, - "Chunk.integrate", - "DEP_WEBPACK_CHUNK_INTEGRATE" - ); - if (chunkGraph.canChunksBeIntegrated(this, otherChunk)) { - chunkGraph.integrateChunks(this, otherChunk); - return true; +const execute = () => { + /** @type {Map} */ + const map = new Map(); + const addWatcher = (watcher, filePath) => { + const entry = map.get(filePath); + if (entry === undefined) { + map.set(filePath, watcher); + } else if (Array.isArray(entry)) { + entry.push(watcher); } else { - return false; + map.set(filePath, [entry, watcher]); } + }; + for (const [watcher, filePath] of pendingWatchers) { + addWatcher(watcher, filePath); } + pendingWatchers.clear(); - /** - * @param {Chunk} otherChunk the other chunk - * @returns {boolean} true, if chunks could be integrated - */ - canBeIntegrated(otherChunk) { - const chunkGraph = ChunkGraph.getChunkGraphForChunk( - this, - "Chunk.canBeIntegrated", - "DEP_WEBPACK_CHUNK_CAN_BE_INTEGRATED" - ); - return chunkGraph.canChunksBeIntegrated(this, otherChunk); + // Fast case when we are not reaching the limit + if (!SUPPORTS_RECURSIVE_WATCHING || watcherLimit - watcherCount >= map.size) { + // Create watchers for all entries in the map + for (const [filePath, entry] of map) { + const w = createDirectWatcher(filePath); + if (Array.isArray(entry)) { + for (const item of entry) w.add(item); + } else { + w.add(entry); + } + } + return; } - /** - * @returns {boolean} true, if this chunk contains no module - */ - isEmpty() { - const chunkGraph = ChunkGraph.getChunkGraphForChunk( - this, - "Chunk.isEmpty", - "DEP_WEBPACK_CHUNK_IS_EMPTY" - ); - return chunkGraph.getNumberOfChunkModules(this) === 0; + // Reconsider existing watchers to improving watch plan + for (const watcher of recursiveWatchers.values()) { + for (const [w, subpath] of watcher.getWatchers()) { + addWatcher(w, path.join(watcher.rootPath, subpath)); + } } - - /** - * @returns {number} total size of all modules in this chunk - */ - modulesSize() { - const chunkGraph = ChunkGraph.getChunkGraphForChunk( - this, - "Chunk.modulesSize", - "DEP_WEBPACK_CHUNK_MODULES_SIZE" - ); - return chunkGraph.getChunkModulesSize(this); + for (const watcher of directWatchers.values()) { + for (const w of watcher.getWatchers()) { + addWatcher(w, watcher.filePath); + } } - /** - * @param {ChunkSizeOptions} options options object - * @returns {number} total size of this chunk - */ - size(options = {}) { - const chunkGraph = ChunkGraph.getChunkGraphForChunk( - this, - "Chunk.size", - "DEP_WEBPACK_CHUNK_SIZE" - ); - return chunkGraph.getChunkSize(this, options); - } + // Merge map entries to keep watcher limit + // Create a 10% buffer to be able to enter fast case more often + const plan = reducePlan(map, watcherLimit * 0.9); - /** - * @param {Chunk} otherChunk the other chunk - * @param {ChunkSizeOptions} options options object - * @returns {number} total size of the chunk or false if the chunk can't be integrated - */ - integratedSize(otherChunk, options) { - const chunkGraph = ChunkGraph.getChunkGraphForChunk( - this, - "Chunk.integratedSize", - "DEP_WEBPACK_CHUNK_INTEGRATED_SIZE" - ); - return chunkGraph.getIntegratedChunksSize(this, otherChunk, options); + // Update watchers for all entries in the map + for (const [filePath, entry] of plan) { + if (entry.size === 1) { + for (const [watcher, filePath] of entry) { + const w = createDirectWatcher(filePath); + const old = underlyingWatcher.get(watcher); + if (old === w) continue; + w.add(watcher); + if (old !== undefined) old.remove(watcher); + } + } else { + const filePaths = new Set(entry.values()); + if (filePaths.size > 1) { + const w = createRecursiveWatcher(filePath); + for (const [watcher, watcherPath] of entry) { + const old = underlyingWatcher.get(watcher); + if (old === w) continue; + w.add(watcherPath, watcher); + if (old !== undefined) old.remove(watcher); + } + } else { + for (const filePath of filePaths) { + const w = createDirectWatcher(filePath); + for (const watcher of entry.keys()) { + const old = underlyingWatcher.get(watcher); + if (old === w) continue; + w.add(watcher); + if (old !== undefined) old.remove(watcher); + } + } + } + } } +}; - /** - * @param {ModuleFilterPredicate} filterFn function used to filter modules - * @returns {ChunkModuleMaps} module map information - */ - getChunkModuleMaps(filterFn) { - const chunkGraph = ChunkGraph.getChunkGraphForChunk( - this, - "Chunk.getChunkModuleMaps", - "DEP_WEBPACK_CHUNK_GET_CHUNK_MODULE_MAPS" - ); - /** @type {Record} */ - const chunkModuleIdMap = Object.create(null); - /** @type {Record} */ - const chunkModuleHashMap = Object.create(null); - - for (const asyncChunk of this.getAllAsyncChunks()) { - /** @type {(string|number)[]} */ - let array; - for (const module of chunkGraph.getOrderedChunkModulesIterable( - asyncChunk, - compareModulesById(chunkGraph) - )) { - if (filterFn(module)) { - if (array === undefined) { - array = []; - chunkModuleIdMap[asyncChunk.id] = array; - } - const moduleId = chunkGraph.getModuleId(module); - array.push(moduleId); - chunkModuleHashMap[moduleId] = chunkGraph.getRenderedModuleHash( - module, - undefined - ); - } - } - } - - return { - id: chunkModuleIdMap, - hash: chunkModuleHashMap - }; - } - - /** - * @param {ModuleFilterPredicate} filterFn predicate function used to filter modules - * @param {ChunkFilterPredicate=} filterChunkFn predicate function used to filter chunks - * @returns {boolean} return true if module exists in graph - */ - hasModuleInGraph(filterFn, filterChunkFn) { - const chunkGraph = ChunkGraph.getChunkGraphForChunk( - this, - "Chunk.hasModuleInGraph", - "DEP_WEBPACK_CHUNK_HAS_MODULE_IN_GRAPH" - ); - return chunkGraph.hasModuleInGraph(this, filterFn, filterChunkFn); +exports.watch = filePath => { + const watcher = new Watcher(); + // Find an existing watcher + const directWatcher = directWatchers.get(filePath); + if (directWatcher !== undefined) { + directWatcher.add(watcher); + return watcher; } - - /** - * @deprecated - * @param {boolean} realHash whether the full hash or the rendered hash is to be used - * @returns {ChunkMaps} the chunk map information - */ - getChunkMaps(realHash) { - /** @type {Record} */ - const chunkHashMap = Object.create(null); - /** @type {Record>} */ - const chunkContentHashMap = Object.create(null); - /** @type {Record} */ - const chunkNameMap = Object.create(null); - - for (const chunk of this.getAllAsyncChunks()) { - chunkHashMap[chunk.id] = realHash ? chunk.hash : chunk.renderedHash; - for (const key of Object.keys(chunk.contentHash)) { - if (!chunkContentHashMap[key]) { - chunkContentHashMap[key] = Object.create(null); - } - chunkContentHashMap[key][chunk.id] = chunk.contentHash[key]; - } - if (chunk.name) { - chunkNameMap[chunk.id] = chunk.name; - } + let current = filePath; + for (;;) { + const recursiveWatcher = recursiveWatchers.get(current); + if (recursiveWatcher !== undefined) { + recursiveWatcher.add(filePath, watcher); + return watcher; } - - return { - hash: chunkHashMap, - contentHash: chunkContentHashMap, - name: chunkNameMap - }; + const parent = path.dirname(current); + if (parent === current) break; + current = parent; } - // BACKWARD-COMPAT END + // Queue up watcher for creation + pendingWatchers.set(watcher, filePath); + if (!isBatch) execute(); + return watcher; +}; - /** - * @returns {boolean} whether or not the Chunk will have a runtime - */ - hasRuntime() { - for (const chunkGroup of this._groups) { - if ( - chunkGroup instanceof Entrypoint && - chunkGroup.getRuntimeChunk() === this - ) { - return true; - } - } - return false; +exports.batch = fn => { + isBatch = true; + try { + fn(); + } finally { + isBatch = false; + execute(); } +}; - /** - * @returns {boolean} whether or not this chunk can be an initial chunk - */ - canBeInitial() { - for (const chunkGroup of this._groups) { - if (chunkGroup.isInitial()) return true; - } - return false; - } +exports.getNumberOfWatchers = () => { + return watcherCount; +}; - /** - * @returns {boolean} whether this chunk can only be an initial chunk - */ - isOnlyInitial() { - if (this._groups.size <= 0) return false; - for (const chunkGroup of this._groups) { - if (!chunkGroup.isInitial()) return false; - } - return true; - } - /** - * @returns {EntryOptions | undefined} the entry options for this chunk - */ - getEntryOptions() { - for (const chunkGroup of this._groups) { - if (chunkGroup instanceof Entrypoint) { - return chunkGroup.options; - } - } - return undefined; - } +/***/ }), - /** - * @param {ChunkGroup} chunkGroup the chunkGroup the chunk is being added - * @returns {void} - */ - addGroup(chunkGroup) { - this._groups.add(chunkGroup); - } +/***/ 29149: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - /** - * @param {ChunkGroup} chunkGroup the chunkGroup the chunk is being removed from - * @returns {void} - */ - removeGroup(chunkGroup) { - this._groups.delete(chunkGroup); - } +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ - /** - * @param {ChunkGroup} chunkGroup the chunkGroup to check - * @returns {boolean} returns true if chunk has chunkGroup reference and exists in chunkGroup - */ - isInGroup(chunkGroup) { - return this._groups.has(chunkGroup); - } - /** - * @returns {number} the amount of groups that the said chunk is in - */ - getNumberOfGroups() { - return this._groups.size; - } +const getWatcherManager = __webpack_require__(56001); +const LinkResolver = __webpack_require__(30417); +const EventEmitter = __webpack_require__(28614).EventEmitter; +const globToRegExp = __webpack_require__(22797); +const watchEventSource = __webpack_require__(72511); - /** - * @returns {Iterable} the chunkGroups that the said chunk is referenced in - */ - get groupsIterable() { - this._groups.sort(); - return this._groups; - } +const EMPTY_ARRAY = []; +const EMPTY_OPTIONS = {}; - /** - * @returns {void} - */ - disconnectFromGroups() { - for (const chunkGroup of this._groups) { - chunkGroup.removeChunk(this); +function addWatchersToSet(watchers, set) { + for (const ww of watchers) { + const w = ww.watcher; + if (!set.has(w.directoryWatcher)) { + set.add(w.directoryWatcher); } } +} - /** - * @param {Chunk} newChunk the new chunk that will be split out of - * @returns {void} - */ - split(newChunk) { - for (const chunkGroup of this._groups) { - chunkGroup.insertChunk(newChunk, this); - newChunk.addGroup(chunkGroup); - } - for (const idHint of this.idNameHints) { - newChunk.idNameHints.add(idHint); - } - newChunk.runtime = mergeRuntime(newChunk.runtime, this.runtime); - } +const stringToRegexp = ignored => { + const source = globToRegExp(ignored, { globstar: true, extended: true }) + .source; + const matchingStart = source.slice(0, source.length - 1) + "(?:$|\\/)"; + return matchingStart; +}; - /** - * @param {Hash} hash hash (will be modified) - * @param {ChunkGraph} chunkGraph the chunk graph - * @returns {void} - */ - updateHash(hash, chunkGraph) { - hash.update( - `${this.id} ${this.ids ? this.ids.join() : ""} ${this.name || ""} ` - ); - const xor = new StringXor(); - for (const m of chunkGraph.getChunkModulesIterable(this)) { - xor.add(chunkGraph.getModuleHash(m, this.runtime)); - } - xor.updateHash(hash); - const entryModules = - chunkGraph.getChunkEntryModulesWithChunkGroupIterable(this); - for (const [m, chunkGroup] of entryModules) { - hash.update(`entry${chunkGraph.getModuleId(m)}${chunkGroup.id}`); - } +const ignoredToFunction = ignored => { + if (Array.isArray(ignored)) { + const regexp = new RegExp(ignored.map(i => stringToRegexp(i)).join("|")); + return x => regexp.test(x.replace(/\\/g, "/")); + } else if (typeof ignored === "string") { + const regexp = new RegExp(stringToRegexp(ignored)); + return x => regexp.test(x.replace(/\\/g, "/")); + } else if (ignored instanceof RegExp) { + return x => ignored.test(x.replace(/\\/g, "/")); + } else if (ignored instanceof Function) { + return ignored; + } else if (ignored) { + throw new Error(`Invalid option for 'ignored': ${ignored}`); + } else { + return () => false; } +}; - /** - * @returns {Set} a set of all the async chunks - */ - getAllAsyncChunks() { - const queue = new Set(); - const chunks = new Set(); - - const initialChunks = intersect( - Array.from(this.groupsIterable, g => new Set(g.chunks)) - ); +const normalizeOptions = options => { + return { + followSymlinks: !!options.followSymlinks, + ignored: ignoredToFunction(options.ignored), + poll: options.poll + }; +}; - const initialQueue = new Set(this.groupsIterable); +const normalizeCache = new WeakMap(); +const cachedNormalizeOptions = options => { + const cacheEntry = normalizeCache.get(options); + if (cacheEntry !== undefined) return cacheEntry; + const normalized = normalizeOptions(options); + normalizeCache.set(options, normalized); + return normalized; +}; - for (const chunkGroup of initialQueue) { - for (const child of chunkGroup.childrenIterable) { - if (child instanceof Entrypoint) { - initialQueue.add(child); - } else { - queue.add(child); - } +class WatchpackFileWatcher { + constructor(watchpack, watcher, files) { + if (!watcher) throw new Error(); + this.files = Array.isArray(files) ? files : [files]; + this.watcher = watcher; + watcher.on("initial-missing", type => { + for (const file of this.files) { + if (!watchpack._missing.has(file)) + watchpack._onRemove(file, file, type); } - } - - for (const chunkGroup of queue) { - for (const chunk of chunkGroup.chunks) { - if (!initialChunks.has(chunk)) { - chunks.add(chunk); - } + }); + watcher.on("change", (mtime, type) => { + for (const file of this.files) { + watchpack._onChange(file, mtime, file, type); } - for (const child of chunkGroup.childrenIterable) { - queue.add(child); + }); + watcher.on("remove", type => { + for (const file of this.files) { + watchpack._onRemove(file, file, type); } - } - - return chunks; + }); } - /** - * @returns {Set} a set of all the initial chunks (including itself) - */ - getAllInitialChunks() { - const chunks = new Set(); - const queue = new Set(this.groupsIterable); - for (const group of queue) { - if (group.isInitial()) { - for (const c of group.chunks) chunks.add(c); - for (const g of group.childrenIterable) queue.add(g); + update(files) { + if (!Array.isArray(files)) { + if (this.files.length !== 1) { + this.files = [files]; + } else if (this.files[0] !== files) { + this.files[0] = files; } + } else { + this.files = files; } - return chunks; } - /** - * @returns {Set} a set of all the referenced chunks (including itself) - */ - getAllReferencedChunks() { - const queue = new Set(this.groupsIterable); - const chunks = new Set(); + close() { + this.watcher.close(); + } +} - for (const chunkGroup of queue) { - for (const chunk of chunkGroup.chunks) { - chunks.add(chunk); +class WatchpackDirectoryWatcher { + constructor(watchpack, watcher, directories) { + if (!watcher) throw new Error(); + this.directories = Array.isArray(directories) ? directories : [directories]; + this.watcher = watcher; + watcher.on("initial-missing", type => { + for (const item of this.directories) { + watchpack._onRemove(item, item, type); } - for (const child of chunkGroup.childrenIterable) { - queue.add(child); + }); + watcher.on("change", (file, mtime, type) => { + for (const item of this.directories) { + watchpack._onChange(item, mtime, file, type); } - } - - return chunks; + }); + watcher.on("remove", type => { + for (const item of this.directories) { + watchpack._onRemove(item, item, type); + } + }); } - /** - * @returns {Set} a set of all the referenced entrypoints - */ - getAllReferencedAsyncEntrypoints() { - const queue = new Set(this.groupsIterable); - const entrypoints = new Set(); - - for (const chunkGroup of queue) { - for (const entrypoint of chunkGroup.asyncEntrypointsIterable) { - entrypoints.add(entrypoint); - } - for (const child of chunkGroup.childrenIterable) { - queue.add(child); + update(directories) { + if (!Array.isArray(directories)) { + if (this.directories.length !== 1) { + this.directories = [directories]; + } else if (this.directories[0] !== directories) { + this.directories[0] = directories; } + } else { + this.directories = directories; } - - return entrypoints; } - /** - * @returns {boolean} true, if the chunk references async chunks - */ - hasAsyncChunks() { - const queue = new Set(); + close() { + this.watcher.close(); + } +} - const initialChunks = intersect( - Array.from(this.groupsIterable, g => new Set(g.chunks)) - ); +class Watchpack extends EventEmitter { + constructor(options) { + super(); + if (!options) options = EMPTY_OPTIONS; + this.options = options; + this.aggregateTimeout = + typeof options.aggregateTimeout === "number" + ? options.aggregateTimeout + : 200; + this.watcherOptions = cachedNormalizeOptions(options); + this.watcherManager = getWatcherManager(this.watcherOptions); + this.fileWatchers = new Map(); + this.directoryWatchers = new Map(); + this._missing = new Set(); + this.startTime = undefined; + this.paused = false; + this.aggregatedChanges = new Set(); + this.aggregatedRemovals = new Set(); + this.aggregateTimer = undefined; + this._onTimeout = this._onTimeout.bind(this); + } - for (const chunkGroup of this.groupsIterable) { - for (const child of chunkGroup.childrenIterable) { - queue.add(child); - } + watch(arg1, arg2, arg3) { + let files, directories, missing, startTime; + if (!arg2) { + ({ + files = EMPTY_ARRAY, + directories = EMPTY_ARRAY, + missing = EMPTY_ARRAY, + startTime + } = arg1); + } else { + files = arg1; + directories = arg2; + missing = EMPTY_ARRAY; + startTime = arg3; } - - for (const chunkGroup of queue) { - for (const chunk of chunkGroup.chunks) { - if (!initialChunks.has(chunk)) { - return true; + this.paused = false; + const fileWatchers = this.fileWatchers; + const directoryWatchers = this.directoryWatchers; + const ignored = this.watcherOptions.ignored; + const filter = path => !ignored(path); + const addToMap = (map, key, item) => { + const list = map.get(key); + if (list === undefined) { + map.set(key, item); + } else if (Array.isArray(list)) { + list.push(item); + } else { + map.set(key, [list, item]); + } + }; + const fileWatchersNeeded = new Map(); + const directoryWatchersNeeded = new Map(); + const missingFiles = new Set(); + if (this.watcherOptions.followSymlinks) { + const resolver = new LinkResolver(); + for (const file of files) { + if (filter(file)) { + for (const innerFile of resolver.resolve(file)) { + if (file === innerFile || filter(innerFile)) { + addToMap(fileWatchersNeeded, innerFile, file); + } + } } } - for (const child of chunkGroup.childrenIterable) { - queue.add(child); + for (const file of missing) { + if (filter(file)) { + for (const innerFile of resolver.resolve(file)) { + if (file === innerFile || filter(innerFile)) { + missingFiles.add(file); + addToMap(fileWatchersNeeded, innerFile, file); + } + } + } } - } - - return false; - } - - /** - * @param {ChunkGraph} chunkGraph the chunk graph - * @param {ChunkFilterPredicate=} filterFn function used to filter chunks - * @returns {Record} a record object of names to lists of child ids(?) - */ - getChildIdsByOrders(chunkGraph, filterFn) { - /** @type {Map} */ - const lists = new Map(); - for (const group of this.groupsIterable) { - if (group.chunks[group.chunks.length - 1] === this) { - for (const childGroup of group.childrenIterable) { - for (const key of Object.keys(childGroup.options)) { - if (key.endsWith("Order")) { - const name = key.substr(0, key.length - "Order".length); - let list = lists.get(name); - if (list === undefined) { - list = []; - lists.set(name, list); - } - list.push({ - order: childGroup.options[key], - group: childGroup - }); + for (const dir of directories) { + if (filter(dir)) { + let first = true; + for (const innerItem of resolver.resolve(dir)) { + if (filter(innerItem)) { + addToMap( + first ? directoryWatchersNeeded : fileWatchersNeeded, + innerItem, + dir + ); } + first = false; } } } - } - /** @type {Record} */ - const result = Object.create(null); - for (const [name, list] of lists) { - list.sort((a, b) => { - const cmp = b.order - a.order; - if (cmp !== 0) return cmp; - return a.group.compareTo(chunkGraph, b.group); - }); - /** @type {Set} */ - const chunkIdSet = new Set(); - for (const item of list) { - for (const chunk of item.group.chunks) { - if (filterFn && !filterFn(chunk, chunkGraph)) continue; - chunkIdSet.add(chunk.id); + } else { + for (const file of files) { + if (filter(file)) { + addToMap(fileWatchersNeeded, file, file); } } - if (chunkIdSet.size > 0) { - result[name] = Array.from(chunkIdSet); + for (const file of missing) { + if (filter(file)) { + missingFiles.add(file); + addToMap(fileWatchersNeeded, file, file); + } + } + for (const dir of directories) { + if (filter(dir)) { + addToMap(directoryWatchersNeeded, dir, dir); + } } } - return result; - } - - /** - * @param {ChunkGraph} chunkGraph the chunk graph - * @param {string} type option name - * @returns {{ onChunks: Chunk[], chunks: Set }[]} referenced chunks for a specific type - */ - getChildrenOfTypeInOrder(chunkGraph, type) { - const list = []; - for (const group of this.groupsIterable) { - for (const childGroup of group.childrenIterable) { - const order = childGroup.options[type]; - if (order === undefined) continue; - list.push({ - order, - group, - childGroup - }); + // Close unneeded old watchers + // and update existing watchers + for (const [key, w] of fileWatchers) { + const needed = fileWatchersNeeded.get(key); + if (needed === undefined) { + w.close(); + fileWatchers.delete(key); + } else { + w.update(needed); + fileWatchersNeeded.delete(key); } } - if (list.length === 0) return undefined; - list.sort((a, b) => { - const cmp = b.order - a.order; - if (cmp !== 0) return cmp; - return a.group.compareTo(chunkGraph, b.group); - }); - const result = []; - let lastEntry; - for (const { group, childGroup } of list) { - if (lastEntry && lastEntry.onChunks === group.chunks) { - for (const chunk of childGroup.chunks) { - lastEntry.chunks.add(chunk); - } + for (const [key, w] of directoryWatchers) { + const needed = directoryWatchersNeeded.get(key); + if (needed === undefined) { + w.close(); + directoryWatchers.delete(key); } else { - result.push( - (lastEntry = { - onChunks: group.chunks, - chunks: new Set(childGroup.chunks) - }) - ); + w.update(needed); + directoryWatchersNeeded.delete(key); } } - return result; - } - - /** - * @param {ChunkGraph} chunkGraph the chunk graph - * @param {boolean=} includeDirectChildren include direct children (by default only children of async children are included) - * @param {ChunkFilterPredicate=} filterFn function used to filter chunks - * @returns {Record>} a record object of names to lists of child ids(?) by chunk id - */ - getChildIdsByOrdersMap(chunkGraph, includeDirectChildren, filterFn) { - /** @type {Record>} */ - const chunkMaps = Object.create(null); - - /** - * @param {Chunk} chunk a chunk - * @returns {void} - */ - const addChildIdsByOrdersToMap = chunk => { - const data = chunk.getChildIdsByOrders(chunkGraph, filterFn); - for (const key of Object.keys(data)) { - let chunkMap = chunkMaps[key]; - if (chunkMap === undefined) { - chunkMaps[key] = chunkMap = Object.create(null); + // Create new watchers and install handlers on these watchers + watchEventSource.batch(() => { + for (const [key, files] of fileWatchersNeeded) { + const watcher = this.watcherManager.watchFile(key, startTime); + if (watcher) { + fileWatchers.set(key, new WatchpackFileWatcher(this, watcher, files)); } - chunkMap[chunk.id] = data[key]; } - }; - - if (includeDirectChildren) { - /** @type {Set} */ - const chunks = new Set(); - for (const chunkGroup of this.groupsIterable) { - for (const chunk of chunkGroup.chunks) { - chunks.add(chunk); + for (const [key, directories] of directoryWatchersNeeded) { + const watcher = this.watcherManager.watchDirectory(key, startTime); + if (watcher) { + directoryWatchers.set( + key, + new WatchpackDirectoryWatcher(this, watcher, directories) + ); } } - for (const chunk of chunks) { - addChildIdsByOrdersToMap(chunk); - } + }); + this._missing = missingFiles; + this.startTime = startTime; + } + + close() { + this.paused = true; + if (this.aggregateTimer) clearTimeout(this.aggregateTimer); + for (const w of this.fileWatchers.values()) w.close(); + for (const w of this.directoryWatchers.values()) w.close(); + this.fileWatchers.clear(); + this.directoryWatchers.clear(); + } + + pause() { + this.paused = true; + if (this.aggregateTimer) clearTimeout(this.aggregateTimer); + } + + getTimes() { + const directoryWatchers = new Set(); + addWatchersToSet(this.fileWatchers.values(), directoryWatchers); + addWatchersToSet(this.directoryWatchers.values(), directoryWatchers); + const obj = Object.create(null); + for (const w of directoryWatchers) { + const times = w.getTimes(); + for (const file of Object.keys(times)) obj[file] = times[file]; } + return obj; + } - for (const chunk of this.getAllAsyncChunks()) { - addChildIdsByOrdersToMap(chunk); + getTimeInfoEntries() { + const map = new Map(); + this.collectTimeInfoEntries(map, map); + return map; + } + + collectTimeInfoEntries(fileTimestamps, directoryTimestamps) { + const allWatchers = new Set(); + addWatchersToSet(this.fileWatchers.values(), allWatchers); + addWatchersToSet(this.directoryWatchers.values(), allWatchers); + const safeTime = { value: 0 }; + for (const w of allWatchers) { + w.collectTimeInfoEntries(fileTimestamps, directoryTimestamps, safeTime); } + } - return chunkMaps; + getAggregated() { + if (this.aggregateTimer) { + clearTimeout(this.aggregateTimer); + this.aggregateTimer = undefined; + } + const changes = this.aggregatedChanges; + const removals = this.aggregatedRemovals; + this.aggregatedChanges = new Set(); + this.aggregatedRemovals = new Set(); + return { changes, removals }; + } + + _onChange(item, mtime, file, type) { + file = file || item; + if (!this.paused) { + this.emit("change", file, mtime, type); + if (this.aggregateTimer) clearTimeout(this.aggregateTimer); + this.aggregateTimer = setTimeout(this._onTimeout, this.aggregateTimeout); + } + this.aggregatedRemovals.delete(item); + this.aggregatedChanges.add(item); + } + + _onRemove(item, file, type) { + file = file || item; + if (!this.paused) { + this.emit("remove", file, type); + if (this.aggregateTimer) clearTimeout(this.aggregateTimer); + this.aggregateTimer = setTimeout(this._onTimeout, this.aggregateTimeout); + } + this.aggregatedChanges.delete(item); + this.aggregatedRemovals.add(item); + } + + _onTimeout() { + this.aggregateTimer = undefined; + const changes = this.aggregatedChanges; + const removals = this.aggregatedRemovals; + this.aggregatedChanges = new Set(); + this.aggregatedRemovals = new Set(); + this.emit("aggregated", changes, removals); } } -module.exports = Chunk; +module.exports = Watchpack; /***/ }), -/***/ 97860: +/***/ 46806: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; @@ -24710,2236 +24488,1949 @@ module.exports = Chunk; -const util = __webpack_require__(31669); -const Entrypoint = __webpack_require__(86695); -const ModuleGraphConnection = __webpack_require__(94144); -const { first } = __webpack_require__(34715); -const SortableSet = __webpack_require__(67563); -const { - compareModulesById, - compareIterables, - compareModulesByIdentifier, - concatComparators, - compareSelect, - compareIds -} = __webpack_require__(26296); -const createHash = __webpack_require__(24123); -const findGraphRoots = __webpack_require__(38670); +const RuntimeGlobals = __webpack_require__(49404); +const WebpackError = __webpack_require__(68422); +const ConstDependency = __webpack_require__(60864); +const BasicEvaluatedExpression = __webpack_require__(2412); const { - RuntimeSpecMap, - RuntimeSpecSet, - runtimeToString, - mergeRuntime, - forEachRuntime -} = __webpack_require__(19655); + toConstantDependency, + evaluateToString +} = __webpack_require__(28723); +const ChunkNameRuntimeModule = __webpack_require__(43818); +const GetFullHashRuntimeModule = __webpack_require__(28454); -/** @typedef {import("./AsyncDependenciesBlock")} AsyncDependenciesBlock */ -/** @typedef {import("./Chunk")} Chunk */ -/** @typedef {import("./ChunkGroup")} ChunkGroup */ -/** @typedef {import("./Module")} Module */ -/** @typedef {import("./ModuleGraph")} ModuleGraph */ -/** @typedef {import("./RuntimeModule")} RuntimeModule */ -/** @typedef {typeof import("./util/Hash")} Hash */ -/** @typedef {import("./util/runtime").RuntimeSpec} RuntimeSpec */ +/** @typedef {import("./Compiler")} Compiler */ +/** @typedef {import("./javascript/JavascriptParser")} JavascriptParser */ -/** @type {ReadonlySet} */ -const EMPTY_SET = new Set(); +/* eslint-disable camelcase */ +const REPLACEMENTS = { + __webpack_require__: { + expr: RuntimeGlobals.require, + req: [RuntimeGlobals.require], + type: "function", + assign: false + }, + __webpack_public_path__: { + expr: RuntimeGlobals.publicPath, + req: [RuntimeGlobals.publicPath], + type: "string", + assign: true + }, + __webpack_base_uri__: { + expr: RuntimeGlobals.baseURI, + req: [RuntimeGlobals.baseURI], + type: "string", + assign: true + }, + __webpack_modules__: { + expr: RuntimeGlobals.moduleFactories, + req: [RuntimeGlobals.moduleFactories], + type: "object", + assign: false + }, + __webpack_chunk_load__: { + expr: RuntimeGlobals.ensureChunk, + req: [RuntimeGlobals.ensureChunk], + type: "function", + assign: true + }, + __non_webpack_require__: { + expr: "require", + req: null, + type: undefined, // type is not known, depends on environment + assign: true + }, + __webpack_nonce__: { + expr: RuntimeGlobals.scriptNonce, + req: [RuntimeGlobals.scriptNonce], + type: "string", + assign: true + }, + __webpack_hash__: { + expr: `${RuntimeGlobals.getFullHash}()`, + req: [RuntimeGlobals.getFullHash], + type: "string", + assign: false + }, + __webpack_chunkname__: { + expr: RuntimeGlobals.chunkName, + req: [RuntimeGlobals.chunkName], + type: "string", + assign: false + }, + __webpack_get_script_filename__: { + expr: RuntimeGlobals.getChunkScriptFilename, + req: [RuntimeGlobals.getChunkScriptFilename], + type: "function", + assign: true + }, + __webpack_runtime_id__: { + expr: RuntimeGlobals.runtimeId, + req: [RuntimeGlobals.runtimeId], + assign: false + }, + "require.onError": { + expr: RuntimeGlobals.uncaughtErrorHandler, + req: [RuntimeGlobals.uncaughtErrorHandler], + type: undefined, // type is not known, could be function or undefined + assign: true // is never a pattern + }, + __system_context__: { + expr: RuntimeGlobals.systemContext, + req: [RuntimeGlobals.systemContext], + type: "object", + assign: false + }, + __webpack_share_scopes__: { + expr: RuntimeGlobals.shareScopeMap, + req: [RuntimeGlobals.shareScopeMap], + type: "object", + assign: false + }, + __webpack_init_sharing__: { + expr: RuntimeGlobals.initializeSharing, + req: [RuntimeGlobals.initializeSharing], + type: "function", + assign: true + } +}; +/* eslint-enable camelcase */ -const ZERO_BIG_INT = BigInt(0); +class APIPlugin { + /** + * Apply the plugin + * @param {Compiler} compiler the compiler instance + * @returns {void} + */ + apply(compiler) { + compiler.hooks.compilation.tap( + "APIPlugin", + (compilation, { normalModuleFactory }) => { + compilation.dependencyTemplates.set( + ConstDependency, + new ConstDependency.Template() + ); -const compareModuleIterables = compareIterables(compareModulesByIdentifier); + compilation.hooks.runtimeRequirementInTree + .for(RuntimeGlobals.chunkName) + .tap("APIPlugin", chunk => { + compilation.addRuntimeModule( + chunk, + new ChunkNameRuntimeModule(chunk.name) + ); + return true; + }); -/** @typedef {(c: Chunk, chunkGraph: ChunkGraph) => boolean} ChunkFilterPredicate */ -/** @typedef {(m: Module) => boolean} ModuleFilterPredicate */ + compilation.hooks.runtimeRequirementInTree + .for(RuntimeGlobals.getFullHash) + .tap("APIPlugin", (chunk, set) => { + compilation.addRuntimeModule(chunk, new GetFullHashRuntimeModule()); + return true; + }); -/** - * @typedef {Object} ChunkSizeOptions - * @property {number=} chunkOverhead constant overhead for a chunk - * @property {number=} entryChunkMultiplicator multiplicator for initial chunks - */ + /** + * @param {JavascriptParser} parser the parser + */ + const handler = parser => { + Object.keys(REPLACEMENTS).forEach(key => { + const info = REPLACEMENTS[key]; + parser.hooks.expression + .for(key) + .tap( + "APIPlugin", + toConstantDependency(parser, info.expr, info.req) + ); + if (info.assign === false) { + parser.hooks.assign.for(key).tap("APIPlugin", expr => { + const err = new WebpackError(`${key} must not be assigned`); + err.loc = expr.loc; + throw err; + }); + } + if (info.type) { + parser.hooks.evaluateTypeof + .for(key) + .tap("APIPlugin", evaluateToString(info.type)); + } + }); -class ModuleHashInfo { - constructor(hash, renderedHash) { - this.hash = hash; - this.renderedHash = renderedHash; + parser.hooks.expression + .for("__webpack_layer__") + .tap("APIPlugin", expr => { + const dep = new ConstDependency( + JSON.stringify(parser.state.module.layer), + expr.range + ); + dep.loc = expr.loc; + parser.state.module.addPresentationalDependency(dep); + return true; + }); + parser.hooks.evaluateIdentifier + .for("__webpack_layer__") + .tap("APIPlugin", expr => + (parser.state.module.layer === null + ? new BasicEvaluatedExpression().setNull() + : new BasicEvaluatedExpression().setString( + parser.state.module.layer + ) + ).setRange(expr.range) + ); + parser.hooks.evaluateTypeof + .for("__webpack_layer__") + .tap("APIPlugin", expr => + new BasicEvaluatedExpression() + .setString( + parser.state.module.layer === null ? "object" : "string" + ) + .setRange(expr.range) + ); + }; + + normalModuleFactory.hooks.parser + .for("javascript/auto") + .tap("APIPlugin", handler); + normalModuleFactory.hooks.parser + .for("javascript/dynamic") + .tap("APIPlugin", handler); + normalModuleFactory.hooks.parser + .for("javascript/esm") + .tap("APIPlugin", handler); + } + ); } } -/** @template T @typedef {(set: SortableSet) => T[]} SetToArrayFunction */ +module.exports = APIPlugin; -/** - * @template T - * @param {SortableSet} set the set - * @returns {T[]} set as array - */ -const getArray = set => { - return Array.from(set); -}; -/** - * @param {SortableSet} chunks the chunks - * @returns {RuntimeSpecSet} runtimes - */ -const getModuleRuntimes = chunks => { - const runtimes = new RuntimeSpecSet(); - for (const chunk of chunks) { - runtimes.add(chunk.runtime); - } - return runtimes; -}; +/***/ }), -/** - * @param {SortableSet} set the set - * @returns {Map>} modules by source type - */ -const modulesBySourceType = set => { - /** @type {Map>} */ - const map = new Map(); - for (const module of set) { - for (const sourceType of module.getSourceTypes()) { - let innerSet = map.get(sourceType); - if (innerSet === undefined) { - innerSet = new SortableSet(); - map.set(sourceType, innerSet); - } - innerSet.add(module); - } - } - for (const [key, innerSet] of map) { - // When all modules have the source type, we reuse the original SortableSet - // to benefit from the shared cache (especially for sorting) - if (innerSet.size === set.size) { - map.set(key, set); - } - } - return map; -}; +/***/ 570: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { -/** @type {WeakMap} */ -const createOrderedArrayFunctionMap = new WeakMap(); +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Ivan Kopeykin @vankop +*/ -/** - * @template T - * @param {function(T, T): -1|0|1} comparator comparator function - * @returns {SetToArrayFunction} set as ordered array - */ -const createOrderedArrayFunction = comparator => { - /** @type {SetToArrayFunction} */ - let fn = createOrderedArrayFunctionMap.get(comparator); - if (fn !== undefined) return fn; - fn = set => { - set.sortWith(comparator); - return Array.from(set); - }; - createOrderedArrayFunctionMap.set(comparator, fn); - return fn; -}; + + +const WebpackError = __webpack_require__(68422); +const CURRENT_METHOD_REGEXP = /at ([a-zA-Z0-9_.]*)/; /** - * @param {Iterable} modules the modules to get the count/size of - * @returns {number} the size of the modules + * @param {string=} method method name + * @returns {string} message */ -const getModulesSize = modules => { - let size = 0; - for (const module of modules) { - for (const type of module.getSourceTypes()) { - size += module.size(type); - } - } - return size; -}; +function createMessage(method) { + return `Abstract method${method ? " " + method : ""}. Must be overridden.`; +} /** - * @param {Iterable} modules the sortable Set to get the size of - * @returns {Record} the sizes of the modules + * @constructor */ -const getModulesSizes = modules => { - let sizes = Object.create(null); - for (const module of modules) { - for (const type of module.getSourceTypes()) { - sizes[type] = (sizes[type] || 0) + module.size(type); - } - } - return sizes; -}; +function Message() { + /** @type {string} */ + this.stack = undefined; + Error.captureStackTrace(this); + /** @type {RegExpMatchArray} */ + const match = this.stack.split("\n")[3].match(CURRENT_METHOD_REGEXP); + + this.message = match && match[1] ? createMessage(match[1]) : createMessage(); +} /** - * @param {Chunk} a chunk - * @param {Chunk} b chunk - * @returns {boolean} true, if a is always a parent of b + * Error for abstract method + * @example + * class FooClass { + * abstractMethod() { + * throw new AbstractMethodError(); // error message: Abstract method FooClass.abstractMethod. Must be overridden. + * } + * } + * */ -const isAvailableChunk = (a, b) => { - const queue = new Set(b.groupsIterable); - for (const chunkGroup of queue) { - if (a.isInGroup(chunkGroup)) continue; - if (chunkGroup.isInitial()) return false; - for (const parent of chunkGroup.parentsIterable) { - queue.add(parent); - } - } - return true; -}; - -class ChunkGraphModule { +class AbstractMethodError extends WebpackError { constructor() { - /** @type {SortableSet} */ - this.chunks = new SortableSet(); - /** @type {Set | undefined} */ - this.entryInChunks = undefined; - /** @type {Set | undefined} */ - this.runtimeInChunks = undefined; - /** @type {RuntimeSpecMap} */ - this.hashes = undefined; - /** @type {string | number} */ - this.id = null; - /** @type {RuntimeSpecMap> | undefined} */ - this.runtimeRequirements = undefined; - /** @type {RuntimeSpecMap} */ - this.graphHashes = undefined; - /** @type {RuntimeSpecMap} */ - this.graphHashesWithConnections = undefined; + super(new Message().message); + this.name = "AbstractMethodError"; } } -class ChunkGraphChunk { - constructor() { - /** @type {SortableSet} */ - this.modules = new SortableSet(); - /** @type {Map} */ - this.entryModules = new Map(); - /** @type {SortableSet} */ - this.runtimeModules = new SortableSet(); - /** @type {Set | undefined} */ - this.fullHashModules = undefined; - /** @type {Set | undefined} */ - this.dependentHashModules = undefined; - /** @type {Set | undefined} */ - this.runtimeRequirements = undefined; - /** @type {Set} */ - this.runtimeRequirementsInTree = new Set(); - } -} +module.exports = AbstractMethodError; -class ChunkGraph { - /** - * @param {ModuleGraph} moduleGraph the module graph - * @param {string | Hash} hashFunction the hash function to use - */ - constructor(moduleGraph, hashFunction = "md4") { - /** @private @type {WeakMap} */ - this._modules = new WeakMap(); - /** @private @type {WeakMap} */ - this._chunks = new WeakMap(); - /** @private @type {WeakMap} */ - this._blockChunkGroups = new WeakMap(); - /** @private @type {Map} */ - this._runtimeIds = new Map(); - /** @type {ModuleGraph} */ - this.moduleGraph = moduleGraph; - this._hashFunction = hashFunction; +/***/ }), - this._getGraphRoots = this._getGraphRoots.bind(this); - } +/***/ 11315: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - /** - * @private - * @param {Module} module the module - * @returns {ChunkGraphModule} internal module - */ - _getChunkGraphModule(module) { - let cgm = this._modules.get(module); - if (cgm === undefined) { - cgm = new ChunkGraphModule(); - this._modules.set(module, cgm); - } - return cgm; - } +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ - /** - * @private - * @param {Chunk} chunk the chunk - * @returns {ChunkGraphChunk} internal chunk - */ - _getChunkGraphChunk(chunk) { - let cgc = this._chunks.get(chunk); - if (cgc === undefined) { - cgc = new ChunkGraphChunk(); - this._chunks.set(chunk, cgc); - } - return cgc; - } - /** - * @param {SortableSet} set the sortable Set to get the roots of - * @returns {Module[]} the graph roots - */ - _getGraphRoots(set) { - const { moduleGraph } = this; - return Array.from( - findGraphRoots(set, module => { - /** @type {Set} */ - const set = new Set(); - const addDependencies = module => { - for (const connection of moduleGraph.getOutgoingConnections(module)) { - if (!connection.module) continue; - const activeState = connection.getActiveState(undefined); - if (activeState === false) continue; - if (activeState === ModuleGraphConnection.TRANSITIVE_ONLY) { - addDependencies(connection.module); - continue; - } - set.add(connection.module); - } - }; - addDependencies(module); - return set; - }) - ).sort(compareModulesByIdentifier); - } +const DependenciesBlock = __webpack_require__(21484); +const makeSerializable = __webpack_require__(26522); + +/** @typedef {import("./ChunkGraph")} ChunkGraph */ +/** @typedef {import("./ChunkGroup")} ChunkGroup */ +/** @typedef {import("./ChunkGroup").ChunkGroupOptions} ChunkGroupOptions */ +/** @typedef {import("./Dependency").DependencyLocation} DependencyLocation */ +/** @typedef {import("./Dependency").UpdateHashContext} UpdateHashContext */ +/** @typedef {import("./Entrypoint").EntryOptions} EntryOptions */ +/** @typedef {import("./Module")} Module */ +/** @typedef {import("./util/Hash")} Hash */ + +class AsyncDependenciesBlock extends DependenciesBlock { /** - * @param {Chunk} chunk the new chunk - * @param {Module} module the module - * @returns {void} + * @param {ChunkGroupOptions & { entryOptions?: EntryOptions }} groupOptions options for the group + * @param {DependencyLocation=} loc the line of code + * @param {string=} request the request */ - connectChunkAndModule(chunk, module) { - const cgm = this._getChunkGraphModule(module); - const cgc = this._getChunkGraphChunk(chunk); - cgm.chunks.add(chunk); - cgc.modules.add(module); + constructor(groupOptions, loc, request) { + super(); + if (typeof groupOptions === "string") { + groupOptions = { name: groupOptions }; + } else if (!groupOptions) { + groupOptions = { name: undefined }; + } + this.groupOptions = groupOptions; + this.loc = loc; + this.request = request; + this._stringifiedGroupOptions = undefined; } /** - * @param {Chunk} chunk the chunk - * @param {Module} module the module - * @returns {void} + * @returns {string} The name of the chunk */ - disconnectChunkAndModule(chunk, module) { - const cgm = this._getChunkGraphModule(module); - const cgc = this._getChunkGraphChunk(chunk); - cgc.modules.delete(module); - cgm.chunks.delete(chunk); + get chunkName() { + return this.groupOptions.name; } /** - * @param {Chunk} chunk the chunk which will be disconnected + * @param {string} value The new chunk name * @returns {void} */ - disconnectChunk(chunk) { - const cgc = this._getChunkGraphChunk(chunk); - for (const module of cgc.modules) { - const cgm = this._getChunkGraphModule(module); - cgm.chunks.delete(chunk); + set chunkName(value) { + if (this.groupOptions.name !== value) { + this.groupOptions.name = value; + this._stringifiedGroupOptions = undefined; } - cgc.modules.clear(); - chunk.disconnectFromGroups(); - ChunkGraph.clearChunkGraphForChunk(chunk); } /** - * @param {Chunk} chunk the chunk - * @param {Iterable} modules the modules + * @param {Hash} hash the hash used to track dependencies + * @param {UpdateHashContext} context context * @returns {void} */ - attachModules(chunk, modules) { - const cgc = this._getChunkGraphChunk(chunk); - for (const module of modules) { - cgc.modules.add(module); + updateHash(hash, context) { + const { chunkGraph } = context; + if (this._stringifiedGroupOptions === undefined) { + this._stringifiedGroupOptions = JSON.stringify(this.groupOptions); } + const chunkGroup = chunkGraph.getBlockChunkGroup(this); + hash.update( + `${this._stringifiedGroupOptions}${chunkGroup ? chunkGroup.id : ""}` + ); + super.updateHash(hash, context); } - /** - * @param {Chunk} chunk the chunk - * @param {Iterable} modules the runtime modules - * @returns {void} - */ - attachRuntimeModules(chunk, modules) { - const cgc = this._getChunkGraphChunk(chunk); - for (const module of modules) { - cgc.runtimeModules.add(module); - } + serialize(context) { + const { write } = context; + write(this.groupOptions); + write(this.loc); + write(this.request); + super.serialize(context); } - /** - * @param {Chunk} chunk the chunk - * @param {Iterable} modules the modules that require a full hash - * @returns {void} - */ - attachFullHashModules(chunk, modules) { - const cgc = this._getChunkGraphChunk(chunk); - if (cgc.fullHashModules === undefined) cgc.fullHashModules = new Set(); - for (const module of modules) { - cgc.fullHashModules.add(module); - } + deserialize(context) { + const { read } = context; + this.groupOptions = read(); + this.loc = read(); + this.request = read(); + super.deserialize(context); } +} - /** - * @param {Chunk} chunk the chunk - * @param {Iterable} modules the modules that require a full hash - * @returns {void} - */ - attachDependentHashModules(chunk, modules) { - const cgc = this._getChunkGraphChunk(chunk); - if (cgc.dependentHashModules === undefined) - cgc.dependentHashModules = new Set(); - for (const module of modules) { - cgc.dependentHashModules.add(module); - } +makeSerializable(AsyncDependenciesBlock, "webpack/lib/AsyncDependenciesBlock"); + +Object.defineProperty(AsyncDependenciesBlock.prototype, "module", { + get() { + throw new Error( + "module property was removed from AsyncDependenciesBlock (it's not needed)" + ); + }, + set() { + throw new Error( + "module property was removed from AsyncDependenciesBlock (it's not needed)" + ); } +}); - /** - * @param {Module} oldModule the replaced module - * @param {Module} newModule the replacing module - * @returns {void} - */ - replaceModule(oldModule, newModule) { - const oldCgm = this._getChunkGraphModule(oldModule); - const newCgm = this._getChunkGraphModule(newModule); +module.exports = AsyncDependenciesBlock; - for (const chunk of oldCgm.chunks) { - const cgc = this._getChunkGraphChunk(chunk); - cgc.modules.delete(oldModule); - cgc.modules.add(newModule); - newCgm.chunks.add(chunk); - } - oldCgm.chunks.clear(); - if (oldCgm.entryInChunks !== undefined) { - if (newCgm.entryInChunks === undefined) { - newCgm.entryInChunks = new Set(); - } - for (const chunk of oldCgm.entryInChunks) { - const cgc = this._getChunkGraphChunk(chunk); - const old = cgc.entryModules.get(oldModule); - /** @type {Map} */ - const newEntryModules = new Map(); - for (const [m, cg] of cgc.entryModules) { - if (m === oldModule) { - newEntryModules.set(newModule, old); - } else { - newEntryModules.set(m, cg); - } - } - cgc.entryModules = newEntryModules; - newCgm.entryInChunks.add(chunk); - } - oldCgm.entryInChunks = undefined; - } +/***/ }), - if (oldCgm.runtimeInChunks !== undefined) { - if (newCgm.runtimeInChunks === undefined) { - newCgm.runtimeInChunks = new Set(); - } - for (const chunk of oldCgm.runtimeInChunks) { - const cgc = this._getChunkGraphChunk(chunk); - cgc.runtimeModules.delete(/** @type {RuntimeModule} */ (oldModule)); - cgc.runtimeModules.add(/** @type {RuntimeModule} */ (newModule)); - newCgm.runtimeInChunks.add(chunk); - if ( - cgc.fullHashModules !== undefined && - cgc.fullHashModules.has(/** @type {RuntimeModule} */ (oldModule)) - ) { - cgc.fullHashModules.delete(/** @type {RuntimeModule} */ (oldModule)); - cgc.fullHashModules.add(/** @type {RuntimeModule} */ (newModule)); - } - if ( - cgc.dependentHashModules !== undefined && - cgc.dependentHashModules.has(/** @type {RuntimeModule} */ (oldModule)) - ) { - cgc.dependentHashModules.delete( - /** @type {RuntimeModule} */ (oldModule) - ); - cgc.dependentHashModules.add( - /** @type {RuntimeModule} */ (newModule) - ); - } - } - oldCgm.runtimeInChunks = undefined; - } - } +/***/ 69073: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - /** - * @param {Module} module the checked module - * @param {Chunk} chunk the checked chunk - * @returns {boolean} true, if the chunk contains the module - */ - isModuleInChunk(module, chunk) { - const cgc = this._getChunkGraphChunk(chunk); - return cgc.modules.has(module); - } +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Sean Larkin @thelarkinn +*/ - /** - * @param {Module} module the checked module - * @param {ChunkGroup} chunkGroup the checked chunk group - * @returns {boolean} true, if the chunk contains the module - */ - isModuleInChunkGroup(module, chunkGroup) { - for (const chunk of chunkGroup.chunks) { - if (this.isModuleInChunk(module, chunk)) return true; - } - return false; - } - /** - * @param {Module} module the checked module - * @returns {boolean} true, if the module is entry of any chunk - */ - isEntryModule(module) { - const cgm = this._getChunkGraphModule(module); - return cgm.entryInChunks !== undefined; - } - /** - * @param {Module} module the module - * @returns {Iterable} iterable of chunks (do not modify) - */ - getModuleChunksIterable(module) { - const cgm = this._getChunkGraphModule(module); - return cgm.chunks; - } +const WebpackError = __webpack_require__(68422); - /** - * @param {Module} module the module - * @param {function(Chunk, Chunk): -1|0|1} sortFn sort function - * @returns {Iterable} iterable of chunks (do not modify) - */ - getOrderedModuleChunksIterable(module, sortFn) { - const cgm = this._getChunkGraphModule(module); - cgm.chunks.sortWith(sortFn); - return cgm.chunks; - } +/** @typedef {import("./Dependency").DependencyLocation} DependencyLocation */ +/** @typedef {import("./Module")} Module */ +class AsyncDependencyToInitialChunkError extends WebpackError { /** - * @param {Module} module the module - * @returns {Chunk[]} array of chunks (cached, do not modify) + * Creates an instance of AsyncDependencyToInitialChunkError. + * @param {string} chunkName Name of Chunk + * @param {Module} module module tied to dependency + * @param {DependencyLocation} loc location of dependency */ - getModuleChunks(module) { - const cgm = this._getChunkGraphModule(module); - return cgm.chunks.getFromCache(getArray); - } + constructor(chunkName, module, loc) { + super( + `It's not allowed to load an initial chunk on demand. The chunk name "${chunkName}" is already used by an entrypoint.` + ); - /** - * @param {Module} module the module - * @returns {number} the number of chunk which contain the module - */ - getNumberOfModuleChunks(module) { - const cgm = this._getChunkGraphModule(module); - return cgm.chunks.size; + this.name = "AsyncDependencyToInitialChunkError"; + this.module = module; + this.loc = loc; } +} - /** - * @param {Module} module the module - * @returns {RuntimeSpecSet} runtimes - */ - getModuleRuntimes(module) { - const cgm = this._getChunkGraphModule(module); - return cgm.chunks.getFromUnorderedCache(getModuleRuntimes); - } +module.exports = AsyncDependencyToInitialChunkError; - /** - * @param {Chunk} chunk the chunk - * @returns {number} the number of modules which are contained in this chunk - */ - getNumberOfChunkModules(chunk) { - const cgc = this._getChunkGraphChunk(chunk); - return cgc.modules.size; - } - /** - * @param {Chunk} chunk the chunk - * @returns {number} the number of full hash modules which are contained in this chunk - */ - getNumberOfChunkFullHashModules(chunk) { - const cgc = this._getChunkGraphChunk(chunk); - return cgc.fullHashModules === undefined ? 0 : cgc.fullHashModules.size; - } +/***/ }), - /** - * @param {Chunk} chunk the chunk - * @returns {Iterable} return the modules for this chunk - */ - getChunkModulesIterable(chunk) { - const cgc = this._getChunkGraphChunk(chunk); - return cgc.modules; - } +/***/ 51714: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - /** - * @param {Chunk} chunk the chunk - * @param {string} sourceType source type - * @returns {Iterable | undefined} return the modules for this chunk - */ - getChunkModulesIterableBySourceType(chunk, sourceType) { - const cgc = this._getChunkGraphChunk(chunk); - const modulesWithSourceType = cgc.modules - .getFromUnorderedCache(modulesBySourceType) - .get(sourceType); - return modulesWithSourceType; - } +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ - /** - * @param {Chunk} chunk the chunk - * @param {function(Module, Module): -1|0|1} comparator comparator function - * @returns {Iterable} return the modules for this chunk - */ - getOrderedChunkModulesIterable(chunk, comparator) { - const cgc = this._getChunkGraphChunk(chunk); - cgc.modules.sortWith(comparator); - return cgc.modules; - } + +const asyncLib = __webpack_require__(36386); +const NormalModule = __webpack_require__(11026); +const PrefetchDependency = __webpack_require__(39986); + +/** @typedef {import("./Compiler")} Compiler */ + +class AutomaticPrefetchPlugin { /** - * @param {Chunk} chunk the chunk - * @param {string} sourceType source type - * @param {function(Module, Module): -1|0|1} comparator comparator function - * @returns {Iterable | undefined} return the modules for this chunk + * Apply the plugin + * @param {Compiler} compiler the compiler instance + * @returns {void} */ - getOrderedChunkModulesIterableBySourceType(chunk, sourceType, comparator) { - const cgc = this._getChunkGraphChunk(chunk); - const modulesWithSourceType = cgc.modules - .getFromUnorderedCache(modulesBySourceType) - .get(sourceType); - if (modulesWithSourceType === undefined) return undefined; - modulesWithSourceType.sortWith(comparator); - return modulesWithSourceType; - } + apply(compiler) { + compiler.hooks.compilation.tap( + "AutomaticPrefetchPlugin", + (compilation, { normalModuleFactory }) => { + compilation.dependencyFactories.set( + PrefetchDependency, + normalModuleFactory + ); + } + ); + let lastModules = null; + compiler.hooks.afterCompile.tap("AutomaticPrefetchPlugin", compilation => { + lastModules = []; - /** - * @param {Chunk} chunk the chunk - * @returns {Module[]} return the modules for this chunk (cached, do not modify) - */ - getChunkModules(chunk) { - const cgc = this._getChunkGraphChunk(chunk); - return cgc.modules.getFromUnorderedCache(getArray); + for (const m of compilation.modules) { + if (m instanceof NormalModule) { + lastModules.push({ + context: m.context, + request: m.request + }); + } + } + }); + compiler.hooks.make.tapAsync( + "AutomaticPrefetchPlugin", + (compilation, callback) => { + if (!lastModules) return callback(); + asyncLib.forEach( + lastModules, + (m, callback) => { + compilation.addModuleChain( + m.context || compiler.context, + new PrefetchDependency(`!!${m.request}`), + callback + ); + }, + err => { + lastModules = null; + callback(err); + } + ); + } + ); } +} +module.exports = AutomaticPrefetchPlugin; - /** - * @param {Chunk} chunk the chunk - * @param {function(Module, Module): -1|0|1} comparator comparator function - * @returns {Module[]} return the modules for this chunk (cached, do not modify) - */ - getOrderedChunkModules(chunk, comparator) { - const cgc = this._getChunkGraphChunk(chunk); - const arrayFunction = createOrderedArrayFunction(comparator); - return cgc.modules.getFromUnorderedCache(arrayFunction); - } - /** - * @param {Chunk} chunk the chunk - * @param {ModuleFilterPredicate} filterFn function used to filter modules - * @param {boolean} includeAllChunks all chunks or only async chunks - * @returns {Record} chunk to module ids object - */ - getChunkModuleIdMap(chunk, filterFn, includeAllChunks = false) { - /** @type {Record} */ - const chunkModuleIdMap = Object.create(null); +/***/ }), - for (const asyncChunk of includeAllChunks - ? chunk.getAllReferencedChunks() - : chunk.getAllAsyncChunks()) { - /** @type {(string|number)[]} */ - let array; - for (const module of this.getOrderedChunkModulesIterable( - asyncChunk, - compareModulesById(this) - )) { - if (filterFn(module)) { - if (array === undefined) { - array = []; - chunkModuleIdMap[asyncChunk.id] = array; - } - const moduleId = this.getModuleId(module); - array.push(moduleId); - } - } - } +/***/ 45480: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - return chunkModuleIdMap; - } +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ - /** - * @param {Chunk} chunk the chunk - * @param {ModuleFilterPredicate} filterFn function used to filter modules - * @param {number} hashLength length of the hash - * @param {boolean} includeAllChunks all chunks or only async chunks - * @returns {Record>} chunk to module id to module hash object - */ - getChunkModuleRenderedHashMap( - chunk, - filterFn, - hashLength = 0, - includeAllChunks = false - ) { - /** @type {Record>} */ - const chunkModuleHashMap = Object.create(null); - for (const asyncChunk of includeAllChunks - ? chunk.getAllReferencedChunks() - : chunk.getAllAsyncChunks()) { - /** @type {Record} */ - let idToHashMap; - for (const module of this.getOrderedChunkModulesIterable( - asyncChunk, - compareModulesById(this) - )) { - if (filterFn(module)) { - if (idToHashMap === undefined) { - idToHashMap = Object.create(null); - chunkModuleHashMap[asyncChunk.id] = idToHashMap; - } - const moduleId = this.getModuleId(module); - const hash = this.getRenderedModuleHash(module, asyncChunk.runtime); - idToHashMap[moduleId] = hashLength ? hash.slice(0, hashLength) : hash; - } - } - } - return chunkModuleHashMap; +const { ConcatSource } = __webpack_require__(96192); +const Compilation = __webpack_require__(59622); +const ModuleFilenameHelpers = __webpack_require__(80295); +const Template = __webpack_require__(92066); +const createSchemaValidation = __webpack_require__(77695); + +/** @typedef {import("../declarations/plugins/BannerPlugin").BannerPluginArgument} BannerPluginArgument */ +/** @typedef {import("../declarations/plugins/BannerPlugin").BannerPluginOptions} BannerPluginOptions */ +/** @typedef {import("./Compiler")} Compiler */ + +const validate = createSchemaValidation( + __webpack_require__(79456), + () => __webpack_require__(33946), + { + name: "Banner Plugin", + baseDataPath: "options" + } +); + +const wrapComment = str => { + if (!str.includes("\n")) { + return Template.toComment(str); } + return `/*!\n * ${str + .replace(/\*\//g, "* /") + .split("\n") + .join("\n * ") + .replace(/\s+\n/g, "\n") + .trimRight()}\n */`; +}; +class BannerPlugin { /** - * @param {Chunk} chunk the chunk - * @param {ChunkFilterPredicate} filterFn function used to filter chunks - * @returns {Record} chunk map + * @param {BannerPluginArgument} options options object */ - getChunkConditionMap(chunk, filterFn) { - const map = Object.create(null); - for (const c of chunk.getAllReferencedChunks()) { - map[c.id] = filterFn(c, this); + constructor(options) { + if (typeof options === "string" || typeof options === "function") { + options = { + banner: options + }; + } + + validate(options); + + this.options = options; + + const bannerOption = options.banner; + if (typeof bannerOption === "function") { + const getBanner = bannerOption; + this.banner = this.options.raw + ? getBanner + : data => wrapComment(getBanner(data)); + } else { + const banner = this.options.raw + ? bannerOption + : wrapComment(bannerOption); + this.banner = () => banner; } - return map; } /** - * @param {Chunk} chunk the chunk - * @param {ModuleFilterPredicate} filterFn predicate function used to filter modules - * @param {ChunkFilterPredicate=} filterChunkFn predicate function used to filter chunks - * @returns {boolean} return true if module exists in graph + * Apply the plugin + * @param {Compiler} compiler the compiler instance + * @returns {void} */ - hasModuleInGraph(chunk, filterFn, filterChunkFn) { - const queue = new Set(chunk.groupsIterable); - const chunksProcessed = new Set(); + apply(compiler) { + const options = this.options; + const banner = this.banner; + const matchObject = ModuleFilenameHelpers.matchObject.bind( + undefined, + options + ); - for (const chunkGroup of queue) { - for (const innerChunk of chunkGroup.chunks) { - if (!chunksProcessed.has(innerChunk)) { - chunksProcessed.add(innerChunk); - if (!filterChunkFn || filterChunkFn(innerChunk, this)) { - for (const module of this.getChunkModulesIterable(innerChunk)) { - if (filterFn(module)) { - return true; + compiler.hooks.compilation.tap("BannerPlugin", compilation => { + compilation.hooks.processAssets.tap( + { + name: "BannerPlugin", + stage: Compilation.PROCESS_ASSETS_STAGE_ADDITIONS + }, + () => { + for (const chunk of compilation.chunks) { + if (options.entryOnly && !chunk.canBeInitial()) { + continue; + } + + for (const file of chunk.files) { + if (!matchObject(file)) { + continue; } + + const data = { + chunk, + filename: file + }; + + const comment = compilation.getPath(banner, data); + + compilation.updateAsset( + file, + old => new ConcatSource(comment, "\n", old) + ); } } } - } - for (const child of chunkGroup.childrenIterable) { - queue.add(child); - } + ); + }); + } +} + +module.exports = BannerPlugin; + + +/***/ }), + +/***/ 99453: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ + + + +const { AsyncParallelHook, AsyncSeriesBailHook, SyncHook } = __webpack_require__(34718); +const { + makeWebpackError, + makeWebpackErrorCallback +} = __webpack_require__(89935); + +/** @typedef {import("./WebpackError")} WebpackError */ + +/** + * @typedef {Object} Etag + * @property {function(): string} toString + */ + +/** + * @template T + * @callback CallbackCache + * @param {WebpackError=} err + * @param {T=} result + * @returns {void} + */ + +/** + * @callback GotHandler + * @param {any} result + * @param {function(Error=): void} callback + * @returns {void} + */ + +const needCalls = (times, callback) => { + return err => { + if (--times === 0) { + return callback(err); } - return false; + if (err && times > 0) { + times = 0; + return callback(err); + } + }; +}; + +class Cache { + constructor() { + this.hooks = { + /** @type {AsyncSeriesBailHook<[string, Etag | null, GotHandler[]], any>} */ + get: new AsyncSeriesBailHook(["identifier", "etag", "gotHandlers"]), + /** @type {AsyncParallelHook<[string, Etag | null, any]>} */ + store: new AsyncParallelHook(["identifier", "etag", "data"]), + /** @type {AsyncParallelHook<[Iterable]>} */ + storeBuildDependencies: new AsyncParallelHook(["dependencies"]), + /** @type {SyncHook<[]>} */ + beginIdle: new SyncHook([]), + /** @type {AsyncParallelHook<[]>} */ + endIdle: new AsyncParallelHook([]), + /** @type {AsyncParallelHook<[]>} */ + shutdown: new AsyncParallelHook([]) + }; } /** - * @param {Chunk} chunkA first chunk - * @param {Chunk} chunkB second chunk - * @returns {-1|0|1} this is a comparator function like sort and returns -1, 0, or 1 based on sort order + * @template T + * @param {string} identifier the cache identifier + * @param {Etag | null} etag the etag + * @param {CallbackCache} callback signals when the value is retrieved + * @returns {void} */ - compareChunks(chunkA, chunkB) { - const cgcA = this._getChunkGraphChunk(chunkA); - const cgcB = this._getChunkGraphChunk(chunkB); - if (cgcA.modules.size > cgcB.modules.size) return -1; - if (cgcA.modules.size < cgcB.modules.size) return 1; - cgcA.modules.sortWith(compareModulesByIdentifier); - cgcB.modules.sortWith(compareModulesByIdentifier); - return compareModuleIterables(cgcA.modules, cgcB.modules); + get(identifier, etag, callback) { + const gotHandlers = []; + this.hooks.get.callAsync(identifier, etag, gotHandlers, (err, result) => { + if (err) { + callback(makeWebpackError(err, "Cache.hooks.get")); + return; + } + if (result === null) { + result = undefined; + } + if (gotHandlers.length > 1) { + const innerCallback = needCalls(gotHandlers.length, () => + callback(null, result) + ); + for (const gotHandler of gotHandlers) { + gotHandler(result, innerCallback); + } + } else if (gotHandlers.length === 1) { + gotHandlers[0](result, () => callback(null, result)); + } else { + callback(null, result); + } + }); } /** - * @param {Chunk} chunk the chunk - * @returns {number} total size of all modules in the chunk + * @template T + * @param {string} identifier the cache identifier + * @param {Etag | null} etag the etag + * @param {T} data the value to store + * @param {CallbackCache} callback signals when the value is stored + * @returns {void} */ - getChunkModulesSize(chunk) { - const cgc = this._getChunkGraphChunk(chunk); - return cgc.modules.getFromUnorderedCache(getModulesSize); + store(identifier, etag, data, callback) { + this.hooks.store.callAsync( + identifier, + etag, + data, + makeWebpackErrorCallback(callback, "Cache.hooks.store") + ); } /** - * @param {Chunk} chunk the chunk - * @returns {Record} total sizes of all modules in the chunk by source type + * After this method has succeeded the cache can only be restored when build dependencies are + * @param {Iterable} dependencies list of all build dependencies + * @param {CallbackCache} callback signals when the dependencies are stored + * @returns {void} */ - getChunkModulesSizes(chunk) { - const cgc = this._getChunkGraphChunk(chunk); - return cgc.modules.getFromUnorderedCache(getModulesSizes); + storeBuildDependencies(dependencies, callback) { + this.hooks.storeBuildDependencies.callAsync( + dependencies, + makeWebpackErrorCallback(callback, "Cache.hooks.storeBuildDependencies") + ); } /** - * @param {Chunk} chunk the chunk - * @returns {Module[]} root modules of the chunks (ordered by identifier) + * @returns {void} */ - getChunkRootModules(chunk) { - const cgc = this._getChunkGraphChunk(chunk); - return cgc.modules.getFromUnorderedCache(this._getGraphRoots); + beginIdle() { + this.hooks.beginIdle.call(); } /** - * @param {Chunk} chunk the chunk - * @param {ChunkSizeOptions} options options object - * @returns {number} total size of the chunk + * @param {CallbackCache} callback signals when the call finishes + * @returns {void} */ - getChunkSize(chunk, options = {}) { - const cgc = this._getChunkGraphChunk(chunk); - const modulesSize = cgc.modules.getFromUnorderedCache(getModulesSize); - const chunkOverhead = - typeof options.chunkOverhead === "number" ? options.chunkOverhead : 10000; - const entryChunkMultiplicator = - typeof options.entryChunkMultiplicator === "number" - ? options.entryChunkMultiplicator - : 10; - return ( - chunkOverhead + - modulesSize * (chunk.canBeInitial() ? entryChunkMultiplicator : 1) + endIdle(callback) { + this.hooks.endIdle.callAsync( + makeWebpackErrorCallback(callback, "Cache.hooks.endIdle") ); } /** - * @param {Chunk} chunkA chunk - * @param {Chunk} chunkB chunk - * @param {ChunkSizeOptions} options options object - * @returns {number} total size of the chunk or false if chunks can't be integrated + * @param {CallbackCache} callback signals when the call finishes + * @returns {void} */ - getIntegratedChunksSize(chunkA, chunkB, options = {}) { - const cgcA = this._getChunkGraphChunk(chunkA); - const cgcB = this._getChunkGraphChunk(chunkB); - const allModules = new Set(cgcA.modules); - for (const m of cgcB.modules) allModules.add(m); - let modulesSize = getModulesSize(allModules); - const chunkOverhead = - typeof options.chunkOverhead === "number" ? options.chunkOverhead : 10000; - const entryChunkMultiplicator = - typeof options.entryChunkMultiplicator === "number" - ? options.entryChunkMultiplicator - : 10; - return ( - chunkOverhead + - modulesSize * - (chunkA.canBeInitial() || chunkB.canBeInitial() - ? entryChunkMultiplicator - : 1) + shutdown(callback) { + this.hooks.shutdown.callAsync( + makeWebpackErrorCallback(callback, "Cache.hooks.shutdown") ); } +} - /** - * @param {Chunk} chunkA chunk - * @param {Chunk} chunkB chunk - * @returns {boolean} true, if chunks could be integrated - */ - canChunksBeIntegrated(chunkA, chunkB) { - if (chunkA.preventIntegration || chunkB.preventIntegration) { - return false; - } +Cache.STAGE_MEMORY = -10; +Cache.STAGE_DEFAULT = 0; +Cache.STAGE_DISK = 10; +Cache.STAGE_NETWORK = 20; - const hasRuntimeA = chunkA.hasRuntime(); - const hasRuntimeB = chunkB.hasRuntime(); +module.exports = Cache; - if (hasRuntimeA !== hasRuntimeB) { - if (hasRuntimeA) { - return isAvailableChunk(chunkA, chunkB); - } else if (hasRuntimeB) { - return isAvailableChunk(chunkB, chunkA); - } else { - return false; - } - } - if ( - this.getNumberOfEntryModules(chunkA) > 0 || - this.getNumberOfEntryModules(chunkB) > 0 - ) { - return false; - } +/***/ }), - return true; - } +/***/ 67014: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - /** - * @param {Chunk} chunkA the target chunk - * @param {Chunk} chunkB the chunk to integrate - * @returns {void} - */ - integrateChunks(chunkA, chunkB) { - // Decide for one name (deterministic) - if (chunkA.name && chunkB.name) { - if ( - this.getNumberOfEntryModules(chunkA) > 0 === - this.getNumberOfEntryModules(chunkB) > 0 - ) { - // When both chunks have entry modules or none have one, use - // shortest name - if (chunkA.name.length !== chunkB.name.length) { - chunkA.name = - chunkA.name.length < chunkB.name.length ? chunkA.name : chunkB.name; - } else { - chunkA.name = chunkA.name < chunkB.name ? chunkA.name : chunkB.name; - } - } else if (this.getNumberOfEntryModules(chunkB) > 0) { - // Pick the name of the chunk with the entry module - chunkA.name = chunkB.name; - } - } else if (chunkB.name) { - chunkA.name = chunkB.name; - } +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ - // Merge id name hints - for (const hint of chunkB.idNameHints) { - chunkA.idNameHints.add(hint); - } - // Merge runtime - chunkA.runtime = mergeRuntime(chunkA.runtime, chunkB.runtime); - // getChunkModules is used here to create a clone, because disconnectChunkAndModule modifies - for (const module of this.getChunkModules(chunkB)) { - this.disconnectChunkAndModule(chunkB, module); - this.connectChunkAndModule(chunkA, module); - } +const asyncLib = __webpack_require__(36386); +const getLazyHashedEtag = __webpack_require__(12339); +const mergeEtags = __webpack_require__(53885); - for (const [module, chunkGroup] of Array.from( - this.getChunkEntryModulesWithChunkGroupIterable(chunkB) - )) { - this.disconnectChunkAndEntryModule(chunkB, module); - this.connectChunkAndEntryModule(chunkA, module, chunkGroup); - } +/** @typedef {import("./Cache")} Cache */ +/** @typedef {import("./Cache").Etag} Etag */ +/** @typedef {import("./WebpackError")} WebpackError */ +/** @typedef {import("./cache/getLazyHashedEtag").HashableObject} HashableObject */ +/** @typedef {typeof import("./util/Hash")} HashConstructor */ - for (const chunkGroup of chunkB.groupsIterable) { - chunkGroup.replaceChunk(chunkB, chunkA); - chunkA.addGroup(chunkGroup); - chunkB.removeGroup(chunkGroup); - } - ChunkGraph.clearChunkGraphForChunk(chunkB); - } +/** + * @template T + * @callback CallbackCache + * @param {WebpackError=} err + * @param {T=} result + * @returns {void} + */ - /** - * @param {Chunk} chunk the chunk to upgrade - * @returns {void} - */ - upgradeDependentToFullHashModules(chunk) { - const cgc = this._getChunkGraphChunk(chunk); - if (cgc.dependentHashModules === undefined) return; - if (cgc.fullHashModules === undefined) { - cgc.fullHashModules = cgc.dependentHashModules; - } else { - for (const m of cgc.dependentHashModules) { - cgc.fullHashModules.add(m); - } - cgc.dependentHashModules = undefined; - } - } +/** + * @template T + * @callback CallbackNormalErrorCache + * @param {Error=} err + * @param {T=} result + * @returns {void} + */ +class MultiItemCache { /** - * @param {Module} module the checked module - * @param {Chunk} chunk the checked chunk - * @returns {boolean} true, if the chunk contains the module as entry + * @param {ItemCacheFacade[]} items item caches */ - isEntryModuleInChunk(module, chunk) { - const cgc = this._getChunkGraphChunk(chunk); - return cgc.entryModules.has(module); + constructor(items) { + this._items = items; + if (items.length === 1) return /** @type {any} */ (items[0]); } /** - * @param {Chunk} chunk the new chunk - * @param {Module} module the entry module - * @param {Entrypoint=} entrypoint the chunk group which must be loaded before the module is executed + * @template T + * @param {CallbackCache} callback signals when the value is retrieved * @returns {void} */ - connectChunkAndEntryModule(chunk, module, entrypoint) { - const cgm = this._getChunkGraphModule(module); - const cgc = this._getChunkGraphChunk(chunk); - if (cgm.entryInChunks === undefined) { - cgm.entryInChunks = new Set(); - } - cgm.entryInChunks.add(chunk); - cgc.entryModules.set(module, entrypoint); + get(callback) { + const next = i => { + this._items[i].get((err, result) => { + if (err) return callback(err); + if (result !== undefined) return callback(null, result); + if (++i >= this._items.length) return callback(); + next(i); + }); + }; + next(0); } /** - * @param {Chunk} chunk the new chunk - * @param {RuntimeModule} module the runtime module - * @returns {void} + * @template T + * @returns {Promise} promise with the data */ - connectChunkAndRuntimeModule(chunk, module) { - const cgm = this._getChunkGraphModule(module); - const cgc = this._getChunkGraphChunk(chunk); - if (cgm.runtimeInChunks === undefined) { - cgm.runtimeInChunks = new Set(); - } - cgm.runtimeInChunks.add(chunk); - cgc.runtimeModules.add(module); + getPromise() { + const next = i => { + return this._items[i].getPromise().then(result => { + if (result !== undefined) return result; + if (++i < this._items.length) return next(i); + }); + }; + return next(0); } /** - * @param {Chunk} chunk the new chunk - * @param {RuntimeModule} module the module that require a full hash + * @template T + * @param {T} data the value to store + * @param {CallbackCache} callback signals when the value is stored * @returns {void} */ - addFullHashModuleToChunk(chunk, module) { - const cgc = this._getChunkGraphChunk(chunk); - if (cgc.fullHashModules === undefined) cgc.fullHashModules = new Set(); - cgc.fullHashModules.add(module); + store(data, callback) { + asyncLib.each( + this._items, + (item, callback) => item.store(data, callback), + callback + ); } /** - * @param {Chunk} chunk the new chunk - * @param {RuntimeModule} module the module that require a full hash - * @returns {void} + * @template T + * @param {T} data the value to store + * @returns {Promise} promise signals when the value is stored */ - addDependentHashModuleToChunk(chunk, module) { - const cgc = this._getChunkGraphChunk(chunk); - if (cgc.dependentHashModules === undefined) - cgc.dependentHashModules = new Set(); - cgc.dependentHashModules.add(module); + storePromise(data) { + return Promise.all(this._items.map(item => item.storePromise(data))).then( + () => {} + ); } +} +class ItemCacheFacade { /** - * @param {Chunk} chunk the new chunk - * @param {Module} module the entry module - * @returns {void} + * @param {Cache} cache the root cache + * @param {string} name the child cache item name + * @param {Etag | null} etag the etag */ - disconnectChunkAndEntryModule(chunk, module) { - const cgm = this._getChunkGraphModule(module); - const cgc = this._getChunkGraphChunk(chunk); - cgm.entryInChunks.delete(chunk); - if (cgm.entryInChunks.size === 0) { - cgm.entryInChunks = undefined; - } - cgc.entryModules.delete(module); + constructor(cache, name, etag) { + this._cache = cache; + this._name = name; + this._etag = etag; } /** - * @param {Chunk} chunk the new chunk - * @param {RuntimeModule} module the runtime module + * @template T + * @param {CallbackCache} callback signals when the value is retrieved * @returns {void} */ - disconnectChunkAndRuntimeModule(chunk, module) { - const cgm = this._getChunkGraphModule(module); - const cgc = this._getChunkGraphChunk(chunk); - cgm.runtimeInChunks.delete(chunk); - if (cgm.runtimeInChunks.size === 0) { - cgm.runtimeInChunks = undefined; - } - cgc.runtimeModules.delete(module); + get(callback) { + this._cache.get(this._name, this._etag, callback); } /** - * @param {Module} module the entry module, it will no longer be entry - * @returns {void} + * @template T + * @returns {Promise} promise with the data */ - disconnectEntryModule(module) { - const cgm = this._getChunkGraphModule(module); - for (const chunk of cgm.entryInChunks) { - const cgc = this._getChunkGraphChunk(chunk); - cgc.entryModules.delete(module); - } - cgm.entryInChunks = undefined; + getPromise() { + return new Promise((resolve, reject) => { + this._cache.get(this._name, this._etag, (err, data) => { + if (err) { + reject(err); + } else { + resolve(data); + } + }); + }); } /** - * @param {Chunk} chunk the chunk, for which all entries will be removed + * @template T + * @param {T} data the value to store + * @param {CallbackCache} callback signals when the value is stored * @returns {void} */ - disconnectEntries(chunk) { - const cgc = this._getChunkGraphChunk(chunk); - for (const module of cgc.entryModules.keys()) { - const cgm = this._getChunkGraphModule(module); - cgm.entryInChunks.delete(chunk); - if (cgm.entryInChunks.size === 0) { - cgm.entryInChunks = undefined; - } - } - cgc.entryModules.clear(); - } - - /** - * @param {Chunk} chunk the chunk - * @returns {number} the amount of entry modules in chunk - */ - getNumberOfEntryModules(chunk) { - const cgc = this._getChunkGraphChunk(chunk); - return cgc.entryModules.size; - } - - /** - * @param {Chunk} chunk the chunk - * @returns {number} the amount of entry modules in chunk - */ - getNumberOfRuntimeModules(chunk) { - const cgc = this._getChunkGraphChunk(chunk); - return cgc.runtimeModules.size; - } - - /** - * @param {Chunk} chunk the chunk - * @returns {Iterable} iterable of modules (do not modify) - */ - getChunkEntryModulesIterable(chunk) { - const cgc = this._getChunkGraphChunk(chunk); - return cgc.entryModules.keys(); + store(data, callback) { + this._cache.store(this._name, this._etag, data, callback); } /** - * @param {Chunk} chunk the chunk - * @returns {Iterable} iterable of chunks + * @template T + * @param {T} data the value to store + * @returns {Promise} promise signals when the value is stored */ - getChunkEntryDependentChunksIterable(chunk) { - /** @type {Set} */ - const set = new Set(); - for (const chunkGroup of chunk.groupsIterable) { - if (chunkGroup instanceof Entrypoint) { - const entrypointChunk = chunkGroup.getEntrypointChunk(); - const cgc = this._getChunkGraphChunk(entrypointChunk); - for (const chunkGroup of cgc.entryModules.values()) { - for (const c of chunkGroup.chunks) { - if (c !== chunk && c !== entrypointChunk && !c.hasRuntime()) { - set.add(c); - } - } + storePromise(data) { + return new Promise((resolve, reject) => { + this._cache.store(this._name, this._etag, data, err => { + if (err) { + reject(err); + } else { + resolve(); } - } - } - - return set; + }); + }); } /** - * @param {Chunk} chunk the chunk - * @returns {boolean} true, when it has dependent chunks + * @template T + * @param {function(CallbackNormalErrorCache): void} computer function to compute the value if not cached + * @param {CallbackNormalErrorCache} callback signals when the value is retrieved + * @returns {void} */ - hasChunkEntryDependentChunks(chunk) { - const cgc = this._getChunkGraphChunk(chunk); - for (const chunkGroup of cgc.entryModules.values()) { - for (const c of chunkGroup.chunks) { - if (c !== chunk) { - return true; - } - } - } - return false; + provide(computer, callback) { + this.get((err, cacheEntry) => { + if (err) return callback(err); + if (cacheEntry !== undefined) return cacheEntry; + computer((err, result) => { + if (err) return callback(err); + this.store(result, err => { + if (err) return callback(err); + callback(null, result); + }); + }); + }); } /** - * @param {Chunk} chunk the chunk - * @returns {Iterable} iterable of modules (do not modify) + * @template T + * @param {function(): Promise | T} computer function to compute the value if not cached + * @returns {Promise} promise with the data */ - getChunkRuntimeModulesIterable(chunk) { - const cgc = this._getChunkGraphChunk(chunk); - return cgc.runtimeModules; + async providePromise(computer) { + const cacheEntry = await this.getPromise(); + if (cacheEntry !== undefined) return cacheEntry; + const result = await computer(); + await this.storePromise(result); + return result; } +} +class CacheFacade { /** - * @param {Chunk} chunk the chunk - * @returns {RuntimeModule[]} array of modules in order of execution + * @param {Cache} cache the root cache + * @param {string} name the child cache name + * @param {string | HashConstructor} hashFunction the hash function to use */ - getChunkRuntimeModulesInOrder(chunk) { - const cgc = this._getChunkGraphChunk(chunk); - const array = Array.from(cgc.runtimeModules); - array.sort( - concatComparators( - compareSelect( - /** - * @param {RuntimeModule} r runtime module - * @returns {number=} stage - */ - r => r.stage, - compareIds - ), - compareModulesByIdentifier - ) - ); - return array; + constructor(cache, name, hashFunction) { + this._cache = cache; + this._name = name; + this._hashFunction = hashFunction; } /** - * @param {Chunk} chunk the chunk - * @returns {Iterable | undefined} iterable of modules (do not modify) + * @param {string} name the child cache name# + * @returns {CacheFacade} child cache */ - getChunkFullHashModulesIterable(chunk) { - const cgc = this._getChunkGraphChunk(chunk); - return cgc.fullHashModules; + getChildCache(name) { + return new CacheFacade( + this._cache, + `${this._name}|${name}`, + this._hashFunction + ); } /** - * @param {Chunk} chunk the chunk - * @returns {ReadonlySet | undefined} set of modules (do not modify) + * @param {string} identifier the cache identifier + * @param {Etag | null} etag the etag + * @returns {ItemCacheFacade} item cache */ - getChunkFullHashModulesSet(chunk) { - const cgc = this._getChunkGraphChunk(chunk); - return cgc.fullHashModules; + getItemCache(identifier, etag) { + return new ItemCacheFacade( + this._cache, + `${this._name}|${identifier}`, + etag + ); } /** - * @param {Chunk} chunk the chunk - * @returns {Iterable | undefined} iterable of modules (do not modify) + * @param {HashableObject} obj an hashable object + * @returns {Etag} an etag that is lazy hashed */ - getChunkDependentHashModulesIterable(chunk) { - const cgc = this._getChunkGraphChunk(chunk); - return cgc.dependentHashModules; + getLazyHashedEtag(obj) { + return getLazyHashedEtag(obj, this._hashFunction); } - /** @typedef {[Module, Entrypoint | undefined]} EntryModuleWithChunkGroup */ - /** - * @param {Chunk} chunk the chunk - * @returns {Iterable} iterable of modules (do not modify) + * @param {Etag} a an etag + * @param {Etag} b another etag + * @returns {Etag} an etag that represents both */ - getChunkEntryModulesWithChunkGroupIterable(chunk) { - const cgc = this._getChunkGraphChunk(chunk); - return cgc.entryModules; + mergeEtags(a, b) { + return mergeEtags(a, b); } /** - * @param {AsyncDependenciesBlock} depBlock the async block - * @returns {ChunkGroup} the chunk group + * @template T + * @param {string} identifier the cache identifier + * @param {Etag | null} etag the etag + * @param {CallbackCache} callback signals when the value is retrieved + * @returns {void} */ - getBlockChunkGroup(depBlock) { - return this._blockChunkGroups.get(depBlock); + get(identifier, etag, callback) { + this._cache.get(`${this._name}|${identifier}`, etag, callback); } /** - * @param {AsyncDependenciesBlock} depBlock the async block - * @param {ChunkGroup} chunkGroup the chunk group - * @returns {void} + * @template T + * @param {string} identifier the cache identifier + * @param {Etag | null} etag the etag + * @returns {Promise} promise with the data */ - connectBlockAndChunkGroup(depBlock, chunkGroup) { - this._blockChunkGroups.set(depBlock, chunkGroup); - chunkGroup.addBlock(depBlock); + getPromise(identifier, etag) { + return new Promise((resolve, reject) => { + this._cache.get(`${this._name}|${identifier}`, etag, (err, data) => { + if (err) { + reject(err); + } else { + resolve(data); + } + }); + }); } /** - * @param {ChunkGroup} chunkGroup the chunk group + * @template T + * @param {string} identifier the cache identifier + * @param {Etag | null} etag the etag + * @param {T} data the value to store + * @param {CallbackCache} callback signals when the value is stored * @returns {void} */ - disconnectChunkGroup(chunkGroup) { - for (const block of chunkGroup.blocksIterable) { - this._blockChunkGroups.delete(block); - } - // TODO refactor by moving blocks list into ChunkGraph - chunkGroup._blocks.clear(); + store(identifier, etag, data, callback) { + this._cache.store(`${this._name}|${identifier}`, etag, data, callback); } /** - * @param {Module} module the module - * @returns {string | number} the id of the module + * @template T + * @param {string} identifier the cache identifier + * @param {Etag | null} etag the etag + * @param {T} data the value to store + * @returns {Promise} promise signals when the value is stored */ - getModuleId(module) { - const cgm = this._getChunkGraphModule(module); - return cgm.id; + storePromise(identifier, etag, data) { + return new Promise((resolve, reject) => { + this._cache.store(`${this._name}|${identifier}`, etag, data, err => { + if (err) { + reject(err); + } else { + resolve(); + } + }); + }); } /** - * @param {Module} module the module - * @param {string | number} id the id of the module + * @template T + * @param {string} identifier the cache identifier + * @param {Etag | null} etag the etag + * @param {function(CallbackNormalErrorCache): void} computer function to compute the value if not cached + * @param {CallbackNormalErrorCache} callback signals when the value is retrieved * @returns {void} */ - setModuleId(module, id) { - const cgm = this._getChunkGraphModule(module); - cgm.id = id; + provide(identifier, etag, computer, callback) { + this.get(identifier, etag, (err, cacheEntry) => { + if (err) return callback(err); + if (cacheEntry !== undefined) return cacheEntry; + computer((err, result) => { + if (err) return callback(err); + this.store(identifier, etag, result, err => { + if (err) return callback(err); + callback(null, result); + }); + }); + }); } /** - * @param {string} runtime runtime - * @returns {string | number} the id of the runtime + * @template T + * @param {string} identifier the cache identifier + * @param {Etag | null} etag the etag + * @param {function(): Promise | T} computer function to compute the value if not cached + * @returns {Promise} promise with the data */ - getRuntimeId(runtime) { - return this._runtimeIds.get(runtime); + async providePromise(identifier, etag, computer) { + const cacheEntry = await this.getPromise(identifier, etag); + if (cacheEntry !== undefined) return cacheEntry; + const result = await computer(); + await this.storePromise(identifier, etag, result); + return result; } +} +module.exports = CacheFacade; +module.exports.ItemCacheFacade = ItemCacheFacade; +module.exports.MultiItemCache = MultiItemCache; + + +/***/ }), + +/***/ 42444: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ + + + +const WebpackError = __webpack_require__(68422); + +/** @typedef {import("./Module")} Module */ +/** @typedef {import("./ModuleGraph")} ModuleGraph */ + +/** + * @param {Module[]} modules the modules to be sorted + * @returns {Module[]} sorted version of original modules + */ +const sortModules = modules => { + return modules.sort((a, b) => { + const aIdent = a.identifier(); + const bIdent = b.identifier(); + /* istanbul ignore next */ + if (aIdent < bIdent) return -1; + /* istanbul ignore next */ + if (aIdent > bIdent) return 1; + /* istanbul ignore next */ + return 0; + }); +}; + +/** + * @param {Module[]} modules each module from throw + * @param {ModuleGraph} moduleGraph the module graph + * @returns {string} each message from provided modules + */ +const createModulesListMessage = (modules, moduleGraph) => { + return modules + .map(m => { + let message = `* ${m.identifier()}`; + const validReasons = Array.from( + moduleGraph.getIncomingConnectionsByOriginModule(m).keys() + ).filter(x => x); + + if (validReasons.length > 0) { + message += `\n Used by ${validReasons.length} module(s), i. e.`; + message += `\n ${validReasons[0].identifier()}`; + } + return message; + }) + .join("\n"); +}; + +class CaseSensitiveModulesWarning extends WebpackError { /** - * @param {string} runtime runtime - * @param {string | number} id the id of the runtime - * @returns {void} + * Creates an instance of CaseSensitiveModulesWarning. + * @param {Iterable} modules modules that were detected + * @param {ModuleGraph} moduleGraph the module graph */ - setRuntimeId(runtime, id) { - this._runtimeIds.set(runtime, id); + constructor(modules, moduleGraph) { + const sortedModules = sortModules(Array.from(modules)); + const modulesList = createModulesListMessage(sortedModules, moduleGraph); + super(`There are multiple modules with names that only differ in casing. +This can lead to unexpected behavior when compiling on a filesystem with other case-semantic. +Use equal casing. Compare these module identifiers: +${modulesList}`); + + this.name = "CaseSensitiveModulesWarning"; + this.module = sortedModules[0]; } +} + +module.exports = CaseSensitiveModulesWarning; + + +/***/ }), + +/***/ 65574: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ + + + +const ChunkGraph = __webpack_require__(97860); +const Entrypoint = __webpack_require__(86695); +const { intersect } = __webpack_require__(34715); +const SortableSet = __webpack_require__(67563); +const StringXor = __webpack_require__(23877); +const { + compareModulesByIdentifier, + compareChunkGroupsByIndex, + compareModulesById +} = __webpack_require__(26296); +const { createArrayToSetDeprecationSet } = __webpack_require__(2594); +const { mergeRuntime } = __webpack_require__(19655); + +/** @typedef {import("webpack-sources").Source} Source */ +/** @typedef {import("./ChunkGraph").ChunkFilterPredicate} ChunkFilterPredicate */ +/** @typedef {import("./ChunkGraph").ChunkSizeOptions} ChunkSizeOptions */ +/** @typedef {import("./ChunkGraph").ModuleFilterPredicate} ModuleFilterPredicate */ +/** @typedef {import("./ChunkGroup")} ChunkGroup */ +/** @typedef {import("./Compilation")} Compilation */ +/** @typedef {import("./Compilation").AssetInfo} AssetInfo */ +/** @typedef {import("./Compilation").PathData} PathData */ +/** @typedef {import("./Entrypoint").EntryOptions} EntryOptions */ +/** @typedef {import("./Module")} Module */ +/** @typedef {import("./ModuleGraph")} ModuleGraph */ +/** @typedef {import("./util/Hash")} Hash */ +/** @typedef {import("./util/runtime").RuntimeSpec} RuntimeSpec */ + +const ChunkFilesSet = createArrayToSetDeprecationSet("chunk.files"); + +/** + * @typedef {Object} WithId an object who has an id property * + * @property {string | number} id the id of the object + */ + +/** + * @deprecated + * @typedef {Object} ChunkMaps + * @property {Record} hash + * @property {Record>} contentHash + * @property {Record} name + */ + +/** + * @deprecated + * @typedef {Object} ChunkModuleMaps + * @property {Record} id + * @property {Record} hash + */ + +let debugId = 1000; +/** + * A Chunk is a unit of encapsulation for Modules. + * Chunks are "rendered" into bundles that get emitted when the build completes. + */ +class Chunk { /** - * @template T - * @param {Module} module the module - * @param {RuntimeSpecMap} hashes hashes data - * @param {RuntimeSpec} runtime the runtime - * @returns {T} hash + * @param {string=} name of chunk being created, is optional (for subclasses) + * @param {boolean} backCompat enable backward-compatibility */ - _getModuleHashInfo(module, hashes, runtime) { - if (!hashes) { + constructor(name, backCompat = true) { + /** @type {number | string | null} */ + this.id = null; + /** @type {(number|string)[] | null} */ + this.ids = null; + /** @type {number} */ + this.debugId = debugId++; + /** @type {string} */ + this.name = name; + /** @type {SortableSet} */ + this.idNameHints = new SortableSet(); + /** @type {boolean} */ + this.preventIntegration = false; + /** @type {(string | function(PathData, AssetInfo=): string)?} */ + this.filenameTemplate = undefined; + /** @private @type {SortableSet} */ + this._groups = new SortableSet(undefined, compareChunkGroupsByIndex); + /** @type {RuntimeSpec} */ + this.runtime = undefined; + /** @type {Set} */ + this.files = backCompat ? new ChunkFilesSet() : new Set(); + /** @type {Set} */ + this.auxiliaryFiles = new Set(); + /** @type {boolean} */ + this.rendered = false; + /** @type {string=} */ + this.hash = undefined; + /** @type {Record} */ + this.contentHash = Object.create(null); + /** @type {string=} */ + this.renderedHash = undefined; + /** @type {string=} */ + this.chunkReason = undefined; + /** @type {boolean} */ + this.extraAsync = false; + } + + // TODO remove in webpack 6 + // BACKWARD-COMPAT START + get entryModule() { + const entryModules = Array.from( + ChunkGraph.getChunkGraphForChunk( + this, + "Chunk.entryModule", + "DEP_WEBPACK_CHUNK_ENTRY_MODULE" + ).getChunkEntryModulesIterable(this) + ); + if (entryModules.length === 0) { + return undefined; + } else if (entryModules.length === 1) { + return entryModules[0]; + } else { throw new Error( - `Module ${module.identifier()} has no hash info for runtime ${runtimeToString( - runtime - )} (hashes not set at all)` + "Module.entryModule: Multiple entry modules are not supported by the deprecated API (Use the new ChunkGroup API)" ); - } else if (runtime === undefined) { - const hashInfoItems = new Set(hashes.values()); - if (hashInfoItems.size !== 1) { - throw new Error( - `No unique hash info entry for unspecified runtime for ${module.identifier()} (existing runtimes: ${Array.from( - hashes.keys(), - r => runtimeToString(r) - ).join(", ")}). -Caller might not support runtime-dependent code generation (opt-out via optimization.usedExports: "global").` - ); - } - return first(hashInfoItems); - } else { - const hashInfo = hashes.get(runtime); - if (!hashInfo) { - throw new Error( - `Module ${module.identifier()} has no hash info for runtime ${runtimeToString( - runtime - )} (available runtimes ${Array.from( - hashes.keys(), - runtimeToString - ).join(", ")})` - ); - } - return hashInfo; } } /** - * @param {Module} module the module - * @param {RuntimeSpec} runtime the runtime - * @returns {boolean} true, if the module has hashes for this runtime + * @returns {boolean} true, if the chunk contains an entry module */ - hasModuleHashes(module, runtime) { - const cgm = this._getChunkGraphModule(module); - const hashes = cgm.hashes; - return hashes && hashes.has(runtime); + hasEntryModule() { + return ( + ChunkGraph.getChunkGraphForChunk( + this, + "Chunk.hasEntryModule", + "DEP_WEBPACK_CHUNK_HAS_ENTRY_MODULE" + ).getNumberOfEntryModules(this) > 0 + ); } /** * @param {Module} module the module - * @param {RuntimeSpec} runtime the runtime - * @returns {string} hash + * @returns {boolean} true, if the chunk could be added */ - getModuleHash(module, runtime) { - const cgm = this._getChunkGraphModule(module); - const hashes = cgm.hashes; - return this._getModuleHashInfo(module, hashes, runtime).hash; + addModule(module) { + const chunkGraph = ChunkGraph.getChunkGraphForChunk( + this, + "Chunk.addModule", + "DEP_WEBPACK_CHUNK_ADD_MODULE" + ); + if (chunkGraph.isModuleInChunk(module, this)) return false; + chunkGraph.connectChunkAndModule(this, module); + return true; } /** * @param {Module} module the module - * @param {RuntimeSpec} runtime the runtime - * @returns {string} hash + * @returns {void} */ - getRenderedModuleHash(module, runtime) { - const cgm = this._getChunkGraphModule(module); - const hashes = cgm.hashes; - return this._getModuleHashInfo(module, hashes, runtime).renderedHash; + removeModule(module) { + ChunkGraph.getChunkGraphForChunk( + this, + "Chunk.removeModule", + "DEP_WEBPACK_CHUNK_REMOVE_MODULE" + ).disconnectChunkAndModule(this, module); } /** - * @param {Module} module the module - * @param {RuntimeSpec} runtime the runtime - * @param {string} hash the full hash - * @param {string} renderedHash the shortened hash for rendering - * @returns {void} + * @returns {number} the number of module which are contained in this chunk */ - setModuleHashes(module, runtime, hash, renderedHash) { - const cgm = this._getChunkGraphModule(module); - if (cgm.hashes === undefined) { - cgm.hashes = new RuntimeSpecMap(); - } - cgm.hashes.set(runtime, new ModuleHashInfo(hash, renderedHash)); + getNumberOfModules() { + return ChunkGraph.getChunkGraphForChunk( + this, + "Chunk.getNumberOfModules", + "DEP_WEBPACK_CHUNK_GET_NUMBER_OF_MODULES" + ).getNumberOfChunkModules(this); + } + + get modulesIterable() { + const chunkGraph = ChunkGraph.getChunkGraphForChunk( + this, + "Chunk.modulesIterable", + "DEP_WEBPACK_CHUNK_MODULES_ITERABLE" + ); + return chunkGraph.getOrderedChunkModulesIterable( + this, + compareModulesByIdentifier + ); + } + + /** + * @param {Chunk} otherChunk the chunk to compare with + * @returns {-1|0|1} the comparison result + */ + compareTo(otherChunk) { + const chunkGraph = ChunkGraph.getChunkGraphForChunk( + this, + "Chunk.compareTo", + "DEP_WEBPACK_CHUNK_COMPARE_TO" + ); + return chunkGraph.compareChunks(this, otherChunk); } /** * @param {Module} module the module - * @param {RuntimeSpec} runtime the runtime - * @param {Set} items runtime requirements to be added (ownership of this Set is given to ChunkGraph when transferOwnership not false) - * @param {boolean} transferOwnership true: transfer ownership of the items object, false: items is immutable and shared and won't be modified - * @returns {void} + * @returns {boolean} true, if the chunk contains the module */ - addModuleRuntimeRequirements( - module, - runtime, - items, - transferOwnership = true - ) { - const cgm = this._getChunkGraphModule(module); - const runtimeRequirementsMap = cgm.runtimeRequirements; - if (runtimeRequirementsMap === undefined) { - const map = new RuntimeSpecMap(); - // TODO avoid cloning item and track ownership instead - map.set(runtime, transferOwnership ? items : new Set(items)); - cgm.runtimeRequirements = map; - return; - } - runtimeRequirementsMap.update(runtime, runtimeRequirements => { - if (runtimeRequirements === undefined) { - return transferOwnership ? items : new Set(items); - } else if (!transferOwnership || runtimeRequirements.size >= items.size) { - for (const item of items) runtimeRequirements.add(item); - return runtimeRequirements; - } else { - for (const item of runtimeRequirements) items.add(item); - return items; - } - }); + containsModule(module) { + return ChunkGraph.getChunkGraphForChunk( + this, + "Chunk.containsModule", + "DEP_WEBPACK_CHUNK_CONTAINS_MODULE" + ).isModuleInChunk(module, this); } /** - * @param {Chunk} chunk the chunk - * @param {Set} items runtime requirements to be added (ownership of this Set is given to ChunkGraph) - * @returns {void} + * @returns {Module[]} the modules for this chunk */ - addChunkRuntimeRequirements(chunk, items) { - const cgc = this._getChunkGraphChunk(chunk); - const runtimeRequirements = cgc.runtimeRequirements; - if (runtimeRequirements === undefined) { - cgc.runtimeRequirements = items; - } else if (runtimeRequirements.size >= items.size) { - for (const item of items) runtimeRequirements.add(item); - } else { - for (const item of runtimeRequirements) items.add(item); - cgc.runtimeRequirements = items; - } + getModules() { + return ChunkGraph.getChunkGraphForChunk( + this, + "Chunk.getModules", + "DEP_WEBPACK_CHUNK_GET_MODULES" + ).getChunkModules(this); } /** - * @param {Chunk} chunk the chunk - * @param {Iterable} items runtime requirements to be added * @returns {void} */ - addTreeRuntimeRequirements(chunk, items) { - const cgc = this._getChunkGraphChunk(chunk); - const runtimeRequirements = cgc.runtimeRequirementsInTree; - for (const item of items) runtimeRequirements.add(item); + remove() { + const chunkGraph = ChunkGraph.getChunkGraphForChunk( + this, + "Chunk.remove", + "DEP_WEBPACK_CHUNK_REMOVE" + ); + chunkGraph.disconnectChunk(this); + this.disconnectFromGroups(); } /** * @param {Module} module the module - * @param {RuntimeSpec} runtime the runtime - * @returns {ReadonlySet} runtime requirements + * @param {Chunk} otherChunk the target chunk + * @returns {void} */ - getModuleRuntimeRequirements(module, runtime) { - const cgm = this._getChunkGraphModule(module); - const runtimeRequirements = - cgm.runtimeRequirements && cgm.runtimeRequirements.get(runtime); - return runtimeRequirements === undefined ? EMPTY_SET : runtimeRequirements; + moveModule(module, otherChunk) { + const chunkGraph = ChunkGraph.getChunkGraphForChunk( + this, + "Chunk.moveModule", + "DEP_WEBPACK_CHUNK_MOVE_MODULE" + ); + chunkGraph.disconnectChunkAndModule(this, module); + chunkGraph.connectChunkAndModule(otherChunk, module); } /** - * @param {Chunk} chunk the chunk - * @returns {ReadonlySet} runtime requirements + * @param {Chunk} otherChunk the other chunk + * @returns {boolean} true, if the specified chunk has been integrated */ - getChunkRuntimeRequirements(chunk) { - const cgc = this._getChunkGraphChunk(chunk); - const runtimeRequirements = cgc.runtimeRequirements; - return runtimeRequirements === undefined ? EMPTY_SET : runtimeRequirements; + integrate(otherChunk) { + const chunkGraph = ChunkGraph.getChunkGraphForChunk( + this, + "Chunk.integrate", + "DEP_WEBPACK_CHUNK_INTEGRATE" + ); + if (chunkGraph.canChunksBeIntegrated(this, otherChunk)) { + chunkGraph.integrateChunks(this, otherChunk); + return true; + } else { + return false; + } } /** - * @param {Module} module the module - * @param {RuntimeSpec} runtime the runtime - * @param {boolean} withConnections include connections - * @returns {string} hash + * @param {Chunk} otherChunk the other chunk + * @returns {boolean} true, if chunks could be integrated */ - getModuleGraphHash(module, runtime, withConnections = true) { - const cgm = this._getChunkGraphModule(module); - return withConnections - ? this._getModuleGraphHashWithConnections(cgm, module, runtime) - : this._getModuleGraphHashBigInt(cgm, module, runtime).toString(16); + canBeIntegrated(otherChunk) { + const chunkGraph = ChunkGraph.getChunkGraphForChunk( + this, + "Chunk.canBeIntegrated", + "DEP_WEBPACK_CHUNK_CAN_BE_INTEGRATED" + ); + return chunkGraph.canChunksBeIntegrated(this, otherChunk); } /** - * @param {Module} module the module - * @param {RuntimeSpec} runtime the runtime - * @param {boolean} withConnections include connections - * @returns {bigint} hash + * @returns {boolean} true, if this chunk contains no module */ - getModuleGraphHashBigInt(module, runtime, withConnections = true) { - const cgm = this._getChunkGraphModule(module); - return withConnections - ? BigInt( - `0x${this._getModuleGraphHashWithConnections(cgm, module, runtime)}` - ) - : this._getModuleGraphHashBigInt(cgm, module, runtime); + isEmpty() { + const chunkGraph = ChunkGraph.getChunkGraphForChunk( + this, + "Chunk.isEmpty", + "DEP_WEBPACK_CHUNK_IS_EMPTY" + ); + return chunkGraph.getNumberOfChunkModules(this) === 0; } /** - * @param {ChunkGraphModule} cgm the ChunkGraphModule - * @param {Module} module the module - * @param {RuntimeSpec} runtime the runtime - * @returns {bigint} hash as big int + * @returns {number} total size of all modules in this chunk */ - _getModuleGraphHashBigInt(cgm, module, runtime) { - if (cgm.graphHashes === undefined) { - cgm.graphHashes = new RuntimeSpecMap(); - } - const graphHash = cgm.graphHashes.provide(runtime, () => { - const hash = createHash(this._hashFunction); - hash.update(`${cgm.id}${this.moduleGraph.isAsync(module)}`); - this.moduleGraph.getExportsInfo(module).updateHash(hash, runtime); - return BigInt(`0x${/** @type {string} */ (hash.digest("hex"))}`); - }); - return graphHash; + modulesSize() { + const chunkGraph = ChunkGraph.getChunkGraphForChunk( + this, + "Chunk.modulesSize", + "DEP_WEBPACK_CHUNK_MODULES_SIZE" + ); + return chunkGraph.getChunkModulesSize(this); } /** - * @param {ChunkGraphModule} cgm the ChunkGraphModule - * @param {Module} module the module - * @param {RuntimeSpec} runtime the runtime - * @returns {string} hash + * @param {ChunkSizeOptions} options options object + * @returns {number} total size of this chunk */ - _getModuleGraphHashWithConnections(cgm, module, runtime) { - if (cgm.graphHashesWithConnections === undefined) { - cgm.graphHashesWithConnections = new RuntimeSpecMap(); - } - const activeStateToString = state => { - if (state === false) return "F"; - if (state === true) return "T"; - if (state === ModuleGraphConnection.TRANSITIVE_ONLY) return "O"; - throw new Error("Not implemented active state"); - }; - const strict = module.buildMeta && module.buildMeta.strictHarmonyModule; - return cgm.graphHashesWithConnections.provide(runtime, () => { - const graphHash = this._getModuleGraphHashBigInt( - cgm, - module, - runtime - ).toString(16); - const connections = this.moduleGraph.getOutgoingConnections(module); - /** @type {Set} */ - const activeNamespaceModules = new Set(); - /** @type {Map>} */ - const connectedModules = new Map(); - const processConnection = (connection, stateInfo) => { - const module = connection.module; - stateInfo += module.getExportsType(this.moduleGraph, strict); - // cspell:word Tnamespace - if (stateInfo === "Tnamespace") activeNamespaceModules.add(module); - else { - const oldModule = connectedModules.get(stateInfo); - if (oldModule === undefined) { - connectedModules.set(stateInfo, module); - } else if (oldModule instanceof Set) { - oldModule.add(module); - } else if (oldModule !== module) { - connectedModules.set(stateInfo, new Set([oldModule, module])); - } - } - }; - if (runtime === undefined || typeof runtime === "string") { - for (const connection of connections) { - const state = connection.getActiveState(runtime); - if (state === false) continue; - processConnection(connection, state === true ? "T" : "O"); - } - } else { - // cspell:word Tnamespace - for (const connection of connections) { - const states = new Set(); - let stateInfo = ""; - forEachRuntime( - runtime, - runtime => { - const state = connection.getActiveState(runtime); - states.add(state); - stateInfo += activeStateToString(state) + runtime; - }, - true - ); - if (states.size === 1) { - const state = first(states); - if (state === false) continue; - stateInfo = activeStateToString(state); - } - processConnection(connection, stateInfo); - } - } - // cspell:word Tnamespace - if (activeNamespaceModules.size === 0 && connectedModules.size === 0) - return graphHash; - const connectedModulesInOrder = - connectedModules.size > 1 - ? Array.from(connectedModules).sort(([a], [b]) => (a < b ? -1 : 1)) - : connectedModules; - const hash = createHash(this._hashFunction); - const addModuleToHash = module => { - hash.update( - this._getModuleGraphHashBigInt( - this._getChunkGraphModule(module), - module, - runtime - ).toString(16) - ); - }; - const addModulesToHash = modules => { - let xor = ZERO_BIG_INT; - for (const m of modules) { - xor = - xor ^ - this._getModuleGraphHashBigInt( - this._getChunkGraphModule(m), - m, - runtime - ); - } - hash.update(xor.toString(16)); - }; - if (activeNamespaceModules.size === 1) - addModuleToHash(activeNamespaceModules.values().next().value); - else if (activeNamespaceModules.size > 1) - addModulesToHash(activeNamespaceModules); - for (const [stateInfo, modules] of connectedModulesInOrder) { - hash.update(stateInfo); - if (modules instanceof Set) { - addModulesToHash(modules); - } else { - addModuleToHash(modules); - } - } - hash.update(graphHash); - return /** @type {string} */ (hash.digest("hex")); - }); + size(options = {}) { + const chunkGraph = ChunkGraph.getChunkGraphForChunk( + this, + "Chunk.size", + "DEP_WEBPACK_CHUNK_SIZE" + ); + return chunkGraph.getChunkSize(this, options); } /** - * @param {Chunk} chunk the chunk - * @returns {ReadonlySet} runtime requirements + * @param {Chunk} otherChunk the other chunk + * @param {ChunkSizeOptions} options options object + * @returns {number} total size of the chunk or false if the chunk can't be integrated */ - getTreeRuntimeRequirements(chunk) { - const cgc = this._getChunkGraphChunk(chunk); - return cgc.runtimeRequirementsInTree; + integratedSize(otherChunk, options) { + const chunkGraph = ChunkGraph.getChunkGraphForChunk( + this, + "Chunk.integratedSize", + "DEP_WEBPACK_CHUNK_INTEGRATED_SIZE" + ); + return chunkGraph.getIntegratedChunksSize(this, otherChunk, options); } - // TODO remove in webpack 6 /** - * @param {Module} module the module - * @param {string} deprecateMessage message for the deprecation message - * @param {string} deprecationCode code for the deprecation - * @returns {ChunkGraph} the chunk graph + * @param {ModuleFilterPredicate} filterFn function used to filter modules + * @returns {ChunkModuleMaps} module map information */ - static getChunkGraphForModule(module, deprecateMessage, deprecationCode) { - const fn = deprecateGetChunkGraphForModuleMap.get(deprecateMessage); - if (fn) return fn(module); - const newFn = util.deprecate( - /** - * @param {Module} module the module - * @returns {ChunkGraph} the chunk graph - */ - module => { - const chunkGraph = chunkGraphForModuleMap.get(module); - if (!chunkGraph) - throw new Error( - deprecateMessage + - ": There was no ChunkGraph assigned to the Module for backward-compat (Use the new API)" - ); - return chunkGraph; - }, - deprecateMessage + ": Use new ChunkGraph API", - deprecationCode + getChunkModuleMaps(filterFn) { + const chunkGraph = ChunkGraph.getChunkGraphForChunk( + this, + "Chunk.getChunkModuleMaps", + "DEP_WEBPACK_CHUNK_GET_CHUNK_MODULE_MAPS" ); - deprecateGetChunkGraphForModuleMap.set(deprecateMessage, newFn); - return newFn(module); + /** @type {Record} */ + const chunkModuleIdMap = Object.create(null); + /** @type {Record} */ + const chunkModuleHashMap = Object.create(null); + + for (const asyncChunk of this.getAllAsyncChunks()) { + /** @type {(string|number)[]} */ + let array; + for (const module of chunkGraph.getOrderedChunkModulesIterable( + asyncChunk, + compareModulesById(chunkGraph) + )) { + if (filterFn(module)) { + if (array === undefined) { + array = []; + chunkModuleIdMap[asyncChunk.id] = array; + } + const moduleId = chunkGraph.getModuleId(module); + array.push(moduleId); + chunkModuleHashMap[moduleId] = chunkGraph.getRenderedModuleHash( + module, + undefined + ); + } + } + } + + return { + id: chunkModuleIdMap, + hash: chunkModuleHashMap + }; } - // TODO remove in webpack 6 /** - * @param {Module} module the module - * @param {ChunkGraph} chunkGraph the chunk graph - * @returns {void} + * @param {ModuleFilterPredicate} filterFn predicate function used to filter modules + * @param {ChunkFilterPredicate=} filterChunkFn predicate function used to filter chunks + * @returns {boolean} return true if module exists in graph */ - static setChunkGraphForModule(module, chunkGraph) { - chunkGraphForModuleMap.set(module, chunkGraph); + hasModuleInGraph(filterFn, filterChunkFn) { + const chunkGraph = ChunkGraph.getChunkGraphForChunk( + this, + "Chunk.hasModuleInGraph", + "DEP_WEBPACK_CHUNK_HAS_MODULE_IN_GRAPH" + ); + return chunkGraph.hasModuleInGraph(this, filterFn, filterChunkFn); } - // TODO remove in webpack 6 /** - * @param {Module} module the module - * @returns {void} + * @deprecated + * @param {boolean} realHash whether the full hash or the rendered hash is to be used + * @returns {ChunkMaps} the chunk map information */ - static clearChunkGraphForModule(module) { - chunkGraphForModuleMap.delete(module); + getChunkMaps(realHash) { + /** @type {Record} */ + const chunkHashMap = Object.create(null); + /** @type {Record>} */ + const chunkContentHashMap = Object.create(null); + /** @type {Record} */ + const chunkNameMap = Object.create(null); + + for (const chunk of this.getAllAsyncChunks()) { + chunkHashMap[chunk.id] = realHash ? chunk.hash : chunk.renderedHash; + for (const key of Object.keys(chunk.contentHash)) { + if (!chunkContentHashMap[key]) { + chunkContentHashMap[key] = Object.create(null); + } + chunkContentHashMap[key][chunk.id] = chunk.contentHash[key]; + } + if (chunk.name) { + chunkNameMap[chunk.id] = chunk.name; + } + } + + return { + hash: chunkHashMap, + contentHash: chunkContentHashMap, + name: chunkNameMap + }; } + // BACKWARD-COMPAT END - // TODO remove in webpack 6 /** - * @param {Chunk} chunk the chunk - * @param {string} deprecateMessage message for the deprecation message - * @param {string} deprecationCode code for the deprecation - * @returns {ChunkGraph} the chunk graph + * @returns {boolean} whether or not the Chunk will have a runtime */ - static getChunkGraphForChunk(chunk, deprecateMessage, deprecationCode) { - const fn = deprecateGetChunkGraphForChunkMap.get(deprecateMessage); - if (fn) return fn(chunk); - const newFn = util.deprecate( - /** - * @param {Chunk} chunk the chunk - * @returns {ChunkGraph} the chunk graph - */ - chunk => { - const chunkGraph = chunkGraphForChunkMap.get(chunk); - if (!chunkGraph) - throw new Error( - deprecateMessage + - "There was no ChunkGraph assigned to the Chunk for backward-compat (Use the new API)" - ); - return chunkGraph; - }, - deprecateMessage + ": Use new ChunkGraph API", - deprecationCode - ); - deprecateGetChunkGraphForChunkMap.set(deprecateMessage, newFn); - return newFn(chunk); + hasRuntime() { + for (const chunkGroup of this._groups) { + if ( + chunkGroup instanceof Entrypoint && + chunkGroup.getRuntimeChunk() === this + ) { + return true; + } + } + return false; } - // TODO remove in webpack 6 /** - * @param {Chunk} chunk the chunk - * @param {ChunkGraph} chunkGraph the chunk graph - * @returns {void} + * @returns {boolean} whether or not this chunk can be an initial chunk */ - static setChunkGraphForChunk(chunk, chunkGraph) { - chunkGraphForChunkMap.set(chunk, chunkGraph); + canBeInitial() { + for (const chunkGroup of this._groups) { + if (chunkGroup.isInitial()) return true; + } + return false; } - // TODO remove in webpack 6 /** - * @param {Chunk} chunk the chunk - * @returns {void} + * @returns {boolean} whether this chunk can only be an initial chunk */ - static clearChunkGraphForChunk(chunk) { - chunkGraphForChunkMap.delete(chunk); + isOnlyInitial() { + if (this._groups.size <= 0) return false; + for (const chunkGroup of this._groups) { + if (!chunkGroup.isInitial()) return false; + } + return true; } -} - -// TODO remove in webpack 6 -/** @type {WeakMap} */ -const chunkGraphForModuleMap = new WeakMap(); - -// TODO remove in webpack 6 -/** @type {WeakMap} */ -const chunkGraphForChunkMap = new WeakMap(); - -// TODO remove in webpack 6 -/** @type {Map ChunkGraph>} */ -const deprecateGetChunkGraphForModuleMap = new Map(); - -// TODO remove in webpack 6 -/** @type {Map ChunkGraph>} */ -const deprecateGetChunkGraphForChunkMap = new Map(); - -module.exports = ChunkGraph; - - -/***/ }), - -/***/ 96975: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ - - - -const util = __webpack_require__(31669); -const SortableSet = __webpack_require__(67563); -const { - compareLocations, - compareChunks, - compareIterables -} = __webpack_require__(26296); - -/** @typedef {import("./AsyncDependenciesBlock")} AsyncDependenciesBlock */ -/** @typedef {import("./Chunk")} Chunk */ -/** @typedef {import("./ChunkGraph")} ChunkGraph */ -/** @typedef {import("./Dependency").DependencyLocation} DependencyLocation */ -/** @typedef {import("./Entrypoint")} Entrypoint */ -/** @typedef {import("./Module")} Module */ -/** @typedef {import("./ModuleGraph")} ModuleGraph */ - -/** @typedef {{id: number}} HasId */ -/** @typedef {{module: Module, loc: DependencyLocation, request: string}} OriginRecord */ - -/** - * @typedef {Object} RawChunkGroupOptions - * @property {number=} preloadOrder - * @property {number=} prefetchOrder - */ - -/** @typedef {RawChunkGroupOptions & { name?: string }} ChunkGroupOptions */ - -let debugId = 5000; - -/** - * @template T - * @param {SortableSet} set set to convert to array. - * @returns {T[]} the array format of existing set - */ -const getArray = set => Array.from(set); - -/** - * A convenience method used to sort chunks based on their id's - * @param {ChunkGroup} a first sorting comparator - * @param {ChunkGroup} b second sorting comparator - * @returns {1|0|-1} a sorting index to determine order - */ -const sortById = (a, b) => { - if (a.id < b.id) return -1; - if (b.id < a.id) return 1; - return 0; -}; - -/** - * @param {OriginRecord} a the first comparator in sort - * @param {OriginRecord} b the second comparator in sort - * @returns {1|-1|0} returns sorting order as index - */ -const sortOrigin = (a, b) => { - const aIdent = a.module ? a.module.identifier() : ""; - const bIdent = b.module ? b.module.identifier() : ""; - if (aIdent < bIdent) return -1; - if (aIdent > bIdent) return 1; - return compareLocations(a.loc, b.loc); -}; -class ChunkGroup { /** - * Creates an instance of ChunkGroup. - * @param {string|ChunkGroupOptions=} options chunk group options passed to chunkGroup + * @returns {EntryOptions | undefined} the entry options for this chunk */ - constructor(options) { - if (typeof options === "string") { - options = { name: options }; - } else if (!options) { - options = { name: undefined }; + getEntryOptions() { + for (const chunkGroup of this._groups) { + if (chunkGroup instanceof Entrypoint) { + return chunkGroup.options; + } } - /** @type {number} */ - this.groupDebugId = debugId++; - this.options = options; - /** @type {SortableSet} */ - this._children = new SortableSet(undefined, sortById); - /** @type {SortableSet} */ - this._parents = new SortableSet(undefined, sortById); - /** @type {SortableSet} */ - this._asyncEntrypoints = new SortableSet(undefined, sortById); - this._blocks = new SortableSet(); - /** @type {Chunk[]} */ - this.chunks = []; - /** @type {OriginRecord[]} */ - this.origins = []; - /** Indices in top-down order */ - /** @private @type {Map} */ - this._modulePreOrderIndices = new Map(); - /** Indices in bottom-up order */ - /** @private @type {Map} */ - this._modulePostOrderIndices = new Map(); - /** @type {number} */ - this.index = undefined; + return undefined; } /** - * when a new chunk is added to a chunkGroup, addingOptions will occur. - * @param {ChunkGroupOptions} options the chunkGroup options passed to addOptions + * @param {ChunkGroup} chunkGroup the chunkGroup the chunk is being added * @returns {void} */ - addOptions(options) { - for (const key of Object.keys(options)) { - if (this.options[key] === undefined) { - this.options[key] = options[key]; - } else if (this.options[key] !== options[key]) { - if (key.endsWith("Order")) { - this.options[key] = Math.max(this.options[key], options[key]); - } else { - throw new Error( - `ChunkGroup.addOptions: No option merge strategy for ${key}` - ); - } - } - } + addGroup(chunkGroup) { + this._groups.add(chunkGroup); } /** - * returns the name of current ChunkGroup - * @returns {string|undefined} returns the ChunkGroup name + * @param {ChunkGroup} chunkGroup the chunkGroup the chunk is being removed from + * @returns {void} */ - get name() { - return this.options.name; + removeGroup(chunkGroup) { + this._groups.delete(chunkGroup); } /** - * sets a new name for current ChunkGroup - * @param {string} value the new name for ChunkGroup - * @returns {void} + * @param {ChunkGroup} chunkGroup the chunkGroup to check + * @returns {boolean} returns true if chunk has chunkGroup reference and exists in chunkGroup */ - set name(value) { - this.options.name = value; + isInGroup(chunkGroup) { + return this._groups.has(chunkGroup); } - /* istanbul ignore next */ /** - * get a uniqueId for ChunkGroup, made up of its member Chunk debugId's - * @returns {string} a unique concatenation of chunk debugId's + * @returns {number} the amount of groups that the said chunk is in */ - get debugId() { - return Array.from(this.chunks, x => x.debugId).join("+"); + getNumberOfGroups() { + return this._groups.size; } /** - * get a unique id for ChunkGroup, made up of its member Chunk id's - * @returns {string} a unique concatenation of chunk ids + * @returns {Iterable} the chunkGroups that the said chunk is referenced in */ - get id() { - return Array.from(this.chunks, x => x.id).join("+"); + get groupsIterable() { + this._groups.sort(); + return this._groups; } /** - * Performs an unshift of a specific chunk - * @param {Chunk} chunk chunk being unshifted - * @returns {boolean} returns true if attempted chunk shift is accepted + * @returns {void} */ - unshiftChunk(chunk) { - const oldIdx = this.chunks.indexOf(chunk); - if (oldIdx > 0) { - this.chunks.splice(oldIdx, 1); - this.chunks.unshift(chunk); - } else if (oldIdx < 0) { - this.chunks.unshift(chunk); - return true; + disconnectFromGroups() { + for (const chunkGroup of this._groups) { + chunkGroup.removeChunk(this); } - return false; } /** - * inserts a chunk before another existing chunk in group - * @param {Chunk} chunk Chunk being inserted - * @param {Chunk} before Placeholder/target chunk marking new chunk insertion point - * @returns {boolean} return true if insertion was successful + * @param {Chunk} newChunk the new chunk that will be split out of + * @returns {void} */ - insertChunk(chunk, before) { - const oldIdx = this.chunks.indexOf(chunk); - const idx = this.chunks.indexOf(before); - if (idx < 0) { - throw new Error("before chunk not found"); - } - if (oldIdx >= 0 && oldIdx > idx) { - this.chunks.splice(oldIdx, 1); - this.chunks.splice(idx, 0, chunk); - } else if (oldIdx < 0) { - this.chunks.splice(idx, 0, chunk); - return true; + split(newChunk) { + for (const chunkGroup of this._groups) { + chunkGroup.insertChunk(newChunk, this); + newChunk.addGroup(chunkGroup); } - return false; - } - - /** - * add a chunk into ChunkGroup. Is pushed on or prepended - * @param {Chunk} chunk chunk being pushed into ChunkGroupS - * @returns {boolean} returns true if chunk addition was successful. - */ - pushChunk(chunk) { - const oldIdx = this.chunks.indexOf(chunk); - if (oldIdx >= 0) { - return false; + for (const idHint of this.idNameHints) { + newChunk.idNameHints.add(idHint); } - this.chunks.push(chunk); - return true; + newChunk.runtime = mergeRuntime(newChunk.runtime, this.runtime); } /** - * @param {Chunk} oldChunk chunk to be replaced - * @param {Chunk} newChunk New chunk that will be replaced with - * @returns {boolean} returns true if the replacement was successful + * @param {Hash} hash hash (will be modified) + * @param {ChunkGraph} chunkGraph the chunk graph + * @returns {void} */ - replaceChunk(oldChunk, newChunk) { - const oldIdx = this.chunks.indexOf(oldChunk); - if (oldIdx < 0) return false; - const newIdx = this.chunks.indexOf(newChunk); - if (newIdx < 0) { - this.chunks[oldIdx] = newChunk; - return true; - } - if (newIdx < oldIdx) { - this.chunks.splice(oldIdx, 1); - return true; - } else if (newIdx !== oldIdx) { - this.chunks[oldIdx] = newChunk; - this.chunks.splice(newIdx, 1); - return true; + updateHash(hash, chunkGraph) { + hash.update( + `${this.id} ${this.ids ? this.ids.join() : ""} ${this.name || ""} ` + ); + const xor = new StringXor(); + for (const m of chunkGraph.getChunkModulesIterable(this)) { + xor.add(chunkGraph.getModuleHash(m, this.runtime)); } - } - - /** - * @param {Chunk} chunk chunk to remove - * @returns {boolean} returns true if chunk was removed - */ - removeChunk(chunk) { - const idx = this.chunks.indexOf(chunk); - if (idx >= 0) { - this.chunks.splice(idx, 1); - return true; + xor.updateHash(hash); + const entryModules = + chunkGraph.getChunkEntryModulesWithChunkGroupIterable(this); + for (const [m, chunkGroup] of entryModules) { + hash.update(`entry${chunkGraph.getModuleId(m)}${chunkGroup.id}`); } - return false; - } - - /** - * @returns {boolean} true, when this chunk group will be loaded on initial page load - */ - isInitial() { - return false; - } - - /** - * @param {ChunkGroup} group chunk group to add - * @returns {boolean} returns true if chunk group was added - */ - addChild(group) { - const size = this._children.size; - this._children.add(group); - return size !== this._children.size; } /** - * @returns {ChunkGroup[]} returns the children of this group + * @returns {Set} a set of all the async chunks */ - getChildren() { - return this._children.getFromCache(getArray); - } + getAllAsyncChunks() { + const queue = new Set(); + const chunks = new Set(); - getNumberOfChildren() { - return this._children.size; - } + const initialChunks = intersect( + Array.from(this.groupsIterable, g => new Set(g.chunks)) + ); - get childrenIterable() { - return this._children; - } + const initialQueue = new Set(this.groupsIterable); - /** - * @param {ChunkGroup} group the chunk group to remove - * @returns {boolean} returns true if the chunk group was removed - */ - removeChild(group) { - if (!this._children.has(group)) { - return false; + for (const chunkGroup of initialQueue) { + for (const child of chunkGroup.childrenIterable) { + if (child instanceof Entrypoint) { + initialQueue.add(child); + } else { + queue.add(child); + } + } } - this._children.delete(group); - group.removeParent(this); - return true; - } - - /** - * @param {ChunkGroup} parentChunk the parent group to be added into - * @returns {boolean} returns true if this chunk group was added to the parent group - */ - addParent(parentChunk) { - if (!this._parents.has(parentChunk)) { - this._parents.add(parentChunk); - return true; + for (const chunkGroup of queue) { + for (const chunk of chunkGroup.chunks) { + if (!initialChunks.has(chunk)) { + chunks.add(chunk); + } + } + for (const child of chunkGroup.childrenIterable) { + queue.add(child); + } } - return false; - } - - /** - * @returns {ChunkGroup[]} returns the parents of this group - */ - getParents() { - return this._parents.getFromCache(getArray); - } - - getNumberOfParents() { - return this._parents.size; - } - - /** - * @param {ChunkGroup} parent the parent group - * @returns {boolean} returns true if the parent group contains this group - */ - hasParent(parent) { - return this._parents.has(parent); - } - get parentsIterable() { - return this._parents; + return chunks; } /** - * @param {ChunkGroup} chunkGroup the parent group - * @returns {boolean} returns true if this group has been removed from the parent + * @returns {Set} a set of all the initial chunks (including itself) */ - removeParent(chunkGroup) { - if (this._parents.delete(chunkGroup)) { - chunkGroup.removeChild(this); - return true; + getAllInitialChunks() { + const chunks = new Set(); + const queue = new Set(this.groupsIterable); + for (const group of queue) { + if (group.isInitial()) { + for (const c of group.chunks) chunks.add(c); + for (const g of group.childrenIterable) queue.add(g); + } } - return false; - } - - /** - * @param {Entrypoint} entrypoint entrypoint to add - * @returns {boolean} returns true if entrypoint was added - */ - addAsyncEntrypoint(entrypoint) { - const size = this._asyncEntrypoints.size; - this._asyncEntrypoints.add(entrypoint); - return size !== this._asyncEntrypoints.size; - } - - get asyncEntrypointsIterable() { - return this._asyncEntrypoints; - } - - /** - * @returns {Array} an array containing the blocks - */ - getBlocks() { - return this._blocks.getFromCache(getArray); - } - - getNumberOfBlocks() { - return this._blocks.size; - } - - hasBlock(block) { - return this._blocks.has(block); + return chunks; } /** - * @returns {Iterable} blocks + * @returns {Set} a set of all the referenced chunks (including itself) */ - get blocksIterable() { - return this._blocks; - } + getAllReferencedChunks() { + const queue = new Set(this.groupsIterable); + const chunks = new Set(); - /** - * @param {AsyncDependenciesBlock} block a block - * @returns {boolean} false, if block was already added - */ - addBlock(block) { - if (!this._blocks.has(block)) { - this._blocks.add(block); - return true; + for (const chunkGroup of queue) { + for (const chunk of chunkGroup.chunks) { + chunks.add(chunk); + } + for (const child of chunkGroup.childrenIterable) { + queue.add(child); + } } - return false; - } - /** - * @param {Module} module origin module - * @param {DependencyLocation} loc location of the reference in the origin module - * @param {string} request request name of the reference - * @returns {void} - */ - addOrigin(module, loc, request) { - this.origins.push({ - module, - loc, - request - }); + return chunks; } /** - * @returns {string[]} the files contained this chunk group + * @returns {Set} a set of all the referenced entrypoints */ - getFiles() { - const files = new Set(); + getAllReferencedAsyncEntrypoints() { + const queue = new Set(this.groupsIterable); + const entrypoints = new Set(); - for (const chunk of this.chunks) { - for (const file of chunk.files) { - files.add(file); + for (const chunkGroup of queue) { + for (const entrypoint of chunkGroup.asyncEntrypointsIterable) { + entrypoints.add(entrypoint); + } + for (const child of chunkGroup.childrenIterable) { + queue.add(child); } } - return Array.from(files); + return entrypoints; } /** - * @returns {void} + * @returns {boolean} true, if the chunk references async chunks */ - remove() { - // cleanup parents - for (const parentChunkGroup of this._parents) { - // remove this chunk from its parents - parentChunkGroup._children.delete(this); + hasAsyncChunks() { + const queue = new Set(); - // cleanup "sub chunks" - for (const chunkGroup of this._children) { - /** - * remove this chunk as "intermediary" and connect - * it "sub chunks" and parents directly - */ - // add parent to each "sub chunk" - chunkGroup.addParent(parentChunkGroup); - // add "sub chunk" to parent - parentChunkGroup.addChild(chunkGroup); - } - } + const initialChunks = intersect( + Array.from(this.groupsIterable, g => new Set(g.chunks)) + ); - /** - * we need to iterate again over the children - * to remove this from the child's parents. - * This can not be done in the above loop - * as it is not guaranteed that `this._parents` contains anything. - */ - for (const chunkGroup of this._children) { - // remove this as parent of every "sub chunk" - chunkGroup._parents.delete(this); + for (const chunkGroup of this.groupsIterable) { + for (const child of chunkGroup.childrenIterable) { + queue.add(child); + } } - // remove chunks - for (const chunk of this.chunks) { - chunk.removeGroup(this); + for (const chunkGroup of queue) { + for (const chunk of chunkGroup.chunks) { + if (!initialChunks.has(chunk)) { + return true; + } + } + for (const child of chunkGroup.childrenIterable) { + queue.add(child); + } } - } - - sortItems() { - this.origins.sort(sortOrigin); - } - /** - * Sorting predicate which allows current ChunkGroup to be compared against another. - * Sorting values are based off of number of chunks in ChunkGroup. - * - * @param {ChunkGraph} chunkGraph the chunk graph - * @param {ChunkGroup} otherGroup the chunkGroup to compare this against - * @returns {-1|0|1} sort position for comparison - */ - compareTo(chunkGraph, otherGroup) { - if (this.chunks.length > otherGroup.chunks.length) return -1; - if (this.chunks.length < otherGroup.chunks.length) return 1; - return compareIterables(compareChunks(chunkGraph))( - this.chunks, - otherGroup.chunks - ); + return false; } /** - * @param {ModuleGraph} moduleGraph the module graph * @param {ChunkGraph} chunkGraph the chunk graph - * @returns {Record} mapping from children type to ordered list of ChunkGroups + * @param {ChunkFilterPredicate=} filterFn function used to filter chunks + * @returns {Record} a record object of names to lists of child ids(?) */ - getChildrenByOrders(moduleGraph, chunkGraph) { + getChildIdsByOrders(chunkGraph, filterFn) { /** @type {Map} */ const lists = new Map(); - for (const childGroup of this._children) { - for (const key of Object.keys(childGroup.options)) { - if (key.endsWith("Order")) { - const name = key.substr(0, key.length - "Order".length); - let list = lists.get(name); - if (list === undefined) { - lists.set(name, (list = [])); + for (const group of this.groupsIterable) { + if (group.chunks[group.chunks.length - 1] === this) { + for (const childGroup of group.childrenIterable) { + for (const key of Object.keys(childGroup.options)) { + if (key.endsWith("Order")) { + const name = key.substr(0, key.length - "Order".length); + let list = lists.get(name); + if (list === undefined) { + list = []; + lists.set(name, list); + } + list.push({ + order: childGroup.options[key], + group: childGroup + }); + } } - list.push({ - order: childGroup.options[key], - group: childGroup - }); } } } - /** @type {Record} */ + /** @type {Record} */ const result = Object.create(null); for (const [name, list] of lists) { list.sort((a, b) => { @@ -26947,87 +26438,116 @@ class ChunkGroup { if (cmp !== 0) return cmp; return a.group.compareTo(chunkGraph, b.group); }); - result[name] = list.map(i => i.group); + /** @type {Set} */ + const chunkIdSet = new Set(); + for (const item of list) { + for (const chunk of item.group.chunks) { + if (filterFn && !filterFn(chunk, chunkGraph)) continue; + chunkIdSet.add(chunk.id); + } + } + if (chunkIdSet.size > 0) { + result[name] = Array.from(chunkIdSet); + } } return result; } /** - * Sets the top-down index of a module in this ChunkGroup - * @param {Module} module module for which the index should be set - * @param {number} index the index of the module - * @returns {void} - */ - setModulePreOrderIndex(module, index) { - this._modulePreOrderIndices.set(module, index); - } - - /** - * Gets the top-down index of a module in this ChunkGroup - * @param {Module} module the module - * @returns {number} index + * @param {ChunkGraph} chunkGraph the chunk graph + * @param {string} type option name + * @returns {{ onChunks: Chunk[], chunks: Set }[]} referenced chunks for a specific type */ - getModulePreOrderIndex(module) { - return this._modulePreOrderIndices.get(module); + getChildrenOfTypeInOrder(chunkGraph, type) { + const list = []; + for (const group of this.groupsIterable) { + for (const childGroup of group.childrenIterable) { + const order = childGroup.options[type]; + if (order === undefined) continue; + list.push({ + order, + group, + childGroup + }); + } + } + if (list.length === 0) return undefined; + list.sort((a, b) => { + const cmp = b.order - a.order; + if (cmp !== 0) return cmp; + return a.group.compareTo(chunkGraph, b.group); + }); + const result = []; + let lastEntry; + for (const { group, childGroup } of list) { + if (lastEntry && lastEntry.onChunks === group.chunks) { + for (const chunk of childGroup.chunks) { + lastEntry.chunks.add(chunk); + } + } else { + result.push( + (lastEntry = { + onChunks: group.chunks, + chunks: new Set(childGroup.chunks) + }) + ); + } + } + return result; } /** - * Sets the bottom-up index of a module in this ChunkGroup - * @param {Module} module module for which the index should be set - * @param {number} index the index of the module - * @returns {void} + * @param {ChunkGraph} chunkGraph the chunk graph + * @param {boolean=} includeDirectChildren include direct children (by default only children of async children are included) + * @param {ChunkFilterPredicate=} filterFn function used to filter chunks + * @returns {Record>} a record object of names to lists of child ids(?) by chunk id */ - setModulePostOrderIndex(module, index) { - this._modulePostOrderIndices.set(module, index); - } + getChildIdsByOrdersMap(chunkGraph, includeDirectChildren, filterFn) { + /** @type {Record>} */ + const chunkMaps = Object.create(null); - /** - * Gets the bottom-up index of a module in this ChunkGroup - * @param {Module} module the module - * @returns {number} index - */ - getModulePostOrderIndex(module) { - return this._modulePostOrderIndices.get(module); - } + /** + * @param {Chunk} chunk a chunk + * @returns {void} + */ + const addChildIdsByOrdersToMap = chunk => { + const data = chunk.getChildIdsByOrders(chunkGraph, filterFn); + for (const key of Object.keys(data)) { + let chunkMap = chunkMaps[key]; + if (chunkMap === undefined) { + chunkMaps[key] = chunkMap = Object.create(null); + } + chunkMap[chunk.id] = data[key]; + } + }; - /* istanbul ignore next */ - checkConstraints() { - const chunk = this; - for (const child of chunk._children) { - if (!child._parents.has(chunk)) { - throw new Error( - `checkConstraints: child missing parent ${chunk.debugId} -> ${child.debugId}` - ); + if (includeDirectChildren) { + /** @type {Set} */ + const chunks = new Set(); + for (const chunkGroup of this.groupsIterable) { + for (const chunk of chunkGroup.chunks) { + chunks.add(chunk); + } } - } - for (const parentChunk of chunk._parents) { - if (!parentChunk._children.has(chunk)) { - throw new Error( - `checkConstraints: parent missing child ${parentChunk.debugId} <- ${chunk.debugId}` - ); + for (const chunk of chunks) { + addChildIdsByOrdersToMap(chunk); } } + + for (const chunk of this.getAllAsyncChunks()) { + addChildIdsByOrdersToMap(chunk); + } + + return chunkMaps; } } -ChunkGroup.prototype.getModuleIndex = util.deprecate( - ChunkGroup.prototype.getModulePreOrderIndex, - "ChunkGroup.getModuleIndex was renamed to getModulePreOrderIndex", - "DEP_WEBPACK_CHUNK_GROUP_GET_MODULE_INDEX" -); - -ChunkGroup.prototype.getModuleIndex2 = util.deprecate( - ChunkGroup.prototype.getModulePostOrderIndex, - "ChunkGroup.getModuleIndex2 was renamed to getModulePostOrderIndex", - "DEP_WEBPACK_CHUNK_GROUP_GET_MODULE_INDEX_2" -); - -module.exports = ChunkGroup; +module.exports = Chunk; /***/ }), -/***/ 80187: +/***/ 97860: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; @@ -27038,6475 +26558,4415 @@ module.exports = ChunkGroup; -const WebpackError = __webpack_require__(68422); +const util = __webpack_require__(31669); +const Entrypoint = __webpack_require__(86695); +const ModuleGraphConnection = __webpack_require__(94144); +const { first } = __webpack_require__(34715); +const SortableSet = __webpack_require__(67563); +const { + compareModulesById, + compareIterables, + compareModulesByIdentifier, + concatComparators, + compareSelect, + compareIds +} = __webpack_require__(26296); +const createHash = __webpack_require__(24123); +const findGraphRoots = __webpack_require__(38670); +const { + RuntimeSpecMap, + RuntimeSpecSet, + runtimeToString, + mergeRuntime, + forEachRuntime +} = __webpack_require__(19655); +/** @typedef {import("./AsyncDependenciesBlock")} AsyncDependenciesBlock */ /** @typedef {import("./Chunk")} Chunk */ +/** @typedef {import("./ChunkGroup")} ChunkGroup */ +/** @typedef {import("./Module")} Module */ +/** @typedef {import("./ModuleGraph")} ModuleGraph */ +/** @typedef {import("./RuntimeModule")} RuntimeModule */ +/** @typedef {typeof import("./util/Hash")} Hash */ +/** @typedef {import("./util/runtime").RuntimeSpec} RuntimeSpec */ -class ChunkRenderError extends WebpackError { - /** - * Create a new ChunkRenderError - * @param {Chunk} chunk A chunk - * @param {string} file Related file - * @param {Error} error Original error - */ - constructor(chunk, file, error) { - super(); - - this.name = "ChunkRenderError"; - this.error = error; - this.message = error.message; - this.details = error.stack; - this.file = file; - this.chunk = chunk; - } -} - -module.exports = ChunkRenderError; - - -/***/ }), - -/***/ 50527: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ - +/** @type {ReadonlySet} */ +const EMPTY_SET = new Set(); +const ZERO_BIG_INT = BigInt(0); -const util = __webpack_require__(31669); -const memoize = __webpack_require__(84297); +const compareModuleIterables = compareIterables(compareModulesByIdentifier); -/** @typedef {import("../declarations/WebpackOptions").Output} OutputOptions */ -/** @typedef {import("./Compilation")} Compilation */ +/** @typedef {(c: Chunk, chunkGraph: ChunkGraph) => boolean} ChunkFilterPredicate */ +/** @typedef {(m: Module) => boolean} ModuleFilterPredicate */ -const getJavascriptModulesPlugin = memoize(() => - __webpack_require__(76767) -); +/** + * @typedef {Object} ChunkSizeOptions + * @property {number=} chunkOverhead constant overhead for a chunk + * @property {number=} entryChunkMultiplicator multiplicator for initial chunks + */ -// TODO webpack 6 remove this class -class ChunkTemplate { - /** - * @param {OutputOptions} outputOptions output options - * @param {Compilation} compilation the compilation - */ - constructor(outputOptions, compilation) { - this._outputOptions = outputOptions || {}; - this.hooks = Object.freeze({ - renderManifest: { - tap: util.deprecate( - (options, fn) => { - compilation.hooks.renderManifest.tap( - options, - (entries, options) => { - if (options.chunk.hasRuntime()) return entries; - return fn(entries, options); - } - ); - }, - "ChunkTemplate.hooks.renderManifest is deprecated (use Compilation.hooks.renderManifest instead)", - "DEP_WEBPACK_CHUNK_TEMPLATE_RENDER_MANIFEST" - ) - }, - modules: { - tap: util.deprecate( - (options, fn) => { - getJavascriptModulesPlugin() - .getCompilationHooks(compilation) - .renderChunk.tap(options, (source, renderContext) => - fn( - source, - compilation.moduleTemplates.javascript, - renderContext - ) - ); - }, - "ChunkTemplate.hooks.modules is deprecated (use JavascriptModulesPlugin.getCompilationHooks().renderChunk instead)", - "DEP_WEBPACK_CHUNK_TEMPLATE_MODULES" - ) - }, - render: { - tap: util.deprecate( - (options, fn) => { - getJavascriptModulesPlugin() - .getCompilationHooks(compilation) - .renderChunk.tap(options, (source, renderContext) => - fn( - source, - compilation.moduleTemplates.javascript, - renderContext - ) - ); - }, - "ChunkTemplate.hooks.render is deprecated (use JavascriptModulesPlugin.getCompilationHooks().renderChunk instead)", - "DEP_WEBPACK_CHUNK_TEMPLATE_RENDER" - ) - }, - renderWithEntry: { - tap: util.deprecate( - (options, fn) => { - getJavascriptModulesPlugin() - .getCompilationHooks(compilation) - .render.tap(options, (source, renderContext) => { - if ( - renderContext.chunkGraph.getNumberOfEntryModules( - renderContext.chunk - ) === 0 || - renderContext.chunk.hasRuntime() - ) { - return source; - } - return fn(source, renderContext.chunk); - }); - }, - "ChunkTemplate.hooks.renderWithEntry is deprecated (use JavascriptModulesPlugin.getCompilationHooks().render instead)", - "DEP_WEBPACK_CHUNK_TEMPLATE_RENDER_WITH_ENTRY" - ) - }, - hash: { - tap: util.deprecate( - (options, fn) => { - compilation.hooks.fullHash.tap(options, fn); - }, - "ChunkTemplate.hooks.hash is deprecated (use Compilation.hooks.fullHash instead)", - "DEP_WEBPACK_CHUNK_TEMPLATE_HASH" - ) - }, - hashForChunk: { - tap: util.deprecate( - (options, fn) => { - getJavascriptModulesPlugin() - .getCompilationHooks(compilation) - .chunkHash.tap(options, (chunk, hash, context) => { - if (chunk.hasRuntime()) return; - fn(hash, chunk, context); - }); - }, - "ChunkTemplate.hooks.hashForChunk is deprecated (use JavascriptModulesPlugin.getCompilationHooks().chunkHash instead)", - "DEP_WEBPACK_CHUNK_TEMPLATE_HASH_FOR_CHUNK" - ) - } - }); +class ModuleHashInfo { + constructor(hash, renderedHash) { + this.hash = hash; + this.renderedHash = renderedHash; } } -Object.defineProperty(ChunkTemplate.prototype, "outputOptions", { - get: util.deprecate( - /** - * @this {ChunkTemplate} - * @returns {OutputOptions} output options - */ - function () { - return this._outputOptions; - }, - "ChunkTemplate.outputOptions is deprecated (use Compilation.outputOptions instead)", - "DEP_WEBPACK_CHUNK_TEMPLATE_OUTPUT_OPTIONS" - ) -}); - -module.exports = ChunkTemplate; - - -/***/ }), - -/***/ 49129: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Sergey Melyukov @smelukov -*/ - - - -const asyncLib = __webpack_require__(36386); -const { SyncBailHook } = __webpack_require__(34718); -const Compilation = __webpack_require__(59622); -const createSchemaValidation = __webpack_require__(77695); -const { join } = __webpack_require__(93204); -const processAsyncTree = __webpack_require__(76815); - -/** @typedef {import("../declarations/WebpackOptions").CleanOptions} CleanOptions */ -/** @typedef {import("./Compiler")} Compiler */ -/** @typedef {import("./logging/Logger").Logger} Logger */ -/** @typedef {import("./util/fs").OutputFileSystem} OutputFileSystem */ -/** @typedef {import("./util/fs").StatsCallback} StatsCallback */ - -/** @typedef {(function(string):boolean)|RegExp} IgnoreItem */ -/** @typedef {function(IgnoreItem): void} AddToIgnoreCallback */ +/** @template T @typedef {(set: SortableSet) => T[]} SetToArrayFunction */ /** - * @typedef {Object} CleanPluginCompilationHooks - * @property {SyncBailHook<[string], boolean>} keep when returning true the file/directory will be kept during cleaning, returning false will clean it and ignore the following plugins and config + * @template T + * @param {SortableSet} set the set + * @returns {T[]} set as array */ +const getArray = set => { + return Array.from(set); +}; -const validate = createSchemaValidation( - undefined, - () => { - const { definitions } = __webpack_require__(1863); - return { - definitions, - oneOf: [{ $ref: "#/definitions/CleanOptions" }] - }; - }, - { - name: "Clean Plugin", - baseDataPath: "options" +/** + * @param {SortableSet} chunks the chunks + * @returns {RuntimeSpecSet} runtimes + */ +const getModuleRuntimes = chunks => { + const runtimes = new RuntimeSpecSet(); + for (const chunk of chunks) { + runtimes.add(chunk.runtime); } -); + return runtimes; +}; /** - * @param {OutputFileSystem} fs filesystem - * @param {string} outputPath output path - * @param {Set} currentAssets filename of the current assets (must not start with .. or ., must only use / as path separator) - * @param {function(Error=, Set=): void} callback returns the filenames of the assets that shouldn't be there - * @returns {void} + * @param {SortableSet} set the set + * @returns {Map>} modules by source type */ -const getDiffToFs = (fs, outputPath, currentAssets, callback) => { - const directories = new Set(); - // get directories of assets - for (const asset of currentAssets) { - directories.add(asset.replace(/(^|\/)[^/]*$/, "")); +const modulesBySourceType = set => { + /** @type {Map>} */ + const map = new Map(); + for (const module of set) { + for (const sourceType of module.getSourceTypes()) { + let innerSet = map.get(sourceType); + if (innerSet === undefined) { + innerSet = new SortableSet(); + map.set(sourceType, innerSet); + } + innerSet.add(module); + } } - // and all parent directories - for (const directory of directories) { - directories.add(directory.replace(/(^|\/)[^/]*$/, "")); + for (const [key, innerSet] of map) { + // When all modules have the source type, we reuse the original SortableSet + // to benefit from the shared cache (especially for sorting) + if (innerSet.size === set.size) { + map.set(key, set); + } } - const diff = new Set(); - asyncLib.forEachLimit( - directories, - 10, - (directory, callback) => { - fs.readdir(join(fs, outputPath, directory), (err, entries) => { - if (err) { - if (err.code === "ENOENT") return callback(); - if (err.code === "ENOTDIR") { - diff.add(directory); - return callback(); - } - return callback(err); - } - for (const entry of entries) { - const file = /** @type {string} */ (entry); - const filename = directory ? `${directory}/${file}` : file; - if (!directories.has(filename) && !currentAssets.has(filename)) { - diff.add(filename); - } - } - callback(); - }); - }, - err => { - if (err) return callback(err); + return map; +}; - callback(null, diff); - } - ); +/** @type {WeakMap} */ +const createOrderedArrayFunctionMap = new WeakMap(); + +/** + * @template T + * @param {function(T, T): -1|0|1} comparator comparator function + * @returns {SetToArrayFunction} set as ordered array + */ +const createOrderedArrayFunction = comparator => { + /** @type {SetToArrayFunction} */ + let fn = createOrderedArrayFunctionMap.get(comparator); + if (fn !== undefined) return fn; + fn = set => { + set.sortWith(comparator); + return Array.from(set); + }; + createOrderedArrayFunctionMap.set(comparator, fn); + return fn; }; /** - * @param {Set} currentAssets assets list - * @param {Set} oldAssets old assets list - * @returns {Set} diff + * @param {Iterable} modules the modules to get the count/size of + * @returns {number} the size of the modules */ -const getDiffToOldAssets = (currentAssets, oldAssets) => { - const diff = new Set(); - for (const asset of oldAssets) { - if (!currentAssets.has(asset)) diff.add(asset); +const getModulesSize = modules => { + let size = 0; + for (const module of modules) { + for (const type of module.getSourceTypes()) { + size += module.size(type); + } } - return diff; + return size; }; /** - * @param {OutputFileSystem} fs filesystem - * @param {string} filename path to file - * @param {StatsCallback} callback callback for provided filename - * @returns {void} + * @param {Iterable} modules the sortable Set to get the size of + * @returns {Record} the sizes of the modules */ -const doStat = (fs, filename, callback) => { - if ("lstat" in fs) { - fs.lstat(filename, callback); - } else { - fs.stat(filename, callback); +const getModulesSizes = modules => { + let sizes = Object.create(null); + for (const module of modules) { + for (const type of module.getSourceTypes()) { + sizes[type] = (sizes[type] || 0) + module.size(type); + } } + return sizes; }; /** - * @param {OutputFileSystem} fs filesystem - * @param {string} outputPath output path - * @param {boolean} dry only log instead of fs modification - * @param {Logger} logger logger - * @param {Set} diff filenames of the assets that shouldn't be there - * @param {function(string): boolean} isKept check if the entry is ignored - * @param {function(Error=): void} callback callback - * @returns {void} + * @param {Chunk} a chunk + * @param {Chunk} b chunk + * @returns {boolean} true, if a is always a parent of b */ -const applyDiff = (fs, outputPath, dry, logger, diff, isKept, callback) => { - const log = msg => { - if (dry) { - logger.info(msg); - } else { - logger.log(msg); +const isAvailableChunk = (a, b) => { + const queue = new Set(b.groupsIterable); + for (const chunkGroup of queue) { + if (a.isInGroup(chunkGroup)) continue; + if (chunkGroup.isInitial()) return false; + for (const parent of chunkGroup.parentsIterable) { + queue.add(parent); } - }; - /** @typedef {{ type: "check" | "unlink" | "rmdir", filename: string, parent: { remaining: number, job: Job } | undefined }} Job */ - /** @type {Job[]} */ - const jobs = Array.from(diff, filename => ({ - type: "check", - filename, - parent: undefined - })); - processAsyncTree( - jobs, - 10, - ({ type, filename, parent }, push, callback) => { - const handleError = err => { - if (err.code === "ENOENT") { - log(`${filename} was removed during cleaning by something else`); - handleParent(); - return callback(); - } - return callback(err); - }; - const handleParent = () => { - if (parent && --parent.remaining === 0) push(parent.job); - }; - const path = join(fs, outputPath, filename); - switch (type) { - case "check": - if (isKept(filename)) { - // do not decrement parent entry as we don't want to delete the parent - log(`${filename} will be kept`); - return process.nextTick(callback); - } - doStat(fs, path, (err, stats) => { - if (err) return handleError(err); - if (!stats.isDirectory()) { - push({ - type: "unlink", - filename, - parent - }); - return callback(); - } - fs.readdir(path, (err, entries) => { - if (err) return handleError(err); - /** @type {Job} */ - const deleteJob = { - type: "rmdir", - filename, - parent - }; - if (entries.length === 0) { - push(deleteJob); - } else { - const parentToken = { - remaining: entries.length, - job: deleteJob - }; - for (const entry of entries) { - const file = /** @type {string} */ (entry); - if (file.startsWith(".")) { - log( - `${filename} will be kept (dot-files will never be removed)` - ); - continue; - } - push({ - type: "check", - filename: `${filename}/${file}`, - parent: parentToken - }); - } - } - return callback(); - }); - }); - break; - case "rmdir": - log(`${filename} will be removed`); - if (dry) { - handleParent(); - return process.nextTick(callback); - } - if (!fs.rmdir) { - logger.warn( - `${filename} can't be removed because output file system doesn't support removing directories (rmdir)` - ); - return process.nextTick(callback); - } - fs.rmdir(path, err => { - if (err) return handleError(err); - handleParent(); - callback(); - }); - break; - case "unlink": - log(`${filename} will be removed`); - if (dry) { - handleParent(); - return process.nextTick(callback); - } - if (!fs.unlink) { - logger.warn( - `${filename} can't be removed because output file system doesn't support removing files (rmdir)` - ); - return process.nextTick(callback); - } - fs.unlink(path, err => { - if (err) return handleError(err); - handleParent(); - callback(); - }); - break; - } - }, - callback - ); + } + return true; }; -/** @type {WeakMap} */ -const compilationHooksMap = new WeakMap(); - -class CleanPlugin { - /** - * @param {Compilation} compilation the compilation - * @returns {CleanPluginCompilationHooks} the attached hooks - */ - static getCompilationHooks(compilation) { - if (!(compilation instanceof Compilation)) { - throw new TypeError( - "The 'compilation' argument must be an instance of Compilation" - ); - } - let hooks = compilationHooksMap.get(compilation); - if (hooks === undefined) { - hooks = { - /** @type {SyncBailHook<[string], boolean>} */ - keep: new SyncBailHook(["ignore"]) - }; - compilationHooksMap.set(compilation, hooks); - } - return hooks; +class ChunkGraphModule { + constructor() { + /** @type {SortableSet} */ + this.chunks = new SortableSet(); + /** @type {Set | undefined} */ + this.entryInChunks = undefined; + /** @type {Set | undefined} */ + this.runtimeInChunks = undefined; + /** @type {RuntimeSpecMap} */ + this.hashes = undefined; + /** @type {string | number} */ + this.id = null; + /** @type {RuntimeSpecMap> | undefined} */ + this.runtimeRequirements = undefined; + /** @type {RuntimeSpecMap} */ + this.graphHashes = undefined; + /** @type {RuntimeSpecMap} */ + this.graphHashesWithConnections = undefined; } +} - /** @param {CleanOptions} options options */ - constructor(options = {}) { - validate(options); - this.options = { dry: false, ...options }; +class ChunkGraphChunk { + constructor() { + /** @type {SortableSet} */ + this.modules = new SortableSet(); + /** @type {Map} */ + this.entryModules = new Map(); + /** @type {SortableSet} */ + this.runtimeModules = new SortableSet(); + /** @type {Set | undefined} */ + this.fullHashModules = undefined; + /** @type {Set | undefined} */ + this.dependentHashModules = undefined; + /** @type {Set | undefined} */ + this.runtimeRequirements = undefined; + /** @type {Set} */ + this.runtimeRequirementsInTree = new Set(); } +} +class ChunkGraph { /** - * Apply the plugin - * @param {Compiler} compiler the compiler instance - * @returns {void} + * @param {ModuleGraph} moduleGraph the module graph + * @param {string | Hash} hashFunction the hash function to use */ - apply(compiler) { - const { dry, keep } = this.options; - - const keepFn = - typeof keep === "function" - ? keep - : typeof keep === "string" - ? path => path.startsWith(keep) - : typeof keep === "object" && keep.test - ? path => keep.test(path) - : () => false; - - // We assume that no external modification happens while the compiler is active - // So we can store the old assets and only diff to them to avoid fs access on - // incremental builds - let oldAssets; - - compiler.hooks.emit.tapAsync( - { - name: "CleanPlugin", - stage: 100 - }, - (compilation, callback) => { - const hooks = CleanPlugin.getCompilationHooks(compilation); - const logger = compilation.getLogger("webpack.CleanPlugin"); - const fs = compiler.outputFileSystem; - - if (!fs.readdir) { - return callback( - new Error( - "CleanPlugin: Output filesystem doesn't support listing directories (readdir)" - ) - ); - } - - const currentAssets = new Set(); - for (const asset of Object.keys(compilation.assets)) { - if (/^[A-Za-z]:\\|^\/|^\\\\/.test(asset)) continue; - let normalizedAsset; - let newNormalizedAsset = asset.replace(/\\/g, "/"); - do { - normalizedAsset = newNormalizedAsset; - newNormalizedAsset = normalizedAsset.replace( - /(^|\/)(?!\.\.)[^/]+\/\.\.\//g, - "$1" - ); - } while (newNormalizedAsset !== normalizedAsset); - if (normalizedAsset.startsWith("../")) continue; - currentAssets.add(normalizedAsset); - } - - const outputPath = compilation.getPath(compiler.outputPath, {}); - - const isKept = path => { - const result = hooks.keep.call(path); - if (result !== undefined) return result; - return keepFn(path); - }; + constructor(moduleGraph, hashFunction = "md4") { + /** @private @type {WeakMap} */ + this._modules = new WeakMap(); + /** @private @type {WeakMap} */ + this._chunks = new WeakMap(); + /** @private @type {WeakMap} */ + this._blockChunkGroups = new WeakMap(); + /** @private @type {Map} */ + this._runtimeIds = new Map(); + /** @type {ModuleGraph} */ + this.moduleGraph = moduleGraph; - const diffCallback = (err, diff) => { - if (err) { - oldAssets = undefined; - return callback(err); - } - applyDiff(fs, outputPath, dry, logger, diff, isKept, err => { - if (err) { - oldAssets = undefined; - } else { - oldAssets = currentAssets; - } - callback(err); - }); - }; + this._hashFunction = hashFunction; - if (oldAssets) { - diffCallback(null, getDiffToOldAssets(currentAssets, oldAssets)); - } else { - getDiffToFs(fs, outputPath, currentAssets, diffCallback); - } - } - ); + this._getGraphRoots = this._getGraphRoots.bind(this); } -} - -module.exports = CleanPlugin; - - -/***/ }), -/***/ 43604: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ - - - -const WebpackError = __webpack_require__(68422); - -/** @typedef {import("./Module")} Module */ - -class CodeGenerationError extends WebpackError { /** - * Create a new CodeGenerationError - * @param {Module} module related module - * @param {Error} error Original error + * @private + * @param {Module} module the module + * @returns {ChunkGraphModule} internal module */ - constructor(module, error) { - super(); - - this.name = "CodeGenerationError"; - this.error = error; - this.message = error.message; - this.details = error.stack; - this.module = module; + _getChunkGraphModule(module) { + let cgm = this._modules.get(module); + if (cgm === undefined) { + cgm = new ChunkGraphModule(); + this._modules.set(module, cgm); + } + return cgm; } -} - -module.exports = CodeGenerationError; - - -/***/ }), - -/***/ 74841: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ - - - -const { provide } = __webpack_require__(30498); -const { first } = __webpack_require__(34715); -const createHash = __webpack_require__(24123); -const { runtimeToString, RuntimeSpecMap } = __webpack_require__(19655); - -/** @typedef {import("webpack-sources").Source} Source */ -/** @typedef {import("./Module")} Module */ -/** @typedef {import("./Module").CodeGenerationResult} CodeGenerationResult */ -/** @typedef {typeof import("./util/Hash")} Hash */ -/** @typedef {import("./util/runtime").RuntimeSpec} RuntimeSpec */ -class CodeGenerationResults { /** - * @param {string | Hash} hashFunction the hash function to use + * @private + * @param {Chunk} chunk the chunk + * @returns {ChunkGraphChunk} internal chunk */ - constructor(hashFunction = "md4") { - /** @type {Map>} */ - this.map = new Map(); - this._hashFunction = hashFunction; + _getChunkGraphChunk(chunk) { + let cgc = this._chunks.get(chunk); + if (cgc === undefined) { + cgc = new ChunkGraphChunk(); + this._chunks.set(chunk, cgc); + } + return cgc; } /** - * @param {Module} module the module - * @param {RuntimeSpec} runtime runtime(s) - * @returns {CodeGenerationResult} the CodeGenerationResult + * @param {SortableSet} set the sortable Set to get the roots of + * @returns {Module[]} the graph roots */ - get(module, runtime) { - const entry = this.map.get(module); - if (entry === undefined) { - throw new Error( - `No code generation entry for ${module.identifier()} (existing entries: ${Array.from( - this.map.keys(), - m => m.identifier() - ).join(", ")})` - ); - } - if (runtime === undefined) { - if (entry.size > 1) { - const results = new Set(entry.values()); - if (results.size !== 1) { - throw new Error( - `No unique code generation entry for unspecified runtime for ${module.identifier()} (existing runtimes: ${Array.from( - entry.keys(), - r => runtimeToString(r) - ).join(", ")}). -Caller might not support runtime-dependent code generation (opt-out via optimization.usedExports: "global").` - ); - } - return first(results); - } - return entry.values().next().value; - } - const result = entry.get(runtime); - if (result === undefined) { - throw new Error( - `No code generation entry for runtime ${runtimeToString( - runtime - )} for ${module.identifier()} (existing runtimes: ${Array.from( - entry.keys(), - r => runtimeToString(r) - ).join(", ")})` - ); - } - return result; + _getGraphRoots(set) { + const { moduleGraph } = this; + return Array.from( + findGraphRoots(set, module => { + /** @type {Set} */ + const set = new Set(); + const addDependencies = module => { + for (const connection of moduleGraph.getOutgoingConnections(module)) { + if (!connection.module) continue; + const activeState = connection.getActiveState(undefined); + if (activeState === false) continue; + if (activeState === ModuleGraphConnection.TRANSITIVE_ONLY) { + addDependencies(connection.module); + continue; + } + set.add(connection.module); + } + }; + addDependencies(module); + return set; + }) + ).sort(compareModulesByIdentifier); } /** + * @param {Chunk} chunk the new chunk * @param {Module} module the module - * @param {RuntimeSpec} runtime runtime(s) - * @returns {boolean} true, when we have data for this + * @returns {void} */ - has(module, runtime) { - const entry = this.map.get(module); - if (entry === undefined) { - return false; - } - if (runtime !== undefined) { - return entry.has(runtime); - } else if (entry.size > 1) { - const results = new Set(entry.values()); - return results.size === 1; - } else { - return entry.size === 1; - } + connectChunkAndModule(chunk, module) { + const cgm = this._getChunkGraphModule(module); + const cgc = this._getChunkGraphChunk(chunk); + cgm.chunks.add(chunk); + cgc.modules.add(module); } /** + * @param {Chunk} chunk the chunk * @param {Module} module the module - * @param {RuntimeSpec} runtime runtime(s) - * @param {string} sourceType the source type - * @returns {Source} a source + * @returns {void} */ - getSource(module, runtime, sourceType) { - return this.get(module, runtime).sources.get(sourceType); + disconnectChunkAndModule(chunk, module) { + const cgm = this._getChunkGraphModule(module); + const cgc = this._getChunkGraphChunk(chunk); + cgc.modules.delete(module); + cgm.chunks.delete(chunk); } /** - * @param {Module} module the module - * @param {RuntimeSpec} runtime runtime(s) - * @returns {ReadonlySet} runtime requirements + * @param {Chunk} chunk the chunk which will be disconnected + * @returns {void} */ - getRuntimeRequirements(module, runtime) { - return this.get(module, runtime).runtimeRequirements; + disconnectChunk(chunk) { + const cgc = this._getChunkGraphChunk(chunk); + for (const module of cgc.modules) { + const cgm = this._getChunkGraphModule(module); + cgm.chunks.delete(chunk); + } + cgc.modules.clear(); + chunk.disconnectFromGroups(); + ChunkGraph.clearChunkGraphForChunk(chunk); } /** - * @param {Module} module the module - * @param {RuntimeSpec} runtime runtime(s) - * @param {string} key data key - * @returns {any} data generated by code generation + * @param {Chunk} chunk the chunk + * @param {Iterable} modules the modules + * @returns {void} */ - getData(module, runtime, key) { - const data = this.get(module, runtime).data; - return data === undefined ? undefined : data.get(key); + attachModules(chunk, modules) { + const cgc = this._getChunkGraphChunk(chunk); + for (const module of modules) { + cgc.modules.add(module); + } } /** - * @param {Module} module the module - * @param {RuntimeSpec} runtime runtime(s) - * @returns {any} hash of the code generation + * @param {Chunk} chunk the chunk + * @param {Iterable} modules the runtime modules + * @returns {void} */ - getHash(module, runtime) { - const info = this.get(module, runtime); - if (info.hash !== undefined) return info.hash; - const hash = createHash(this._hashFunction); - for (const [type, source] of info.sources) { - hash.update(type); - source.updateHash(hash); - } - if (info.runtimeRequirements) { - for (const rr of info.runtimeRequirements) hash.update(rr); + attachRuntimeModules(chunk, modules) { + const cgc = this._getChunkGraphChunk(chunk); + for (const module of modules) { + cgc.runtimeModules.add(module); } - return (info.hash = /** @type {string} */ (hash.digest("hex"))); } /** - * @param {Module} module the module - * @param {RuntimeSpec} runtime runtime(s) - * @param {CodeGenerationResult} result result from module + * @param {Chunk} chunk the chunk + * @param {Iterable} modules the modules that require a full hash * @returns {void} */ - add(module, runtime, result) { - const map = provide(this.map, module, () => new RuntimeSpecMap()); - map.set(runtime, result); + attachFullHashModules(chunk, modules) { + const cgc = this._getChunkGraphChunk(chunk); + if (cgc.fullHashModules === undefined) cgc.fullHashModules = new Set(); + for (const module of modules) { + cgc.fullHashModules.add(module); + } } -} - -module.exports = CodeGenerationResults; - - -/***/ }), - -/***/ 28151: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ - - - -const WebpackError = __webpack_require__(68422); -const makeSerializable = __webpack_require__(26522); - -/** @typedef {import("./Dependency").DependencyLocation} DependencyLocation */ -class CommentCompilationWarning extends WebpackError { /** - * - * @param {string} message warning message - * @param {DependencyLocation} loc affected lines of code + * @param {Chunk} chunk the chunk + * @param {Iterable} modules the modules that require a full hash + * @returns {void} */ - constructor(message, loc) { - super(message); - - this.name = "CommentCompilationWarning"; - - this.loc = loc; + attachDependentHashModules(chunk, modules) { + const cgc = this._getChunkGraphChunk(chunk); + if (cgc.dependentHashModules === undefined) + cgc.dependentHashModules = new Set(); + for (const module of modules) { + cgc.dependentHashModules.add(module); + } } -} - -makeSerializable( - CommentCompilationWarning, - "webpack/lib/CommentCompilationWarning" -); - -module.exports = CommentCompilationWarning; + /** + * @param {Module} oldModule the replaced module + * @param {Module} newModule the replacing module + * @returns {void} + */ + replaceModule(oldModule, newModule) { + const oldCgm = this._getChunkGraphModule(oldModule); + const newCgm = this._getChunkGraphModule(newModule); -/***/ }), - -/***/ 27847: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ + for (const chunk of oldCgm.chunks) { + const cgc = this._getChunkGraphChunk(chunk); + cgc.modules.delete(oldModule); + cgc.modules.add(newModule); + newCgm.chunks.add(chunk); + } + oldCgm.chunks.clear(); + if (oldCgm.entryInChunks !== undefined) { + if (newCgm.entryInChunks === undefined) { + newCgm.entryInChunks = new Set(); + } + for (const chunk of oldCgm.entryInChunks) { + const cgc = this._getChunkGraphChunk(chunk); + const old = cgc.entryModules.get(oldModule); + /** @type {Map} */ + const newEntryModules = new Map(); + for (const [m, cg] of cgc.entryModules) { + if (m === oldModule) { + newEntryModules.set(newModule, old); + } else { + newEntryModules.set(m, cg); + } + } + cgc.entryModules = newEntryModules; + newCgm.entryInChunks.add(chunk); + } + oldCgm.entryInChunks = undefined; + } + if (oldCgm.runtimeInChunks !== undefined) { + if (newCgm.runtimeInChunks === undefined) { + newCgm.runtimeInChunks = new Set(); + } + for (const chunk of oldCgm.runtimeInChunks) { + const cgc = this._getChunkGraphChunk(chunk); + cgc.runtimeModules.delete(/** @type {RuntimeModule} */ (oldModule)); + cgc.runtimeModules.add(/** @type {RuntimeModule} */ (newModule)); + newCgm.runtimeInChunks.add(chunk); + if ( + cgc.fullHashModules !== undefined && + cgc.fullHashModules.has(/** @type {RuntimeModule} */ (oldModule)) + ) { + cgc.fullHashModules.delete(/** @type {RuntimeModule} */ (oldModule)); + cgc.fullHashModules.add(/** @type {RuntimeModule} */ (newModule)); + } + if ( + cgc.dependentHashModules !== undefined && + cgc.dependentHashModules.has(/** @type {RuntimeModule} */ (oldModule)) + ) { + cgc.dependentHashModules.delete( + /** @type {RuntimeModule} */ (oldModule) + ); + cgc.dependentHashModules.add( + /** @type {RuntimeModule} */ (newModule) + ); + } + } + oldCgm.runtimeInChunks = undefined; + } + } -const ConstDependency = __webpack_require__(60864); + /** + * @param {Module} module the checked module + * @param {Chunk} chunk the checked chunk + * @returns {boolean} true, if the chunk contains the module + */ + isModuleInChunk(module, chunk) { + const cgc = this._getChunkGraphChunk(chunk); + return cgc.modules.has(module); + } -/** @typedef {import("./Compiler")} Compiler */ -/** @typedef {import("./javascript/JavascriptParser")} JavascriptParser */ + /** + * @param {Module} module the checked module + * @param {ChunkGroup} chunkGroup the checked chunk group + * @returns {boolean} true, if the chunk contains the module + */ + isModuleInChunkGroup(module, chunkGroup) { + for (const chunk of chunkGroup.chunks) { + if (this.isModuleInChunk(module, chunk)) return true; + } + return false; + } -const nestedWebpackRequireTag = Symbol("nested __webpack_require__"); + /** + * @param {Module} module the checked module + * @returns {boolean} true, if the module is entry of any chunk + */ + isEntryModule(module) { + const cgm = this._getChunkGraphModule(module); + return cgm.entryInChunks !== undefined; + } -class CompatibilityPlugin { /** - * Apply the plugin - * @param {Compiler} compiler the compiler instance - * @returns {void} + * @param {Module} module the module + * @returns {Iterable} iterable of chunks (do not modify) */ - apply(compiler) { - compiler.hooks.compilation.tap( - "CompatibilityPlugin", - (compilation, { normalModuleFactory }) => { - compilation.dependencyTemplates.set( - ConstDependency, - new ConstDependency.Template() - ); + getModuleChunksIterable(module) { + const cgm = this._getChunkGraphModule(module); + return cgm.chunks; + } - normalModuleFactory.hooks.parser - .for("javascript/auto") - .tap("CompatibilityPlugin", (parser, parserOptions) => { - if ( - parserOptions.browserify !== undefined && - !parserOptions.browserify - ) - return; + /** + * @param {Module} module the module + * @param {function(Chunk, Chunk): -1|0|1} sortFn sort function + * @returns {Iterable} iterable of chunks (do not modify) + */ + getOrderedModuleChunksIterable(module, sortFn) { + const cgm = this._getChunkGraphModule(module); + cgm.chunks.sortWith(sortFn); + return cgm.chunks; + } - parser.hooks.call - .for("require") - .tap("CompatibilityPlugin", expr => { - // support for browserify style require delegator: "require(o, !0)" - if (expr.arguments.length !== 2) return; - const second = parser.evaluateExpression(expr.arguments[1]); - if (!second.isBoolean()) return; - if (second.asBool() !== true) return; - const dep = new ConstDependency("require", expr.callee.range); - dep.loc = expr.loc; - if (parser.state.current.dependencies.length > 0) { - const last = - parser.state.current.dependencies[ - parser.state.current.dependencies.length - 1 - ]; - if ( - last.critical && - last.options && - last.options.request === "." && - last.userRequest === "." && - last.options.recursive - ) - parser.state.current.dependencies.pop(); - } - parser.state.module.addPresentationalDependency(dep); - return true; - }); - }); + /** + * @param {Module} module the module + * @returns {Chunk[]} array of chunks (cached, do not modify) + */ + getModuleChunks(module) { + const cgm = this._getChunkGraphModule(module); + return cgm.chunks.getFromCache(getArray); + } - /** - * @param {JavascriptParser} parser the parser - * @returns {void} - */ - const handler = parser => { - // Handle nested requires - parser.hooks.preStatement.tap("CompatibilityPlugin", statement => { - if ( - statement.type === "FunctionDeclaration" && - statement.id && - statement.id.name === "__webpack_require__" - ) { - const newName = `__nested_webpack_require_${statement.range[0]}__`; - parser.tagVariable(statement.id.name, nestedWebpackRequireTag, { - name: newName, - declaration: { - updated: false, - loc: statement.id.loc, - range: statement.id.range - } - }); - return true; - } - }); - parser.hooks.pattern - .for("__webpack_require__") - .tap("CompatibilityPlugin", pattern => { - const newName = `__nested_webpack_require_${pattern.range[0]}__`; - parser.tagVariable(pattern.name, nestedWebpackRequireTag, { - name: newName, - declaration: { - updated: false, - loc: pattern.loc, - range: pattern.range - } - }); - return true; - }); - parser.hooks.expression - .for(nestedWebpackRequireTag) - .tap("CompatibilityPlugin", expr => { - const { name, declaration } = parser.currentTagData; - if (!declaration.updated) { - const dep = new ConstDependency(name, declaration.range); - dep.loc = declaration.loc; - parser.state.module.addPresentationalDependency(dep); - declaration.updated = true; - } - const dep = new ConstDependency(name, expr.range); - dep.loc = expr.loc; - parser.state.module.addPresentationalDependency(dep); - return true; - }); + /** + * @param {Module} module the module + * @returns {number} the number of chunk which contain the module + */ + getNumberOfModuleChunks(module) { + const cgm = this._getChunkGraphModule(module); + return cgm.chunks.size; + } - // Handle hashbang - parser.hooks.program.tap( - "CompatibilityPlugin", - (program, comments) => { - if (comments.length === 0) return; - const c = comments[0]; - if (c.type === "Line" && c.range[0] === 0) { - if (parser.state.source.slice(0, 2).toString() !== "#!") return; - // this is a hashbang comment - const dep = new ConstDependency("//", 0); - dep.loc = c.loc; - parser.state.module.addPresentationalDependency(dep); - } - } - ); - }; + /** + * @param {Module} module the module + * @returns {RuntimeSpecSet} runtimes + */ + getModuleRuntimes(module) { + const cgm = this._getChunkGraphModule(module); + return cgm.chunks.getFromUnorderedCache(getModuleRuntimes); + } - normalModuleFactory.hooks.parser - .for("javascript/auto") - .tap("CompatibilityPlugin", handler); - normalModuleFactory.hooks.parser - .for("javascript/dynamic") - .tap("CompatibilityPlugin", handler); - normalModuleFactory.hooks.parser - .for("javascript/esm") - .tap("CompatibilityPlugin", handler); - } - ); + /** + * @param {Chunk} chunk the chunk + * @returns {number} the number of modules which are contained in this chunk + */ + getNumberOfChunkModules(chunk) { + const cgc = this._getChunkGraphChunk(chunk); + return cgc.modules.size; } -} -module.exports = CompatibilityPlugin; + /** + * @param {Chunk} chunk the chunk + * @returns {number} the number of full hash modules which are contained in this chunk + */ + getNumberOfChunkFullHashModules(chunk) { + const cgc = this._getChunkGraphChunk(chunk); + return cgc.fullHashModules === undefined ? 0 : cgc.fullHashModules.size; + } -/***/ }), + /** + * @param {Chunk} chunk the chunk + * @returns {Iterable} return the modules for this chunk + */ + getChunkModulesIterable(chunk) { + const cgc = this._getChunkGraphChunk(chunk); + return cgc.modules; + } -/***/ 59622: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + /** + * @param {Chunk} chunk the chunk + * @param {string} sourceType source type + * @returns {Iterable | undefined} return the modules for this chunk + */ + getChunkModulesIterableBySourceType(chunk, sourceType) { + const cgc = this._getChunkGraphChunk(chunk); + const modulesWithSourceType = cgc.modules + .getFromUnorderedCache(modulesBySourceType) + .get(sourceType); + return modulesWithSourceType; + } -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ + /** + * @param {Chunk} chunk the chunk + * @param {function(Module, Module): -1|0|1} comparator comparator function + * @returns {Iterable} return the modules for this chunk + */ + getOrderedChunkModulesIterable(chunk, comparator) { + const cgc = this._getChunkGraphChunk(chunk); + cgc.modules.sortWith(comparator); + return cgc.modules; + } + /** + * @param {Chunk} chunk the chunk + * @param {string} sourceType source type + * @param {function(Module, Module): -1|0|1} comparator comparator function + * @returns {Iterable | undefined} return the modules for this chunk + */ + getOrderedChunkModulesIterableBySourceType(chunk, sourceType, comparator) { + const cgc = this._getChunkGraphChunk(chunk); + const modulesWithSourceType = cgc.modules + .getFromUnorderedCache(modulesBySourceType) + .get(sourceType); + if (modulesWithSourceType === undefined) return undefined; + modulesWithSourceType.sortWith(comparator); + return modulesWithSourceType; + } + /** + * @param {Chunk} chunk the chunk + * @returns {Module[]} return the modules for this chunk (cached, do not modify) + */ + getChunkModules(chunk) { + const cgc = this._getChunkGraphChunk(chunk); + return cgc.modules.getFromUnorderedCache(getArray); + } -const asyncLib = __webpack_require__(36386); -const { - HookMap, - SyncHook, - SyncBailHook, - SyncWaterfallHook, - AsyncSeriesHook, - AsyncSeriesBailHook, - AsyncParallelHook -} = __webpack_require__(34718); -const util = __webpack_require__(31669); -const { CachedSource } = __webpack_require__(96192); -const { MultiItemCache } = __webpack_require__(67014); -const Chunk = __webpack_require__(65574); -const ChunkGraph = __webpack_require__(97860); -const ChunkGroup = __webpack_require__(96975); -const ChunkRenderError = __webpack_require__(80187); -const ChunkTemplate = __webpack_require__(50527); -const CodeGenerationError = __webpack_require__(43604); -const CodeGenerationResults = __webpack_require__(74841); -const Dependency = __webpack_require__(50384); -const DependencyTemplates = __webpack_require__(31002); -const Entrypoint = __webpack_require__(86695); -const ErrorHelpers = __webpack_require__(22569); -const FileSystemInfo = __webpack_require__(13679); -const { - connectChunkGroupAndChunk, - connectChunkGroupParentAndChild -} = __webpack_require__(76652); -const { - makeWebpackError, - tryRunOrWebpackError -} = __webpack_require__(89935); -const MainTemplate = __webpack_require__(30518); -const Module = __webpack_require__(85887); -const ModuleDependencyError = __webpack_require__(30549); -const ModuleDependencyWarning = __webpack_require__(61528); -const ModuleGraph = __webpack_require__(20258); -const ModuleNotFoundError = __webpack_require__(82908); -const ModuleProfile = __webpack_require__(69631); -const ModuleRestoreError = __webpack_require__(93106); -const ModuleStoreError = __webpack_require__(84521); -const ModuleTemplate = __webpack_require__(38256); -const RuntimeGlobals = __webpack_require__(49404); -const RuntimeTemplate = __webpack_require__(23974); -const Stats = __webpack_require__(87797); -const WebpackError = __webpack_require__(68422); -const buildChunkGraph = __webpack_require__(21743); -const BuildCycleError = __webpack_require__(1808); -const { Logger, LogType } = __webpack_require__(54667); -const StatsFactory = __webpack_require__(69646); -const StatsPrinter = __webpack_require__(61025); -const { equals: arrayEquals } = __webpack_require__(21537); -const AsyncQueue = __webpack_require__(55531); -const LazySet = __webpack_require__(59534); -const { provide } = __webpack_require__(30498); -const WeakTupleMap = __webpack_require__(73963); -const { cachedCleverMerge } = __webpack_require__(11217); -const { - compareLocations, - concatComparators, - compareSelect, - compareIds, - compareStringsNumeric, - compareModulesByIdentifier -} = __webpack_require__(26296); -const createHash = __webpack_require__(24123); -const { - arrayToSetDeprecation, - soonFrozenObjectDeprecation, - createFakeHook -} = __webpack_require__(2594); -const processAsyncTree = __webpack_require__(76815); -const { getRuntimeKey } = __webpack_require__(19655); -const { isSourceEqual } = __webpack_require__(4002); + /** + * @param {Chunk} chunk the chunk + * @param {function(Module, Module): -1|0|1} comparator comparator function + * @returns {Module[]} return the modules for this chunk (cached, do not modify) + */ + getOrderedChunkModules(chunk, comparator) { + const cgc = this._getChunkGraphChunk(chunk); + const arrayFunction = createOrderedArrayFunction(comparator); + return cgc.modules.getFromUnorderedCache(arrayFunction); + } -/** @template T @typedef {import("tapable").AsArray} AsArray */ -/** @typedef {import("webpack-sources").Source} Source */ -/** @typedef {import("../declarations/WebpackOptions").EntryDescriptionNormalized} EntryDescription */ -/** @typedef {import("../declarations/WebpackOptions").OutputNormalized} OutputOptions */ -/** @typedef {import("../declarations/WebpackOptions").StatsOptions} StatsOptions */ -/** @typedef {import("../declarations/WebpackOptions").WebpackPluginFunction} WebpackPluginFunction */ -/** @typedef {import("../declarations/WebpackOptions").WebpackPluginInstance} WebpackPluginInstance */ -/** @typedef {import("./AsyncDependenciesBlock")} AsyncDependenciesBlock */ -/** @typedef {import("./Cache")} Cache */ -/** @typedef {import("./CacheFacade")} CacheFacade */ -/** @typedef {import("./ChunkGroup").ChunkGroupOptions} ChunkGroupOptions */ -/** @typedef {import("./Compiler")} Compiler */ -/** @typedef {import("./Compiler").CompilationParams} CompilationParams */ -/** @typedef {import("./DependenciesBlock")} DependenciesBlock */ -/** @typedef {import("./Dependency").DependencyLocation} DependencyLocation */ -/** @typedef {import("./Dependency").ReferencedExport} ReferencedExport */ -/** @typedef {import("./DependencyTemplate")} DependencyTemplate */ -/** @typedef {import("./Entrypoint").EntryOptions} EntryOptions */ -/** @typedef {import("./Module").CodeGenerationResult} CodeGenerationResult */ -/** @typedef {import("./ModuleFactory")} ModuleFactory */ -/** @typedef {import("./ModuleFactory").ModuleFactoryCreateDataContextInfo} ModuleFactoryCreateDataContextInfo */ -/** @typedef {import("./ModuleFactory").ModuleFactoryResult} ModuleFactoryResult */ -/** @typedef {import("./RequestShortener")} RequestShortener */ -/** @typedef {import("./RuntimeModule")} RuntimeModule */ -/** @typedef {import("./Template").RenderManifestEntry} RenderManifestEntry */ -/** @typedef {import("./Template").RenderManifestOptions} RenderManifestOptions */ -/** @typedef {import("./stats/DefaultStatsFactoryPlugin").StatsAsset} StatsAsset */ -/** @typedef {import("./stats/DefaultStatsFactoryPlugin").StatsError} StatsError */ -/** @typedef {import("./stats/DefaultStatsFactoryPlugin").StatsModule} StatsModule */ -/** @typedef {import("./util/Hash")} Hash */ -/** @template T @typedef {import("./util/deprecation").FakeHook} FakeHook */ -/** @typedef {import("./util/runtime").RuntimeSpec} RuntimeSpec */ + /** + * @param {Chunk} chunk the chunk + * @param {ModuleFilterPredicate} filterFn function used to filter modules + * @param {boolean} includeAllChunks all chunks or only async chunks + * @returns {Record} chunk to module ids object + */ + getChunkModuleIdMap(chunk, filterFn, includeAllChunks = false) { + /** @type {Record} */ + const chunkModuleIdMap = Object.create(null); -/** - * @callback Callback - * @param {WebpackError=} err - * @returns {void} - */ + for (const asyncChunk of includeAllChunks + ? chunk.getAllReferencedChunks() + : chunk.getAllAsyncChunks()) { + /** @type {(string|number)[]} */ + let array; + for (const module of this.getOrderedChunkModulesIterable( + asyncChunk, + compareModulesById(this) + )) { + if (filterFn(module)) { + if (array === undefined) { + array = []; + chunkModuleIdMap[asyncChunk.id] = array; + } + const moduleId = this.getModuleId(module); + array.push(moduleId); + } + } + } -/** - * @callback ModuleCallback - * @param {WebpackError=} err - * @param {Module=} result - * @returns {void} - */ + return chunkModuleIdMap; + } -/** - * @callback ModuleFactoryResultCallback - * @param {WebpackError=} err - * @param {ModuleFactoryResult=} result - * @returns {void} - */ + /** + * @param {Chunk} chunk the chunk + * @param {ModuleFilterPredicate} filterFn function used to filter modules + * @param {number} hashLength length of the hash + * @param {boolean} includeAllChunks all chunks or only async chunks + * @returns {Record>} chunk to module id to module hash object + */ + getChunkModuleRenderedHashMap( + chunk, + filterFn, + hashLength = 0, + includeAllChunks = false + ) { + /** @type {Record>} */ + const chunkModuleHashMap = Object.create(null); -/** - * @callback ModuleOrFactoryResultCallback - * @param {WebpackError=} err - * @param {Module | ModuleFactoryResult=} result - * @returns {void} - */ - -/** - * @callback ExecuteModuleCallback - * @param {WebpackError=} err - * @param {ExecuteModuleResult=} result - * @returns {void} - */ + for (const asyncChunk of includeAllChunks + ? chunk.getAllReferencedChunks() + : chunk.getAllAsyncChunks()) { + /** @type {Record} */ + let idToHashMap; + for (const module of this.getOrderedChunkModulesIterable( + asyncChunk, + compareModulesById(this) + )) { + if (filterFn(module)) { + if (idToHashMap === undefined) { + idToHashMap = Object.create(null); + chunkModuleHashMap[asyncChunk.id] = idToHashMap; + } + const moduleId = this.getModuleId(module); + const hash = this.getRenderedModuleHash(module, asyncChunk.runtime); + idToHashMap[moduleId] = hashLength ? hash.slice(0, hashLength) : hash; + } + } + } -/** - * @callback DepBlockVarDependenciesCallback - * @param {Dependency} dependency - * @returns {any} - */ + return chunkModuleHashMap; + } -/** @typedef {new (...args: any[]) => Dependency} DepConstructor */ -/** @typedef {Record} CompilationAssets */ + /** + * @param {Chunk} chunk the chunk + * @param {ChunkFilterPredicate} filterFn function used to filter chunks + * @returns {Record} chunk map + */ + getChunkConditionMap(chunk, filterFn) { + const map = Object.create(null); + for (const c of chunk.getAllReferencedChunks()) { + map[c.id] = filterFn(c, this); + } + return map; + } -/** - * @typedef {Object} AvailableModulesChunkGroupMapping - * @property {ChunkGroup} chunkGroup - * @property {Set} availableModules - * @property {boolean} needCopy - */ + /** + * @param {Chunk} chunk the chunk + * @param {ModuleFilterPredicate} filterFn predicate function used to filter modules + * @param {ChunkFilterPredicate=} filterChunkFn predicate function used to filter chunks + * @returns {boolean} return true if module exists in graph + */ + hasModuleInGraph(chunk, filterFn, filterChunkFn) { + const queue = new Set(chunk.groupsIterable); + const chunksProcessed = new Set(); -/** - * @typedef {Object} DependenciesBlockLike - * @property {Dependency[]} dependencies - * @property {AsyncDependenciesBlock[]} blocks - */ + for (const chunkGroup of queue) { + for (const innerChunk of chunkGroup.chunks) { + if (!chunksProcessed.has(innerChunk)) { + chunksProcessed.add(innerChunk); + if (!filterChunkFn || filterChunkFn(innerChunk, this)) { + for (const module of this.getChunkModulesIterable(innerChunk)) { + if (filterFn(module)) { + return true; + } + } + } + } + } + for (const child of chunkGroup.childrenIterable) { + queue.add(child); + } + } + return false; + } -/** - * @typedef {Object} ChunkPathData - * @property {string|number} id - * @property {string=} name - * @property {string} hash - * @property {function(number): string=} hashWithLength - * @property {(Record)=} contentHash - * @property {(Record string>)=} contentHashWithLength - */ + /** + * @param {Chunk} chunkA first chunk + * @param {Chunk} chunkB second chunk + * @returns {-1|0|1} this is a comparator function like sort and returns -1, 0, or 1 based on sort order + */ + compareChunks(chunkA, chunkB) { + const cgcA = this._getChunkGraphChunk(chunkA); + const cgcB = this._getChunkGraphChunk(chunkB); + if (cgcA.modules.size > cgcB.modules.size) return -1; + if (cgcA.modules.size < cgcB.modules.size) return 1; + cgcA.modules.sortWith(compareModulesByIdentifier); + cgcB.modules.sortWith(compareModulesByIdentifier); + return compareModuleIterables(cgcA.modules, cgcB.modules); + } -/** - * @typedef {Object} ChunkHashContext - * @property {RuntimeTemplate} runtimeTemplate the runtime template - * @property {ModuleGraph} moduleGraph the module graph - * @property {ChunkGraph} chunkGraph the chunk graph - */ + /** + * @param {Chunk} chunk the chunk + * @returns {number} total size of all modules in the chunk + */ + getChunkModulesSize(chunk) { + const cgc = this._getChunkGraphChunk(chunk); + return cgc.modules.getFromUnorderedCache(getModulesSize); + } -/** - * @typedef {Object} RuntimeRequirementsContext - * @property {ChunkGraph} chunkGraph the chunk graph - * @property {CodeGenerationResults} codeGenerationResults the code generation results - */ + /** + * @param {Chunk} chunk the chunk + * @returns {Record} total sizes of all modules in the chunk by source type + */ + getChunkModulesSizes(chunk) { + const cgc = this._getChunkGraphChunk(chunk); + return cgc.modules.getFromUnorderedCache(getModulesSizes); + } -/** - * @typedef {Object} ExecuteModuleOptions - * @property {EntryOptions=} entryOptions - */ + /** + * @param {Chunk} chunk the chunk + * @returns {Module[]} root modules of the chunks (ordered by identifier) + */ + getChunkRootModules(chunk) { + const cgc = this._getChunkGraphChunk(chunk); + return cgc.modules.getFromUnorderedCache(this._getGraphRoots); + } -/** - * @typedef {Object} ExecuteModuleResult - * @property {any} exports - * @property {boolean} cacheable - * @property {Map} assets - * @property {LazySet} fileDependencies - * @property {LazySet} contextDependencies - * @property {LazySet} missingDependencies - * @property {LazySet} buildDependencies - */ + /** + * @param {Chunk} chunk the chunk + * @param {ChunkSizeOptions} options options object + * @returns {number} total size of the chunk + */ + getChunkSize(chunk, options = {}) { + const cgc = this._getChunkGraphChunk(chunk); + const modulesSize = cgc.modules.getFromUnorderedCache(getModulesSize); + const chunkOverhead = + typeof options.chunkOverhead === "number" ? options.chunkOverhead : 10000; + const entryChunkMultiplicator = + typeof options.entryChunkMultiplicator === "number" + ? options.entryChunkMultiplicator + : 10; + return ( + chunkOverhead + + modulesSize * (chunk.canBeInitial() ? entryChunkMultiplicator : 1) + ); + } -/** - * @typedef {Object} ExecuteModuleArgument - * @property {Module} module - * @property {{ id: string, exports: any, loaded: boolean }=} moduleObject - * @property {any} preparedInfo - * @property {CodeGenerationResult} codeGenerationResult - */ + /** + * @param {Chunk} chunkA chunk + * @param {Chunk} chunkB chunk + * @param {ChunkSizeOptions} options options object + * @returns {number} total size of the chunk or false if chunks can't be integrated + */ + getIntegratedChunksSize(chunkA, chunkB, options = {}) { + const cgcA = this._getChunkGraphChunk(chunkA); + const cgcB = this._getChunkGraphChunk(chunkB); + const allModules = new Set(cgcA.modules); + for (const m of cgcB.modules) allModules.add(m); + let modulesSize = getModulesSize(allModules); + const chunkOverhead = + typeof options.chunkOverhead === "number" ? options.chunkOverhead : 10000; + const entryChunkMultiplicator = + typeof options.entryChunkMultiplicator === "number" + ? options.entryChunkMultiplicator + : 10; + return ( + chunkOverhead + + modulesSize * + (chunkA.canBeInitial() || chunkB.canBeInitial() + ? entryChunkMultiplicator + : 1) + ); + } -/** - * @typedef {Object} ExecuteModuleContext - * @property {Map} assets - * @property {Chunk} chunk - * @property {ChunkGraph} chunkGraph - * @property {function(string): any=} __webpack_require__ - */ + /** + * @param {Chunk} chunkA chunk + * @param {Chunk} chunkB chunk + * @returns {boolean} true, if chunks could be integrated + */ + canChunksBeIntegrated(chunkA, chunkB) { + if (chunkA.preventIntegration || chunkB.preventIntegration) { + return false; + } -/** - * @typedef {Object} EntryData - * @property {Dependency[]} dependencies dependencies of the entrypoint that should be evaluated at startup - * @property {Dependency[]} includeDependencies dependencies of the entrypoint that should be included but not evaluated - * @property {EntryOptions} options options of the entrypoint - */ + const hasRuntimeA = chunkA.hasRuntime(); + const hasRuntimeB = chunkB.hasRuntime(); -/** - * @typedef {Object} LogEntry - * @property {string} type - * @property {any[]} args - * @property {number} time - * @property {string[]=} trace - */ + if (hasRuntimeA !== hasRuntimeB) { + if (hasRuntimeA) { + return isAvailableChunk(chunkA, chunkB); + } else if (hasRuntimeB) { + return isAvailableChunk(chunkB, chunkA); + } else { + return false; + } + } -/** - * @typedef {Object} KnownAssetInfo - * @property {boolean=} immutable true, if the asset can be long term cached forever (contains a hash) - * @property {boolean=} minimized whether the asset is minimized - * @property {string | string[]=} fullhash the value(s) of the full hash used for this asset - * @property {string | string[]=} chunkhash the value(s) of the chunk hash used for this asset - * @property {string | string[]=} modulehash the value(s) of the module hash used for this asset - * @property {string | string[]=} contenthash the value(s) of the content hash used for this asset - * @property {string=} sourceFilename when asset was created from a source file (potentially transformed), the original filename relative to compilation context - * @property {number=} size size in bytes, only set after asset has been emitted - * @property {boolean=} development true, when asset is only used for development and doesn't count towards user-facing assets - * @property {boolean=} hotModuleReplacement true, when asset ships data for updating an existing application (HMR) - * @property {boolean=} javascriptModule true, when asset is javascript and an ESM - * @property {Record=} related object of pointers to other assets, keyed by type of relation (only points from parent to child) - */ + if ( + this.getNumberOfEntryModules(chunkA) > 0 || + this.getNumberOfEntryModules(chunkB) > 0 + ) { + return false; + } -/** @typedef {KnownAssetInfo & Record} AssetInfo */ + return true; + } -/** - * @typedef {Object} Asset - * @property {string} name the filename of the asset - * @property {Source} source source of the asset - * @property {AssetInfo} info info about the asset - */ + /** + * @param {Chunk} chunkA the target chunk + * @param {Chunk} chunkB the chunk to integrate + * @returns {void} + */ + integrateChunks(chunkA, chunkB) { + // Decide for one name (deterministic) + if (chunkA.name && chunkB.name) { + if ( + this.getNumberOfEntryModules(chunkA) > 0 === + this.getNumberOfEntryModules(chunkB) > 0 + ) { + // When both chunks have entry modules or none have one, use + // shortest name + if (chunkA.name.length !== chunkB.name.length) { + chunkA.name = + chunkA.name.length < chunkB.name.length ? chunkA.name : chunkB.name; + } else { + chunkA.name = chunkA.name < chunkB.name ? chunkA.name : chunkB.name; + } + } else if (this.getNumberOfEntryModules(chunkB) > 0) { + // Pick the name of the chunk with the entry module + chunkA.name = chunkB.name; + } + } else if (chunkB.name) { + chunkA.name = chunkB.name; + } -/** - * @typedef {Object} ModulePathData - * @property {string|number} id - * @property {string} hash - * @property {function(number): string=} hashWithLength - */ + // Merge id name hints + for (const hint of chunkB.idNameHints) { + chunkA.idNameHints.add(hint); + } -/** - * @typedef {Object} PathData - * @property {ChunkGraph=} chunkGraph - * @property {string=} hash - * @property {function(number): string=} hashWithLength - * @property {(Chunk|ChunkPathData)=} chunk - * @property {(Module|ModulePathData)=} module - * @property {RuntimeSpec=} runtime - * @property {string=} filename - * @property {string=} basename - * @property {string=} query - * @property {string=} contentHashType - * @property {string=} contentHash - * @property {function(number): string=} contentHashWithLength - * @property {boolean=} noChunkHash - * @property {string=} url - */ + // Merge runtime + chunkA.runtime = mergeRuntime(chunkA.runtime, chunkB.runtime); -/** - * @typedef {Object} KnownNormalizedStatsOptions - * @property {string} context - * @property {RequestShortener} requestShortener - * @property {string} chunksSort - * @property {string} modulesSort - * @property {string} chunkModulesSort - * @property {string} nestedModulesSort - * @property {string} assetsSort - * @property {boolean} ids - * @property {boolean} cachedAssets - * @property {boolean} groupAssetsByEmitStatus - * @property {boolean} groupAssetsByPath - * @property {boolean} groupAssetsByExtension - * @property {number} assetsSpace - * @property {((value: string, asset: StatsAsset) => boolean)[]} excludeAssets - * @property {((name: string, module: StatsModule, type: "module" | "chunk" | "root-of-chunk" | "nested") => boolean)[]} excludeModules - * @property {((warning: StatsError, textValue: string) => boolean)[]} warningsFilter - * @property {boolean} cachedModules - * @property {boolean} orphanModules - * @property {boolean} dependentModules - * @property {boolean} runtimeModules - * @property {boolean} groupModulesByCacheStatus - * @property {boolean} groupModulesByLayer - * @property {boolean} groupModulesByAttributes - * @property {boolean} groupModulesByPath - * @property {boolean} groupModulesByExtension - * @property {boolean} groupModulesByType - * @property {boolean | "auto"} entrypoints - * @property {boolean} chunkGroups - * @property {boolean} chunkGroupAuxiliary - * @property {boolean} chunkGroupChildren - * @property {number} chunkGroupMaxAssets - * @property {number} modulesSpace - * @property {number} chunkModulesSpace - * @property {number} nestedModulesSpace - * @property {false|"none"|"error"|"warn"|"info"|"log"|"verbose"} logging - * @property {((value: string) => boolean)[]} loggingDebug - * @property {boolean} loggingTrace - * @property {any} _env - */ + // getChunkModules is used here to create a clone, because disconnectChunkAndModule modifies + for (const module of this.getChunkModules(chunkB)) { + this.disconnectChunkAndModule(chunkB, module); + this.connectChunkAndModule(chunkA, module); + } -/** @typedef {KnownNormalizedStatsOptions & Omit & Record} NormalizedStatsOptions */ + for (const [module, chunkGroup] of Array.from( + this.getChunkEntryModulesWithChunkGroupIterable(chunkB) + )) { + this.disconnectChunkAndEntryModule(chunkB, module); + this.connectChunkAndEntryModule(chunkA, module, chunkGroup); + } -/** - * @typedef {Object} KnownCreateStatsOptionsContext - * @property {boolean=} forToString - */ + for (const chunkGroup of chunkB.groupsIterable) { + chunkGroup.replaceChunk(chunkB, chunkA); + chunkA.addGroup(chunkGroup); + chunkB.removeGroup(chunkGroup); + } + ChunkGraph.clearChunkGraphForChunk(chunkB); + } -/** @typedef {KnownCreateStatsOptionsContext & Record} CreateStatsOptionsContext */ + /** + * @param {Chunk} chunk the chunk to upgrade + * @returns {void} + */ + upgradeDependentToFullHashModules(chunk) { + const cgc = this._getChunkGraphChunk(chunk); + if (cgc.dependentHashModules === undefined) return; + if (cgc.fullHashModules === undefined) { + cgc.fullHashModules = cgc.dependentHashModules; + } else { + for (const m of cgc.dependentHashModules) { + cgc.fullHashModules.add(m); + } + cgc.dependentHashModules = undefined; + } + } -/** @type {AssetInfo} */ -const EMPTY_ASSET_INFO = Object.freeze({}); + /** + * @param {Module} module the checked module + * @param {Chunk} chunk the checked chunk + * @returns {boolean} true, if the chunk contains the module as entry + */ + isEntryModuleInChunk(module, chunk) { + const cgc = this._getChunkGraphChunk(chunk); + return cgc.entryModules.has(module); + } -const esmDependencyCategory = "esm"; -// TODO webpack 6: remove -const deprecatedNormalModuleLoaderHook = util.deprecate( - compilation => { - return __webpack_require__(11026).getCompilationHooks(compilation).loader; - }, - "Compilation.hooks.normalModuleLoader was moved to NormalModule.getCompilationHooks(compilation).loader", - "DEP_WEBPACK_COMPILATION_NORMAL_MODULE_LOADER_HOOK" -); + /** + * @param {Chunk} chunk the new chunk + * @param {Module} module the entry module + * @param {Entrypoint=} entrypoint the chunk group which must be loaded before the module is executed + * @returns {void} + */ + connectChunkAndEntryModule(chunk, module, entrypoint) { + const cgm = this._getChunkGraphModule(module); + const cgc = this._getChunkGraphChunk(chunk); + if (cgm.entryInChunks === undefined) { + cgm.entryInChunks = new Set(); + } + cgm.entryInChunks.add(chunk); + cgc.entryModules.set(module, entrypoint); + } -// TODO webpack 6: remove -const defineRemovedModuleTemplates = moduleTemplates => { - Object.defineProperties(moduleTemplates, { - asset: { - enumerable: false, - configurable: false, - get: () => { - throw new WebpackError( - "Compilation.moduleTemplates.asset has been removed" - ); - } - }, - webassembly: { - enumerable: false, - configurable: false, - get: () => { - throw new WebpackError( - "Compilation.moduleTemplates.webassembly has been removed" - ); - } + /** + * @param {Chunk} chunk the new chunk + * @param {RuntimeModule} module the runtime module + * @returns {void} + */ + connectChunkAndRuntimeModule(chunk, module) { + const cgm = this._getChunkGraphModule(module); + const cgc = this._getChunkGraphChunk(chunk); + if (cgm.runtimeInChunks === undefined) { + cgm.runtimeInChunks = new Set(); } - }); - moduleTemplates = undefined; -}; + cgm.runtimeInChunks.add(chunk); + cgc.runtimeModules.add(module); + } -const byId = compareSelect( /** - * @param {Chunk} c chunk - * @returns {number | string} id - */ c => c.id, - compareIds -); + * @param {Chunk} chunk the new chunk + * @param {RuntimeModule} module the module that require a full hash + * @returns {void} + */ + addFullHashModuleToChunk(chunk, module) { + const cgc = this._getChunkGraphChunk(chunk); + if (cgc.fullHashModules === undefined) cgc.fullHashModules = new Set(); + cgc.fullHashModules.add(module); + } -const byNameOrHash = concatComparators( - compareSelect( - /** - * @param {Compilation} c compilation - * @returns {string} name - */ - c => c.name, - compareIds - ), - compareSelect( - /** - * @param {Compilation} c compilation - * @returns {string} hash - */ c => c.fullHash, - compareIds - ) -); - -const byMessage = compareSelect(err => `${err.message}`, compareStringsNumeric); + /** + * @param {Chunk} chunk the new chunk + * @param {RuntimeModule} module the module that require a full hash + * @returns {void} + */ + addDependentHashModuleToChunk(chunk, module) { + const cgc = this._getChunkGraphChunk(chunk); + if (cgc.dependentHashModules === undefined) + cgc.dependentHashModules = new Set(); + cgc.dependentHashModules.add(module); + } -const byModule = compareSelect( - err => (err.module && err.module.identifier()) || "", - compareStringsNumeric -); + /** + * @param {Chunk} chunk the new chunk + * @param {Module} module the entry module + * @returns {void} + */ + disconnectChunkAndEntryModule(chunk, module) { + const cgm = this._getChunkGraphModule(module); + const cgc = this._getChunkGraphChunk(chunk); + cgm.entryInChunks.delete(chunk); + if (cgm.entryInChunks.size === 0) { + cgm.entryInChunks = undefined; + } + cgc.entryModules.delete(module); + } -const byLocation = compareSelect(err => err.loc, compareLocations); + /** + * @param {Chunk} chunk the new chunk + * @param {RuntimeModule} module the runtime module + * @returns {void} + */ + disconnectChunkAndRuntimeModule(chunk, module) { + const cgm = this._getChunkGraphModule(module); + const cgc = this._getChunkGraphChunk(chunk); + cgm.runtimeInChunks.delete(chunk); + if (cgm.runtimeInChunks.size === 0) { + cgm.runtimeInChunks = undefined; + } + cgc.runtimeModules.delete(module); + } -const compareErrors = concatComparators(byModule, byLocation, byMessage); + /** + * @param {Module} module the entry module, it will no longer be entry + * @returns {void} + */ + disconnectEntryModule(module) { + const cgm = this._getChunkGraphModule(module); + for (const chunk of cgm.entryInChunks) { + const cgc = this._getChunkGraphChunk(chunk); + cgc.entryModules.delete(module); + } + cgm.entryInChunks = undefined; + } -/** @type {WeakMap} */ -const unsafeCacheDependencies = new WeakMap(); + /** + * @param {Chunk} chunk the chunk, for which all entries will be removed + * @returns {void} + */ + disconnectEntries(chunk) { + const cgc = this._getChunkGraphChunk(chunk); + for (const module of cgc.entryModules.keys()) { + const cgm = this._getChunkGraphModule(module); + cgm.entryInChunks.delete(chunk); + if (cgm.entryInChunks.size === 0) { + cgm.entryInChunks = undefined; + } + } + cgc.entryModules.clear(); + } -/** @type {WeakMap} */ -const unsafeCacheData = new WeakMap(); + /** + * @param {Chunk} chunk the chunk + * @returns {number} the amount of entry modules in chunk + */ + getNumberOfEntryModules(chunk) { + const cgc = this._getChunkGraphChunk(chunk); + return cgc.entryModules.size; + } -class Compilation { /** - * Creates an instance of Compilation. - * @param {Compiler} compiler the compiler which created the compilation - * @param {CompilationParams} params the compilation parameters + * @param {Chunk} chunk the chunk + * @returns {number} the amount of entry modules in chunk */ - constructor(compiler, params) { - this._backCompat = compiler._backCompat; + getNumberOfRuntimeModules(chunk) { + const cgc = this._getChunkGraphChunk(chunk); + return cgc.runtimeModules.size; + } - const getNormalModuleLoader = () => deprecatedNormalModuleLoaderHook(this); - /** @typedef {{ additionalAssets?: true | Function }} ProcessAssetsAdditionalOptions */ - /** @type {AsyncSeriesHook<[CompilationAssets], ProcessAssetsAdditionalOptions>} */ - const processAssetsHook = new AsyncSeriesHook(["assets"]); + /** + * @param {Chunk} chunk the chunk + * @returns {Iterable} iterable of modules (do not modify) + */ + getChunkEntryModulesIterable(chunk) { + const cgc = this._getChunkGraphChunk(chunk); + return cgc.entryModules.keys(); + } - let savedAssets = new Set(); - const popNewAssets = assets => { - let newAssets = undefined; - for (const file of Object.keys(assets)) { - if (savedAssets.has(file)) continue; - if (newAssets === undefined) { - newAssets = Object.create(null); - } - newAssets[file] = assets[file]; - savedAssets.add(file); - } - return newAssets; - }; - processAssetsHook.intercept({ - name: "Compilation", - call: () => { - savedAssets = new Set(Object.keys(this.assets)); - }, - register: tap => { - const { type, name } = tap; - const { fn, additionalAssets, ...remainingTap } = tap; - const additionalAssetsFn = - additionalAssets === true ? fn : additionalAssets; - const processedAssets = additionalAssetsFn ? new WeakSet() : undefined; - switch (type) { - case "sync": - if (additionalAssetsFn) { - this.hooks.processAdditionalAssets.tap(name, assets => { - if (processedAssets.has(this.assets)) - additionalAssetsFn(assets); - }); - } - return { - ...remainingTap, - type: "async", - fn: (assets, callback) => { - try { - fn(assets); - } catch (e) { - return callback(e); - } - if (processedAssets !== undefined) - processedAssets.add(this.assets); - const newAssets = popNewAssets(assets); - if (newAssets !== undefined) { - this.hooks.processAdditionalAssets.callAsync( - newAssets, - callback - ); - return; - } - callback(); - } - }; - case "async": - if (additionalAssetsFn) { - this.hooks.processAdditionalAssets.tapAsync( - name, - (assets, callback) => { - if (processedAssets.has(this.assets)) - return additionalAssetsFn(assets, callback); - callback(); - } - ); - } - return { - ...remainingTap, - fn: (assets, callback) => { - fn(assets, err => { - if (err) return callback(err); - if (processedAssets !== undefined) - processedAssets.add(this.assets); - const newAssets = popNewAssets(assets); - if (newAssets !== undefined) { - this.hooks.processAdditionalAssets.callAsync( - newAssets, - callback - ); - return; - } - callback(); - }); - } - }; - case "promise": - if (additionalAssetsFn) { - this.hooks.processAdditionalAssets.tapPromise(name, assets => { - if (processedAssets.has(this.assets)) - return additionalAssetsFn(assets); - return Promise.resolve(); - }); + /** + * @param {Chunk} chunk the chunk + * @returns {Iterable} iterable of chunks + */ + getChunkEntryDependentChunksIterable(chunk) { + /** @type {Set} */ + const set = new Set(); + for (const chunkGroup of chunk.groupsIterable) { + if (chunkGroup instanceof Entrypoint) { + const entrypointChunk = chunkGroup.getEntrypointChunk(); + const cgc = this._getChunkGraphChunk(entrypointChunk); + for (const chunkGroup of cgc.entryModules.values()) { + for (const c of chunkGroup.chunks) { + if (c !== chunk && c !== entrypointChunk && !c.hasRuntime()) { + set.add(c); } - return { - ...remainingTap, - fn: assets => { - const p = fn(assets); - if (!p || !p.then) return p; - return p.then(() => { - if (processedAssets !== undefined) - processedAssets.add(this.assets); - const newAssets = popNewAssets(assets); - if (newAssets !== undefined) { - return this.hooks.processAdditionalAssets.promise( - newAssets - ); - } - }); - } - }; + } } } - }); + } - /** @type {SyncHook<[CompilationAssets]>} */ - const afterProcessAssetsHook = new SyncHook(["assets"]); + return set; + } - /** - * @template T - * @param {string} name name of the hook - * @param {number} stage new stage - * @param {function(): AsArray} getArgs get old hook function args - * @param {string=} code deprecation code (not deprecated when unset) - * @returns {FakeHook, "tap" | "tapAsync" | "tapPromise" | "name">>} fake hook which redirects - */ - const createProcessAssetsHook = (name, stage, getArgs, code) => { - if (!this._backCompat && code) return undefined; - const errorMessage = - reason => `Can't automatically convert plugin using Compilation.hooks.${name} to Compilation.hooks.processAssets because ${reason}. -BREAKING CHANGE: Asset processing hooks in Compilation has been merged into a single Compilation.hooks.processAssets hook.`; - const getOptions = options => { - if (typeof options === "string") options = { name: options }; - if (options.stage) { - throw new Error(errorMessage("it's using the 'stage' option")); + /** + * @param {Chunk} chunk the chunk + * @returns {boolean} true, when it has dependent chunks + */ + hasChunkEntryDependentChunks(chunk) { + const cgc = this._getChunkGraphChunk(chunk); + for (const chunkGroup of cgc.entryModules.values()) { + for (const c of chunkGroup.chunks) { + if (c !== chunk) { + return true; } - return { ...options, stage: stage }; - }; - return createFakeHook( - { - name, - /** @type {AsyncSeriesHook["intercept"]} */ - intercept(interceptor) { - throw new Error(errorMessage("it's using 'intercept'")); - }, - /** @type {AsyncSeriesHook["tap"]} */ - tap: (options, fn) => { - processAssetsHook.tap(getOptions(options), () => fn(...getArgs())); - }, - /** @type {AsyncSeriesHook["tapAsync"]} */ - tapAsync: (options, fn) => { - processAssetsHook.tapAsync( - getOptions(options), - (assets, callback) => - /** @type {any} */ (fn)(...getArgs(), callback) - ); - }, - /** @type {AsyncSeriesHook["tapPromise"]} */ - tapPromise: (options, fn) => { - processAssetsHook.tapPromise(getOptions(options), () => - fn(...getArgs()) - ); - } - }, - `${name} is deprecated (use Compilation.hooks.processAssets instead and use one of Compilation.PROCESS_ASSETS_STAGE_* as stage option)`, - code - ); - }; - this.hooks = Object.freeze({ - /** @type {SyncHook<[Module]>} */ - buildModule: new SyncHook(["module"]), - /** @type {SyncHook<[Module]>} */ - rebuildModule: new SyncHook(["module"]), - /** @type {SyncHook<[Module, WebpackError]>} */ - failedModule: new SyncHook(["module", "error"]), - /** @type {SyncHook<[Module]>} */ - succeedModule: new SyncHook(["module"]), - /** @type {SyncHook<[Module]>} */ - stillValidModule: new SyncHook(["module"]), - - /** @type {SyncHook<[Dependency, EntryOptions]>} */ - addEntry: new SyncHook(["entry", "options"]), - /** @type {SyncHook<[Dependency, EntryOptions, Error]>} */ - failedEntry: new SyncHook(["entry", "options", "error"]), - /** @type {SyncHook<[Dependency, EntryOptions, Module]>} */ - succeedEntry: new SyncHook(["entry", "options", "module"]), + } + } + return false; + } - /** @type {SyncWaterfallHook<[(string[] | ReferencedExport)[], Dependency, RuntimeSpec]>} */ - dependencyReferencedExports: new SyncWaterfallHook([ - "referencedExports", - "dependency", - "runtime" - ]), + /** + * @param {Chunk} chunk the chunk + * @returns {Iterable} iterable of modules (do not modify) + */ + getChunkRuntimeModulesIterable(chunk) { + const cgc = this._getChunkGraphChunk(chunk); + return cgc.runtimeModules; + } - /** @type {SyncHook<[ExecuteModuleArgument, ExecuteModuleContext]>} */ - executeModule: new SyncHook(["options", "context"]), - /** @type {AsyncParallelHook<[ExecuteModuleArgument, ExecuteModuleContext]>} */ - prepareModuleExecution: new AsyncParallelHook(["options", "context"]), + /** + * @param {Chunk} chunk the chunk + * @returns {RuntimeModule[]} array of modules in order of execution + */ + getChunkRuntimeModulesInOrder(chunk) { + const cgc = this._getChunkGraphChunk(chunk); + const array = Array.from(cgc.runtimeModules); + array.sort( + concatComparators( + compareSelect( + /** + * @param {RuntimeModule} r runtime module + * @returns {number=} stage + */ + r => r.stage, + compareIds + ), + compareModulesByIdentifier + ) + ); + return array; + } - /** @type {AsyncSeriesHook<[Iterable]>} */ - finishModules: new AsyncSeriesHook(["modules"]), - /** @type {AsyncSeriesHook<[Module]>} */ - finishRebuildingModule: new AsyncSeriesHook(["module"]), - /** @type {SyncHook<[]>} */ - unseal: new SyncHook([]), - /** @type {SyncHook<[]>} */ - seal: new SyncHook([]), + /** + * @param {Chunk} chunk the chunk + * @returns {Iterable | undefined} iterable of modules (do not modify) + */ + getChunkFullHashModulesIterable(chunk) { + const cgc = this._getChunkGraphChunk(chunk); + return cgc.fullHashModules; + } - /** @type {SyncHook<[]>} */ - beforeChunks: new SyncHook([]), - /** @type {SyncHook<[Iterable]>} */ - afterChunks: new SyncHook(["chunks"]), + /** + * @param {Chunk} chunk the chunk + * @returns {ReadonlySet | undefined} set of modules (do not modify) + */ + getChunkFullHashModulesSet(chunk) { + const cgc = this._getChunkGraphChunk(chunk); + return cgc.fullHashModules; + } - /** @type {SyncBailHook<[Iterable]>} */ - optimizeDependencies: new SyncBailHook(["modules"]), - /** @type {SyncHook<[Iterable]>} */ - afterOptimizeDependencies: new SyncHook(["modules"]), + /** + * @param {Chunk} chunk the chunk + * @returns {Iterable | undefined} iterable of modules (do not modify) + */ + getChunkDependentHashModulesIterable(chunk) { + const cgc = this._getChunkGraphChunk(chunk); + return cgc.dependentHashModules; + } - /** @type {SyncHook<[]>} */ - optimize: new SyncHook([]), - /** @type {SyncBailHook<[Iterable]>} */ - optimizeModules: new SyncBailHook(["modules"]), - /** @type {SyncHook<[Iterable]>} */ - afterOptimizeModules: new SyncHook(["modules"]), + /** @typedef {[Module, Entrypoint | undefined]} EntryModuleWithChunkGroup */ - /** @type {SyncBailHook<[Iterable, ChunkGroup[]]>} */ - optimizeChunks: new SyncBailHook(["chunks", "chunkGroups"]), - /** @type {SyncHook<[Iterable, ChunkGroup[]]>} */ - afterOptimizeChunks: new SyncHook(["chunks", "chunkGroups"]), + /** + * @param {Chunk} chunk the chunk + * @returns {Iterable} iterable of modules (do not modify) + */ + getChunkEntryModulesWithChunkGroupIterable(chunk) { + const cgc = this._getChunkGraphChunk(chunk); + return cgc.entryModules; + } - /** @type {AsyncSeriesHook<[Iterable, Iterable]>} */ - optimizeTree: new AsyncSeriesHook(["chunks", "modules"]), - /** @type {SyncHook<[Iterable, Iterable]>} */ - afterOptimizeTree: new SyncHook(["chunks", "modules"]), + /** + * @param {AsyncDependenciesBlock} depBlock the async block + * @returns {ChunkGroup} the chunk group + */ + getBlockChunkGroup(depBlock) { + return this._blockChunkGroups.get(depBlock); + } - /** @type {AsyncSeriesBailHook<[Iterable, Iterable]>} */ - optimizeChunkModules: new AsyncSeriesBailHook(["chunks", "modules"]), - /** @type {SyncHook<[Iterable, Iterable]>} */ - afterOptimizeChunkModules: new SyncHook(["chunks", "modules"]), - /** @type {SyncBailHook<[], boolean>} */ - shouldRecord: new SyncBailHook([]), + /** + * @param {AsyncDependenciesBlock} depBlock the async block + * @param {ChunkGroup} chunkGroup the chunk group + * @returns {void} + */ + connectBlockAndChunkGroup(depBlock, chunkGroup) { + this._blockChunkGroups.set(depBlock, chunkGroup); + chunkGroup.addBlock(depBlock); + } - /** @type {SyncHook<[Chunk, Set, RuntimeRequirementsContext]>} */ - additionalChunkRuntimeRequirements: new SyncHook([ - "chunk", - "runtimeRequirements", - "context" - ]), - /** @type {HookMap, RuntimeRequirementsContext]>>} */ - runtimeRequirementInChunk: new HookMap( - () => new SyncBailHook(["chunk", "runtimeRequirements", "context"]) - ), - /** @type {SyncHook<[Module, Set, RuntimeRequirementsContext]>} */ - additionalModuleRuntimeRequirements: new SyncHook([ - "module", - "runtimeRequirements", - "context" - ]), - /** @type {HookMap, RuntimeRequirementsContext]>>} */ - runtimeRequirementInModule: new HookMap( - () => new SyncBailHook(["module", "runtimeRequirements", "context"]) - ), - /** @type {SyncHook<[Chunk, Set, RuntimeRequirementsContext]>} */ - additionalTreeRuntimeRequirements: new SyncHook([ - "chunk", - "runtimeRequirements", - "context" - ]), - /** @type {HookMap, RuntimeRequirementsContext]>>} */ - runtimeRequirementInTree: new HookMap( - () => new SyncBailHook(["chunk", "runtimeRequirements", "context"]) - ), + /** + * @param {ChunkGroup} chunkGroup the chunk group + * @returns {void} + */ + disconnectChunkGroup(chunkGroup) { + for (const block of chunkGroup.blocksIterable) { + this._blockChunkGroups.delete(block); + } + // TODO refactor by moving blocks list into ChunkGraph + chunkGroup._blocks.clear(); + } - /** @type {SyncHook<[RuntimeModule, Chunk]>} */ - runtimeModule: new SyncHook(["module", "chunk"]), + /** + * @param {Module} module the module + * @returns {string | number} the id of the module + */ + getModuleId(module) { + const cgm = this._getChunkGraphModule(module); + return cgm.id; + } - /** @type {SyncHook<[Iterable, any]>} */ - reviveModules: new SyncHook(["modules", "records"]), - /** @type {SyncHook<[Iterable]>} */ - beforeModuleIds: new SyncHook(["modules"]), - /** @type {SyncHook<[Iterable]>} */ - moduleIds: new SyncHook(["modules"]), - /** @type {SyncHook<[Iterable]>} */ - optimizeModuleIds: new SyncHook(["modules"]), - /** @type {SyncHook<[Iterable]>} */ - afterOptimizeModuleIds: new SyncHook(["modules"]), - - /** @type {SyncHook<[Iterable, any]>} */ - reviveChunks: new SyncHook(["chunks", "records"]), - /** @type {SyncHook<[Iterable]>} */ - beforeChunkIds: new SyncHook(["chunks"]), - /** @type {SyncHook<[Iterable]>} */ - chunkIds: new SyncHook(["chunks"]), - /** @type {SyncHook<[Iterable]>} */ - optimizeChunkIds: new SyncHook(["chunks"]), - /** @type {SyncHook<[Iterable]>} */ - afterOptimizeChunkIds: new SyncHook(["chunks"]), - - /** @type {SyncHook<[Iterable, any]>} */ - recordModules: new SyncHook(["modules", "records"]), - /** @type {SyncHook<[Iterable, any]>} */ - recordChunks: new SyncHook(["chunks", "records"]), - - /** @type {SyncHook<[Iterable]>} */ - optimizeCodeGeneration: new SyncHook(["modules"]), - - /** @type {SyncHook<[]>} */ - beforeModuleHash: new SyncHook([]), - /** @type {SyncHook<[]>} */ - afterModuleHash: new SyncHook([]), - - /** @type {SyncHook<[]>} */ - beforeCodeGeneration: new SyncHook([]), - /** @type {SyncHook<[]>} */ - afterCodeGeneration: new SyncHook([]), - - /** @type {SyncHook<[]>} */ - beforeRuntimeRequirements: new SyncHook([]), - /** @type {SyncHook<[]>} */ - afterRuntimeRequirements: new SyncHook([]), - - /** @type {SyncHook<[]>} */ - beforeHash: new SyncHook([]), - /** @type {SyncHook<[Chunk]>} */ - contentHash: new SyncHook(["chunk"]), - /** @type {SyncHook<[]>} */ - afterHash: new SyncHook([]), - /** @type {SyncHook<[any]>} */ - recordHash: new SyncHook(["records"]), - /** @type {SyncHook<[Compilation, any]>} */ - record: new SyncHook(["compilation", "records"]), - - /** @type {SyncHook<[]>} */ - beforeModuleAssets: new SyncHook([]), - /** @type {SyncBailHook<[], boolean>} */ - shouldGenerateChunkAssets: new SyncBailHook([]), - /** @type {SyncHook<[]>} */ - beforeChunkAssets: new SyncHook([]), - // TODO webpack 6 remove - /** @deprecated */ - additionalChunkAssets: createProcessAssetsHook( - "additionalChunkAssets", - Compilation.PROCESS_ASSETS_STAGE_ADDITIONAL, - () => [this.chunks], - "DEP_WEBPACK_COMPILATION_ADDITIONAL_CHUNK_ASSETS" - ), - - // TODO webpack 6 deprecate - /** @deprecated */ - additionalAssets: createProcessAssetsHook( - "additionalAssets", - Compilation.PROCESS_ASSETS_STAGE_ADDITIONAL, - () => [] - ), - // TODO webpack 6 remove - /** @deprecated */ - optimizeChunkAssets: createProcessAssetsHook( - "optimizeChunkAssets", - Compilation.PROCESS_ASSETS_STAGE_OPTIMIZE, - () => [this.chunks], - "DEP_WEBPACK_COMPILATION_OPTIMIZE_CHUNK_ASSETS" - ), - // TODO webpack 6 remove - /** @deprecated */ - afterOptimizeChunkAssets: createProcessAssetsHook( - "afterOptimizeChunkAssets", - Compilation.PROCESS_ASSETS_STAGE_OPTIMIZE + 1, - () => [this.chunks], - "DEP_WEBPACK_COMPILATION_AFTER_OPTIMIZE_CHUNK_ASSETS" - ), - // TODO webpack 6 deprecate - /** @deprecated */ - optimizeAssets: processAssetsHook, - // TODO webpack 6 deprecate - /** @deprecated */ - afterOptimizeAssets: afterProcessAssetsHook, - - processAssets: processAssetsHook, - afterProcessAssets: afterProcessAssetsHook, - /** @type {AsyncSeriesHook<[CompilationAssets]>} */ - processAdditionalAssets: new AsyncSeriesHook(["assets"]), - - /** @type {SyncBailHook<[], boolean>} */ - needAdditionalSeal: new SyncBailHook([]), - /** @type {AsyncSeriesHook<[]>} */ - afterSeal: new AsyncSeriesHook([]), - - /** @type {SyncWaterfallHook<[RenderManifestEntry[], RenderManifestOptions]>} */ - renderManifest: new SyncWaterfallHook(["result", "options"]), - - /** @type {SyncHook<[Hash]>} */ - fullHash: new SyncHook(["hash"]), - /** @type {SyncHook<[Chunk, Hash, ChunkHashContext]>} */ - chunkHash: new SyncHook(["chunk", "chunkHash", "ChunkHashContext"]), - - /** @type {SyncHook<[Module, string]>} */ - moduleAsset: new SyncHook(["module", "filename"]), - /** @type {SyncHook<[Chunk, string]>} */ - chunkAsset: new SyncHook(["chunk", "filename"]), - - /** @type {SyncWaterfallHook<[string, object, AssetInfo]>} */ - assetPath: new SyncWaterfallHook(["path", "options", "assetInfo"]), - - /** @type {SyncBailHook<[], boolean>} */ - needAdditionalPass: new SyncBailHook([]), - - /** @type {SyncHook<[Compiler, string, number]>} */ - childCompiler: new SyncHook([ - "childCompiler", - "compilerName", - "compilerIndex" - ]), - - /** @type {SyncBailHook<[string, LogEntry], true>} */ - log: new SyncBailHook(["origin", "logEntry"]), - - /** @type {SyncWaterfallHook<[WebpackError[]]>} */ - processWarnings: new SyncWaterfallHook(["warnings"]), - /** @type {SyncWaterfallHook<[WebpackError[]]>} */ - processErrors: new SyncWaterfallHook(["errors"]), - - /** @type {HookMap, CreateStatsOptionsContext]>>} */ - statsPreset: new HookMap(() => new SyncHook(["options", "context"])), - /** @type {SyncHook<[Partial, CreateStatsOptionsContext]>} */ - statsNormalize: new SyncHook(["options", "context"]), - /** @type {SyncHook<[StatsFactory, NormalizedStatsOptions]>} */ - statsFactory: new SyncHook(["statsFactory", "options"]), - /** @type {SyncHook<[StatsPrinter, NormalizedStatsOptions]>} */ - statsPrinter: new SyncHook(["statsPrinter", "options"]), - - get normalModuleLoader() { - return getNormalModuleLoader(); - } - }); - /** @type {string=} */ - this.name = undefined; - this.startTime = undefined; - this.endTime = undefined; - /** @type {Compiler} */ - this.compiler = compiler; - this.resolverFactory = compiler.resolverFactory; - this.inputFileSystem = compiler.inputFileSystem; - this.fileSystemInfo = new FileSystemInfo(this.inputFileSystem, { - managedPaths: compiler.managedPaths, - immutablePaths: compiler.immutablePaths, - logger: this.getLogger("webpack.FileSystemInfo"), - hashFunction: compiler.options.output.hashFunction - }); - if (compiler.fileTimestamps) { - this.fileSystemInfo.addFileTimestamps(compiler.fileTimestamps, true); - } - if (compiler.contextTimestamps) { - this.fileSystemInfo.addContextTimestamps( - compiler.contextTimestamps, - true - ); - } - /** @type {Map>} */ - this.valueCacheVersions = new Map(); - this.requestShortener = compiler.requestShortener; - this.compilerPath = compiler.compilerPath; - - this.logger = this.getLogger("webpack.Compilation"); - - const options = compiler.options; - this.options = options; - this.outputOptions = options && options.output; - /** @type {boolean} */ - this.bail = (options && options.bail) || false; - /** @type {boolean} */ - this.profile = (options && options.profile) || false; - - this.params = params; - this.mainTemplate = new MainTemplate(this.outputOptions, this); - this.chunkTemplate = new ChunkTemplate(this.outputOptions, this); - this.runtimeTemplate = new RuntimeTemplate( - this, - this.outputOptions, - this.requestShortener - ); - /** @type {{javascript: ModuleTemplate}} */ - this.moduleTemplates = { - javascript: new ModuleTemplate(this.runtimeTemplate, this) - }; - defineRemovedModuleTemplates(this.moduleTemplates); - - /** @type {Map> | undefined} */ - this.moduleMemCaches = undefined; - /** @type {Map> | undefined} */ - this.moduleMemCaches2 = undefined; - this.moduleGraph = new ModuleGraph(); - /** @type {ChunkGraph} */ - this.chunkGraph = undefined; - /** @type {CodeGenerationResults} */ - this.codeGenerationResults = undefined; - - /** @type {AsyncQueue} */ - this.processDependenciesQueue = new AsyncQueue({ - name: "processDependencies", - parallelism: options.parallelism || 100, - processor: this._processModuleDependencies.bind(this) - }); - /** @type {AsyncQueue} */ - this.addModuleQueue = new AsyncQueue({ - name: "addModule", - parent: this.processDependenciesQueue, - getKey: module => module.identifier(), - processor: this._addModule.bind(this) - }); - /** @type {AsyncQueue} */ - this.factorizeQueue = new AsyncQueue({ - name: "factorize", - parent: this.addModuleQueue, - processor: this._factorizeModule.bind(this) - }); - /** @type {AsyncQueue} */ - this.buildQueue = new AsyncQueue({ - name: "build", - parent: this.factorizeQueue, - processor: this._buildModule.bind(this) - }); - /** @type {AsyncQueue} */ - this.rebuildQueue = new AsyncQueue({ - name: "rebuild", - parallelism: options.parallelism || 100, - processor: this._rebuildModule.bind(this) - }); - - /** - * Modules in value are building during the build of Module in key. - * Means value blocking key from finishing. - * Needed to detect build cycles. - * @type {WeakMap>} - */ - this.creatingModuleDuringBuild = new WeakMap(); - - /** @type {Map} */ - this.entries = new Map(); - /** @type {EntryData} */ - this.globalEntry = { - dependencies: [], - includeDependencies: [], - options: { - name: undefined - } - }; - /** @type {Map} */ - this.entrypoints = new Map(); - /** @type {Entrypoint[]} */ - this.asyncEntrypoints = []; - /** @type {Set} */ - this.chunks = new Set(); - /** @type {ChunkGroup[]} */ - this.chunkGroups = []; - /** @type {Map} */ - this.namedChunkGroups = new Map(); - /** @type {Map} */ - this.namedChunks = new Map(); - /** @type {Set} */ - this.modules = new Set(); - if (this._backCompat) { - arrayToSetDeprecation(this.chunks, "Compilation.chunks"); - arrayToSetDeprecation(this.modules, "Compilation.modules"); - } - /** @private @type {Map} */ - this._modules = new Map(); - this.records = null; - /** @type {string[]} */ - this.additionalChunkAssets = []; - /** @type {CompilationAssets} */ - this.assets = {}; - /** @type {Map} */ - this.assetsInfo = new Map(); - /** @type {Map>>} */ - this._assetsRelatedIn = new Map(); - /** @type {WebpackError[]} */ - this.errors = []; - /** @type {WebpackError[]} */ - this.warnings = []; - /** @type {Compilation[]} */ - this.children = []; - /** @type {Map} */ - this.logging = new Map(); - /** @type {Map} */ - this.dependencyFactories = new Map(); - /** @type {DependencyTemplates} */ - this.dependencyTemplates = new DependencyTemplates(); - this.childrenCounters = {}; - /** @type {Set} */ - this.usedChunkIds = null; - /** @type {Set} */ - this.usedModuleIds = null; - /** @type {boolean} */ - this.needAdditionalPass = false; - /** @type {Set} */ - this._restoredUnsafeCacheModuleEntries = new Set(); - /** @type {Map} */ - this._restoredUnsafeCacheEntries = new Map(); - /** @type {WeakSet} */ - this.builtModules = new WeakSet(); - /** @type {WeakSet} */ - this.codeGeneratedModules = new WeakSet(); - /** @type {WeakSet} */ - this.buildTimeExecutedModules = new WeakSet(); - /** @private @type {Map} */ - this._rebuildingModules = new Map(); - /** @type {Set} */ - this.emittedAssets = new Set(); - /** @type {Set} */ - this.comparedForEmitAssets = new Set(); - /** @type {LazySet} */ - this.fileDependencies = new LazySet(); - /** @type {LazySet} */ - this.contextDependencies = new LazySet(); - /** @type {LazySet} */ - this.missingDependencies = new LazySet(); - /** @type {LazySet} */ - this.buildDependencies = new LazySet(); - // TODO webpack 6 remove - this.compilationDependencies = { - add: util.deprecate( - item => this.fileDependencies.add(item), - "Compilation.compilationDependencies is deprecated (used Compilation.fileDependencies instead)", - "DEP_WEBPACK_COMPILATION_COMPILATION_DEPENDENCIES" - ) - }; - - this._modulesCache = this.getCache("Compilation/modules"); - this._assetsCache = this.getCache("Compilation/assets"); - this._codeGenerationCache = this.getCache("Compilation/codeGeneration"); + /** + * @param {Module} module the module + * @param {string | number} id the id of the module + * @returns {void} + */ + setModuleId(module, id) { + const cgm = this._getChunkGraphModule(module); + cgm.id = id; + } - const unsafeCache = options.module.unsafeCache; - this._unsafeCache = !!unsafeCache; - this._unsafeCachePredicate = - typeof unsafeCache === "function" ? unsafeCache : () => true; + /** + * @param {string} runtime runtime + * @returns {string | number} the id of the runtime + */ + getRuntimeId(runtime) { + return this._runtimeIds.get(runtime); } - getStats() { - return new Stats(this); + /** + * @param {string} runtime runtime + * @param {string | number} id the id of the runtime + * @returns {void} + */ + setRuntimeId(runtime, id) { + this._runtimeIds.set(runtime, id); } /** - * @param {StatsOptions | string} optionsOrPreset stats option value - * @param {CreateStatsOptionsContext} context context - * @returns {NormalizedStatsOptions} normalized options + * @template T + * @param {Module} module the module + * @param {RuntimeSpecMap} hashes hashes data + * @param {RuntimeSpec} runtime the runtime + * @returns {T} hash */ - createStatsOptions(optionsOrPreset, context = {}) { - if ( - typeof optionsOrPreset === "boolean" || - typeof optionsOrPreset === "string" - ) { - optionsOrPreset = { preset: optionsOrPreset }; - } - if (typeof optionsOrPreset === "object" && optionsOrPreset !== null) { - // We use this method of shallow cloning this object to include - // properties in the prototype chain - /** @type {Partial} */ - const options = {}; - for (const key in optionsOrPreset) { - options[key] = optionsOrPreset[key]; - } - if (options.preset !== undefined) { - this.hooks.statsPreset.for(options.preset).call(options, context); + _getModuleHashInfo(module, hashes, runtime) { + if (!hashes) { + throw new Error( + `Module ${module.identifier()} has no hash info for runtime ${runtimeToString( + runtime + )} (hashes not set at all)` + ); + } else if (runtime === undefined) { + const hashInfoItems = new Set(hashes.values()); + if (hashInfoItems.size !== 1) { + throw new Error( + `No unique hash info entry for unspecified runtime for ${module.identifier()} (existing runtimes: ${Array.from( + hashes.keys(), + r => runtimeToString(r) + ).join(", ")}). +Caller might not support runtime-dependent code generation (opt-out via optimization.usedExports: "global").` + ); } - this.hooks.statsNormalize.call(options, context); - return /** @type {NormalizedStatsOptions} */ (options); + return first(hashInfoItems); } else { - /** @type {Partial} */ - const options = {}; - this.hooks.statsNormalize.call(options, context); - return /** @type {NormalizedStatsOptions} */ (options); + const hashInfo = hashes.get(runtime); + if (!hashInfo) { + throw new Error( + `Module ${module.identifier()} has no hash info for runtime ${runtimeToString( + runtime + )} (available runtimes ${Array.from( + hashes.keys(), + runtimeToString + ).join(", ")})` + ); + } + return hashInfo; } } - createStatsFactory(options) { - const statsFactory = new StatsFactory(); - this.hooks.statsFactory.call(statsFactory, options); - return statsFactory; + /** + * @param {Module} module the module + * @param {RuntimeSpec} runtime the runtime + * @returns {boolean} true, if the module has hashes for this runtime + */ + hasModuleHashes(module, runtime) { + const cgm = this._getChunkGraphModule(module); + const hashes = cgm.hashes; + return hashes && hashes.has(runtime); } - createStatsPrinter(options) { - const statsPrinter = new StatsPrinter(); - this.hooks.statsPrinter.call(statsPrinter, options); - return statsPrinter; + /** + * @param {Module} module the module + * @param {RuntimeSpec} runtime the runtime + * @returns {string} hash + */ + getModuleHash(module, runtime) { + const cgm = this._getChunkGraphModule(module); + const hashes = cgm.hashes; + return this._getModuleHashInfo(module, hashes, runtime).hash; } /** - * @param {string} name cache name - * @returns {CacheFacade} the cache facade instance + * @param {Module} module the module + * @param {RuntimeSpec} runtime the runtime + * @returns {string} hash */ - getCache(name) { - return this.compiler.getCache(name); + getRenderedModuleHash(module, runtime) { + const cgm = this._getChunkGraphModule(module); + const hashes = cgm.hashes; + return this._getModuleHashInfo(module, hashes, runtime).renderedHash; } /** - * @param {string | (function(): string)} name name of the logger, or function called once to get the logger name - * @returns {Logger} a logger with that name + * @param {Module} module the module + * @param {RuntimeSpec} runtime the runtime + * @param {string} hash the full hash + * @param {string} renderedHash the shortened hash for rendering + * @returns {void} */ - getLogger(name) { - if (!name) { - throw new TypeError("Compilation.getLogger(name) called without a name"); + setModuleHashes(module, runtime, hash, renderedHash) { + const cgm = this._getChunkGraphModule(module); + if (cgm.hashes === undefined) { + cgm.hashes = new RuntimeSpecMap(); } - /** @type {LogEntry[] | undefined} */ - let logEntries; - return new Logger( - (type, args) => { - if (typeof name === "function") { - name = name(); - if (!name) { - throw new TypeError( - "Compilation.getLogger(name) called with a function not returning a name" - ); - } - } - let trace; - switch (type) { - case LogType.warn: - case LogType.error: - case LogType.trace: - trace = ErrorHelpers.cutOffLoaderExecution(new Error("Trace").stack) - .split("\n") - .slice(3); - break; - } - /** @type {LogEntry} */ - const logEntry = { - time: Date.now(), - type, - args, - trace - }; - if (this.hooks.log.call(name, logEntry) === undefined) { - if (logEntry.type === LogType.profileEnd) { - // eslint-disable-next-line node/no-unsupported-features/node-builtins - if (typeof console.profileEnd === "function") { - // eslint-disable-next-line node/no-unsupported-features/node-builtins - console.profileEnd(`[${name}] ${logEntry.args[0]}`); - } - } - if (logEntries === undefined) { - logEntries = this.logging.get(name); - if (logEntries === undefined) { - logEntries = []; - this.logging.set(name, logEntries); - } - } - logEntries.push(logEntry); - if (logEntry.type === LogType.profile) { - // eslint-disable-next-line node/no-unsupported-features/node-builtins - if (typeof console.profile === "function") { - // eslint-disable-next-line node/no-unsupported-features/node-builtins - console.profile(`[${name}] ${logEntry.args[0]}`); - } - } - } - }, - childName => { - if (typeof name === "function") { - if (typeof childName === "function") { - return this.getLogger(() => { - if (typeof name === "function") { - name = name(); - if (!name) { - throw new TypeError( - "Compilation.getLogger(name) called with a function not returning a name" - ); - } - } - if (typeof childName === "function") { - childName = childName(); - if (!childName) { - throw new TypeError( - "Logger.getChildLogger(name) called with a function not returning a name" - ); - } - } - return `${name}/${childName}`; - }); - } else { - return this.getLogger(() => { - if (typeof name === "function") { - name = name(); - if (!name) { - throw new TypeError( - "Compilation.getLogger(name) called with a function not returning a name" - ); - } - } - return `${name}/${childName}`; - }); - } - } else { - if (typeof childName === "function") { - return this.getLogger(() => { - if (typeof childName === "function") { - childName = childName(); - if (!childName) { - throw new TypeError( - "Logger.getChildLogger(name) called with a function not returning a name" - ); - } - } - return `${name}/${childName}`; - }); - } else { - return this.getLogger(`${name}/${childName}`); - } - } - } - ); + cgm.hashes.set(runtime, new ModuleHashInfo(hash, renderedHash)); } /** - * @param {Module} module module to be added that was created - * @param {ModuleCallback} callback returns the module in the compilation, - * it could be the passed one (if new), or an already existing in the compilation + * @param {Module} module the module + * @param {RuntimeSpec} runtime the runtime + * @param {Set} items runtime requirements to be added (ownership of this Set is given to ChunkGraph when transferOwnership not false) + * @param {boolean} transferOwnership true: transfer ownership of the items object, false: items is immutable and shared and won't be modified * @returns {void} */ - addModule(module, callback) { - this.addModuleQueue.add(module, callback); + addModuleRuntimeRequirements( + module, + runtime, + items, + transferOwnership = true + ) { + const cgm = this._getChunkGraphModule(module); + const runtimeRequirementsMap = cgm.runtimeRequirements; + if (runtimeRequirementsMap === undefined) { + const map = new RuntimeSpecMap(); + // TODO avoid cloning item and track ownership instead + map.set(runtime, transferOwnership ? items : new Set(items)); + cgm.runtimeRequirements = map; + return; + } + runtimeRequirementsMap.update(runtime, runtimeRequirements => { + if (runtimeRequirements === undefined) { + return transferOwnership ? items : new Set(items); + } else if (!transferOwnership || runtimeRequirements.size >= items.size) { + for (const item of items) runtimeRequirements.add(item); + return runtimeRequirements; + } else { + for (const item of runtimeRequirements) items.add(item); + return items; + } + }); } /** - * @param {Module} module module to be added that was created - * @param {ModuleCallback} callback returns the module in the compilation, - * it could be the passed one (if new), or an already existing in the compilation + * @param {Chunk} chunk the chunk + * @param {Set} items runtime requirements to be added (ownership of this Set is given to ChunkGraph) * @returns {void} */ - _addModule(module, callback) { - const identifier = module.identifier(); - const alreadyAddedModule = this._modules.get(identifier); - if (alreadyAddedModule) { - return callback(null, alreadyAddedModule); - } - - const currentProfile = this.profile - ? this.moduleGraph.getProfile(module) - : undefined; - if (currentProfile !== undefined) { - currentProfile.markRestoringStart(); + addChunkRuntimeRequirements(chunk, items) { + const cgc = this._getChunkGraphChunk(chunk); + const runtimeRequirements = cgc.runtimeRequirements; + if (runtimeRequirements === undefined) { + cgc.runtimeRequirements = items; + } else if (runtimeRequirements.size >= items.size) { + for (const item of items) runtimeRequirements.add(item); + } else { + for (const item of runtimeRequirements) items.add(item); + cgc.runtimeRequirements = items; } + } - this._modulesCache.get(identifier, null, (err, cacheModule) => { - if (err) return callback(new ModuleRestoreError(module, err)); - - if (currentProfile !== undefined) { - currentProfile.markRestoringEnd(); - currentProfile.markIntegrationStart(); - } - - if (cacheModule) { - cacheModule.updateCacheModule(module); + /** + * @param {Chunk} chunk the chunk + * @param {Iterable} items runtime requirements to be added + * @returns {void} + */ + addTreeRuntimeRequirements(chunk, items) { + const cgc = this._getChunkGraphChunk(chunk); + const runtimeRequirements = cgc.runtimeRequirementsInTree; + for (const item of items) runtimeRequirements.add(item); + } - module = cacheModule; - } - this._modules.set(identifier, module); - this.modules.add(module); - if (this._backCompat) - ModuleGraph.setModuleGraphForModule(module, this.moduleGraph); - if (currentProfile !== undefined) { - currentProfile.markIntegrationEnd(); - } - callback(null, module); - }); + /** + * @param {Module} module the module + * @param {RuntimeSpec} runtime the runtime + * @returns {ReadonlySet} runtime requirements + */ + getModuleRuntimeRequirements(module, runtime) { + const cgm = this._getChunkGraphModule(module); + const runtimeRequirements = + cgm.runtimeRequirements && cgm.runtimeRequirements.get(runtime); + return runtimeRequirements === undefined ? EMPTY_SET : runtimeRequirements; } /** - * Fetches a module from a compilation by its identifier - * @param {Module} module the module provided - * @returns {Module} the module requested + * @param {Chunk} chunk the chunk + * @returns {ReadonlySet} runtime requirements */ - getModule(module) { - const identifier = module.identifier(); - return this._modules.get(identifier); + getChunkRuntimeRequirements(chunk) { + const cgc = this._getChunkGraphChunk(chunk); + const runtimeRequirements = cgc.runtimeRequirements; + return runtimeRequirements === undefined ? EMPTY_SET : runtimeRequirements; } /** - * Attempts to search for a module by its identifier - * @param {string} identifier identifier (usually path) for module - * @returns {Module|undefined} attempt to search for module and return it, else undefined + * @param {Module} module the module + * @param {RuntimeSpec} runtime the runtime + * @param {boolean} withConnections include connections + * @returns {string} hash */ - findModule(identifier) { - return this._modules.get(identifier); + getModuleGraphHash(module, runtime, withConnections = true) { + const cgm = this._getChunkGraphModule(module); + return withConnections + ? this._getModuleGraphHashWithConnections(cgm, module, runtime) + : this._getModuleGraphHashBigInt(cgm, module, runtime).toString(16); } /** - * Schedules a build of the module object - * - * @param {Module} module module to be built - * @param {ModuleCallback} callback the callback - * @returns {void} + * @param {Module} module the module + * @param {RuntimeSpec} runtime the runtime + * @param {boolean} withConnections include connections + * @returns {bigint} hash */ - buildModule(module, callback) { - this.buildQueue.add(module, callback); + getModuleGraphHashBigInt(module, runtime, withConnections = true) { + const cgm = this._getChunkGraphModule(module); + return withConnections + ? BigInt( + `0x${this._getModuleGraphHashWithConnections(cgm, module, runtime)}` + ) + : this._getModuleGraphHashBigInt(cgm, module, runtime); } /** - * Builds the module object - * - * @param {Module} module module to be built - * @param {ModuleCallback} callback the callback - * @returns {void} + * @param {ChunkGraphModule} cgm the ChunkGraphModule + * @param {Module} module the module + * @param {RuntimeSpec} runtime the runtime + * @returns {bigint} hash as big int */ - _buildModule(module, callback) { - const currentProfile = this.profile - ? this.moduleGraph.getProfile(module) - : undefined; - if (currentProfile !== undefined) { - currentProfile.markBuildingStart(); + _getModuleGraphHashBigInt(cgm, module, runtime) { + if (cgm.graphHashes === undefined) { + cgm.graphHashes = new RuntimeSpecMap(); } + const graphHash = cgm.graphHashes.provide(runtime, () => { + const hash = createHash(this._hashFunction); + hash.update(`${cgm.id}${this.moduleGraph.isAsync(module)}`); + this.moduleGraph.getExportsInfo(module).updateHash(hash, runtime); + return BigInt(`0x${/** @type {string} */ (hash.digest("hex"))}`); + }); + return graphHash; + } - module.needBuild( - { - compilation: this, - fileSystemInfo: this.fileSystemInfo, - valueCacheVersions: this.valueCacheVersions - }, - (err, needBuild) => { - if (err) return callback(err); - - if (!needBuild) { - if (currentProfile !== undefined) { - currentProfile.markBuildingEnd(); + /** + * @param {ChunkGraphModule} cgm the ChunkGraphModule + * @param {Module} module the module + * @param {RuntimeSpec} runtime the runtime + * @returns {string} hash + */ + _getModuleGraphHashWithConnections(cgm, module, runtime) { + if (cgm.graphHashesWithConnections === undefined) { + cgm.graphHashesWithConnections = new RuntimeSpecMap(); + } + const activeStateToString = state => { + if (state === false) return "F"; + if (state === true) return "T"; + if (state === ModuleGraphConnection.TRANSITIVE_ONLY) return "O"; + throw new Error("Not implemented active state"); + }; + const strict = module.buildMeta && module.buildMeta.strictHarmonyModule; + return cgm.graphHashesWithConnections.provide(runtime, () => { + const graphHash = this._getModuleGraphHashBigInt( + cgm, + module, + runtime + ).toString(16); + const connections = this.moduleGraph.getOutgoingConnections(module); + /** @type {Set} */ + const activeNamespaceModules = new Set(); + /** @type {Map>} */ + const connectedModules = new Map(); + const processConnection = (connection, stateInfo) => { + const module = connection.module; + stateInfo += module.getExportsType(this.moduleGraph, strict); + // cspell:word Tnamespace + if (stateInfo === "Tnamespace") activeNamespaceModules.add(module); + else { + const oldModule = connectedModules.get(stateInfo); + if (oldModule === undefined) { + connectedModules.set(stateInfo, module); + } else if (oldModule instanceof Set) { + oldModule.add(module); + } else if (oldModule !== module) { + connectedModules.set(stateInfo, new Set([oldModule, module])); } - this.hooks.stillValidModule.call(module); - return callback(); } - - this.hooks.buildModule.call(module); - this.builtModules.add(module); - module.build( - this.options, - this, - this.resolverFactory.get("normal", module.resolveOptions), - this.inputFileSystem, - err => { - if (currentProfile !== undefined) { - currentProfile.markBuildingEnd(); - } - if (err) { - this.hooks.failedModule.call(module, err); - return callback(err); - } - if (currentProfile !== undefined) { - currentProfile.markStoringStart(); - } - this._modulesCache.store(module.identifier(), null, module, err => { - if (currentProfile !== undefined) { - currentProfile.markStoringEnd(); - } - if (err) { - this.hooks.failedModule.call(module, err); - return callback(new ModuleStoreError(module, err)); - } - this.hooks.succeedModule.call(module); - return callback(); - }); + }; + if (runtime === undefined || typeof runtime === "string") { + for (const connection of connections) { + const state = connection.getActiveState(runtime); + if (state === false) continue; + processConnection(connection, state === true ? "T" : "O"); + } + } else { + // cspell:word Tnamespace + for (const connection of connections) { + const states = new Set(); + let stateInfo = ""; + forEachRuntime( + runtime, + runtime => { + const state = connection.getActiveState(runtime); + states.add(state); + stateInfo += activeStateToString(state) + runtime; + }, + true + ); + if (states.size === 1) { + const state = first(states); + if (state === false) continue; + stateInfo = activeStateToString(state); } + processConnection(connection, stateInfo); + } + } + // cspell:word Tnamespace + if (activeNamespaceModules.size === 0 && connectedModules.size === 0) + return graphHash; + const connectedModulesInOrder = + connectedModules.size > 1 + ? Array.from(connectedModules).sort(([a], [b]) => (a < b ? -1 : 1)) + : connectedModules; + const hash = createHash(this._hashFunction); + const addModuleToHash = module => { + hash.update( + this._getModuleGraphHashBigInt( + this._getChunkGraphModule(module), + module, + runtime + ).toString(16) ); + }; + const addModulesToHash = modules => { + let xor = ZERO_BIG_INT; + for (const m of modules) { + xor = + xor ^ + this._getModuleGraphHashBigInt( + this._getChunkGraphModule(m), + m, + runtime + ); + } + hash.update(xor.toString(16)); + }; + if (activeNamespaceModules.size === 1) + addModuleToHash(activeNamespaceModules.values().next().value); + else if (activeNamespaceModules.size > 1) + addModulesToHash(activeNamespaceModules); + for (const [stateInfo, modules] of connectedModulesInOrder) { + hash.update(stateInfo); + if (modules instanceof Set) { + addModulesToHash(modules); + } else { + addModuleToHash(modules); + } } - ); + hash.update(graphHash); + return /** @type {string} */ (hash.digest("hex")); + }); } /** - * @param {Module} module to be processed for deps - * @param {ModuleCallback} callback callback to be triggered - * @returns {void} + * @param {Chunk} chunk the chunk + * @returns {ReadonlySet} runtime requirements */ - processModuleDependencies(module, callback) { - this.processDependenciesQueue.add(module, callback); + getTreeRuntimeRequirements(chunk) { + const cgc = this._getChunkGraphChunk(chunk); + return cgc.runtimeRequirementsInTree; } + // TODO remove in webpack 6 /** - * @param {Module} module to be processed for deps - * @returns {void} + * @param {Module} module the module + * @param {string} deprecateMessage message for the deprecation message + * @param {string} deprecationCode code for the deprecation + * @returns {ChunkGraph} the chunk graph */ - processModuleDependenciesNonRecursive(module) { - const processDependenciesBlock = block => { - if (block.dependencies) { - let i = 0; - for (const dep of block.dependencies) { - this.moduleGraph.setParents(dep, block, module, i++); - } - } - if (block.blocks) { - for (const b of block.blocks) processDependenciesBlock(b); - } - }; - - processDependenciesBlock(module); + static getChunkGraphForModule(module, deprecateMessage, deprecationCode) { + const fn = deprecateGetChunkGraphForModuleMap.get(deprecateMessage); + if (fn) return fn(module); + const newFn = util.deprecate( + /** + * @param {Module} module the module + * @returns {ChunkGraph} the chunk graph + */ + module => { + const chunkGraph = chunkGraphForModuleMap.get(module); + if (!chunkGraph) + throw new Error( + deprecateMessage + + ": There was no ChunkGraph assigned to the Module for backward-compat (Use the new API)" + ); + return chunkGraph; + }, + deprecateMessage + ": Use new ChunkGraph API", + deprecationCode + ); + deprecateGetChunkGraphForModuleMap.set(deprecateMessage, newFn); + return newFn(module); } + // TODO remove in webpack 6 /** - * @param {Module} module to be processed for deps - * @param {ModuleCallback} callback callback to be triggered + * @param {Module} module the module + * @param {ChunkGraph} chunkGraph the chunk graph * @returns {void} */ - _processModuleDependencies(module, callback) { - /** @type {Array<{factory: ModuleFactory, dependencies: Dependency[], originModule: Module|null}>} */ - const sortedDependencies = []; - - /** @type {DependenciesBlock} */ - let currentBlock; - - /** @type {Map>} */ - let dependencies; - /** @type {DepConstructor} */ - let factoryCacheKey; - /** @type {ModuleFactory} */ - let factoryCacheKey2; - /** @type {Map} */ - let factoryCacheValue; - /** @type {string} */ - let listCacheKey1; - /** @type {string} */ - let listCacheKey2; - /** @type {Dependency[]} */ - let listCacheValue; + static setChunkGraphForModule(module, chunkGraph) { + chunkGraphForModuleMap.set(module, chunkGraph); + } - let inProgressSorting = 1; - let inProgressTransitive = 1; + // TODO remove in webpack 6 + /** + * @param {Module} module the module + * @returns {void} + */ + static clearChunkGraphForModule(module) { + chunkGraphForModuleMap.delete(module); + } - const onDependenciesSorted = err => { - if (err) return callback(err); + // TODO remove in webpack 6 + /** + * @param {Chunk} chunk the chunk + * @param {string} deprecateMessage message for the deprecation message + * @param {string} deprecationCode code for the deprecation + * @returns {ChunkGraph} the chunk graph + */ + static getChunkGraphForChunk(chunk, deprecateMessage, deprecationCode) { + const fn = deprecateGetChunkGraphForChunkMap.get(deprecateMessage); + if (fn) return fn(chunk); + const newFn = util.deprecate( + /** + * @param {Chunk} chunk the chunk + * @returns {ChunkGraph} the chunk graph + */ + chunk => { + const chunkGraph = chunkGraphForChunkMap.get(chunk); + if (!chunkGraph) + throw new Error( + deprecateMessage + + "There was no ChunkGraph assigned to the Chunk for backward-compat (Use the new API)" + ); + return chunkGraph; + }, + deprecateMessage + ": Use new ChunkGraph API", + deprecationCode + ); + deprecateGetChunkGraphForChunkMap.set(deprecateMessage, newFn); + return newFn(chunk); + } - // early exit without changing parallelism back and forth - if (sortedDependencies.length === 0 && inProgressTransitive === 1) { - return callback(); - } + // TODO remove in webpack 6 + /** + * @param {Chunk} chunk the chunk + * @param {ChunkGraph} chunkGraph the chunk graph + * @returns {void} + */ + static setChunkGraphForChunk(chunk, chunkGraph) { + chunkGraphForChunkMap.set(chunk, chunkGraph); + } - // This is nested so we need to allow one additional task - this.processDependenciesQueue.increaseParallelism(); + // TODO remove in webpack 6 + /** + * @param {Chunk} chunk the chunk + * @returns {void} + */ + static clearChunkGraphForChunk(chunk) { + chunkGraphForChunkMap.delete(chunk); + } +} - for (const item of sortedDependencies) { - inProgressTransitive++; - this.handleModuleCreation(item, err => { - // In V8, the Error objects keep a reference to the functions on the stack. These warnings & - // errors are created inside closures that keep a reference to the Compilation, so errors are - // leaking the Compilation object. - if (err && this.bail) { - if (inProgressTransitive <= 0) return; - inProgressTransitive = -1; - // eslint-disable-next-line no-self-assign - err.stack = err.stack; - onTransitiveTasksFinished(err); - return; - } - if (--inProgressTransitive === 0) onTransitiveTasksFinished(); - }); - } - if (--inProgressTransitive === 0) onTransitiveTasksFinished(); - }; +// TODO remove in webpack 6 +/** @type {WeakMap} */ +const chunkGraphForModuleMap = new WeakMap(); - const onTransitiveTasksFinished = err => { - if (err) return callback(err); - this.processDependenciesQueue.decreaseParallelism(); +// TODO remove in webpack 6 +/** @type {WeakMap} */ +const chunkGraphForChunkMap = new WeakMap(); - return callback(); - }; +// TODO remove in webpack 6 +/** @type {Map ChunkGraph>} */ +const deprecateGetChunkGraphForModuleMap = new Map(); - /** - * @param {Dependency} dep dependency - * @param {number} index index in block - * @returns {void} - */ - const processDependency = (dep, index) => { - this.moduleGraph.setParents(dep, currentBlock, module, index); - if (this._unsafeCache) { - try { - const unsafeCachedModule = unsafeCacheDependencies.get(dep); - if (unsafeCachedModule === null) return; - if (unsafeCachedModule !== undefined) { - if ( - this._restoredUnsafeCacheModuleEntries.has(unsafeCachedModule) - ) { - this._handleExistingModuleFromUnsafeCache( - module, - dep, - unsafeCachedModule - ); - return; - } - const identifier = unsafeCachedModule.identifier(); - const cachedModule = - this._restoredUnsafeCacheEntries.get(identifier); - if (cachedModule !== undefined) { - // update unsafe cache to new module - unsafeCacheDependencies.set(dep, cachedModule); - this._handleExistingModuleFromUnsafeCache( - module, - dep, - cachedModule - ); - return; - } - inProgressSorting++; - this._modulesCache.get(identifier, null, (err, cachedModule) => { - if (err) { - if (inProgressSorting <= 0) return; - inProgressSorting = -1; - onDependenciesSorted(err); - return; - } - try { - if (!this._restoredUnsafeCacheEntries.has(identifier)) { - const data = unsafeCacheData.get(cachedModule); - if (data === undefined) { - processDependencyForResolving(dep); - if (--inProgressSorting === 0) onDependenciesSorted(); - return; - } - if (cachedModule !== unsafeCachedModule) { - unsafeCacheDependencies.set(dep, cachedModule); - } - cachedModule.restoreFromUnsafeCache( - data, - this.params.normalModuleFactory, - this.params - ); - this._restoredUnsafeCacheEntries.set( - identifier, - cachedModule - ); - this._restoredUnsafeCacheModuleEntries.add(cachedModule); - if (!this.modules.has(cachedModule)) { - inProgressTransitive++; - this._handleNewModuleFromUnsafeCache( - module, - dep, - cachedModule, - err => { - if (err) { - if (inProgressTransitive <= 0) return; - inProgressTransitive = -1; - onTransitiveTasksFinished(err); - } - if (--inProgressTransitive === 0) - return onTransitiveTasksFinished(); - } - ); - if (--inProgressSorting === 0) onDependenciesSorted(); - return; - } - } - if (unsafeCachedModule !== cachedModule) { - unsafeCacheDependencies.set(dep, cachedModule); - } - this._handleExistingModuleFromUnsafeCache( - module, - dep, - cachedModule - ); // a3 - } catch (err) { - if (inProgressSorting <= 0) return; - inProgressSorting = -1; - onDependenciesSorted(err); - return; - } - if (--inProgressSorting === 0) onDependenciesSorted(); - }); - return; - } - } catch (e) { - console.error(e); - } - } - processDependencyForResolving(dep); - }; +// TODO remove in webpack 6 +/** @type {Map ChunkGraph>} */ +const deprecateGetChunkGraphForChunkMap = new Map(); - /** - * @param {Dependency} dep dependency - * @returns {void} - */ - const processDependencyForResolving = dep => { - const resourceIdent = dep.getResourceIdentifier(); - if (resourceIdent !== undefined && resourceIdent !== null) { - const category = dep.category; - const constructor = /** @type {DepConstructor} */ (dep.constructor); - if (factoryCacheKey === constructor) { - // Fast path 1: same constructor as prev item - if (listCacheKey1 === category && listCacheKey2 === resourceIdent) { - // Super fast path 1: also same resource - listCacheValue.push(dep); - return; - } - } else { - const factory = this.dependencyFactories.get(constructor); - if (factory === undefined) { - throw new Error( - `No module factory available for dependency type: ${constructor.name}` - ); - } - if (factoryCacheKey2 === factory) { - // Fast path 2: same factory as prev item - factoryCacheKey = constructor; - if (listCacheKey1 === category && listCacheKey2 === resourceIdent) { - // Super fast path 2: also same resource - listCacheValue.push(dep); - return; - } - } else { - // Slow path - if (factoryCacheKey2 !== undefined) { - // Archive last cache entry - if (dependencies === undefined) dependencies = new Map(); - dependencies.set(factoryCacheKey2, factoryCacheValue); - factoryCacheValue = dependencies.get(factory); - if (factoryCacheValue === undefined) { - factoryCacheValue = new Map(); - } - } else { - factoryCacheValue = new Map(); - } - factoryCacheKey = constructor; - factoryCacheKey2 = factory; - } - } - // Here webpack is using heuristic that assumes - // mostly esm dependencies would be used - // so we don't allocate extra string for them - const cacheKey = - category === esmDependencyCategory - ? resourceIdent - : `${category}${resourceIdent}`; - let list = factoryCacheValue.get(cacheKey); - if (list === undefined) { - factoryCacheValue.set(cacheKey, (list = [])); - sortedDependencies.push({ - factory: factoryCacheKey2, - dependencies: list, - originModule: module - }); - } - list.push(dep); - listCacheKey1 = category; - listCacheKey2 = resourceIdent; - listCacheValue = list; - } - }; +module.exports = ChunkGraph; - try { - /** @type {DependenciesBlock[]} */ - const queue = [module]; - do { - const block = queue.pop(); - if (block.dependencies) { - currentBlock = block; - let i = 0; - for (const dep of block.dependencies) processDependency(dep, i++); - } - if (block.blocks) { - for (const b of block.blocks) queue.push(b); - } - } while (queue.length !== 0); - } catch (e) { - return callback(e); - } - if (--inProgressSorting === 0) onDependenciesSorted(); - } +/***/ }), - _handleNewModuleFromUnsafeCache(originModule, dependency, module, callback) { - const moduleGraph = this.moduleGraph; +/***/ 96975: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - moduleGraph.setResolvedModule(originModule, dependency, module); +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ - moduleGraph.setIssuerIfUnset( - module, - originModule !== undefined ? originModule : null - ); - this._modules.set(module.identifier(), module); - this.modules.add(module); - if (this._backCompat) - ModuleGraph.setModuleGraphForModule(module, this.moduleGraph); - this._handleModuleBuildAndDependencies( - originModule, - module, - true, - callback - ); - } +const util = __webpack_require__(31669); +const SortableSet = __webpack_require__(67563); +const { + compareLocations, + compareChunks, + compareIterables +} = __webpack_require__(26296); - _handleExistingModuleFromUnsafeCache(originModule, dependency, module) { - const moduleGraph = this.moduleGraph; +/** @typedef {import("./AsyncDependenciesBlock")} AsyncDependenciesBlock */ +/** @typedef {import("./Chunk")} Chunk */ +/** @typedef {import("./ChunkGraph")} ChunkGraph */ +/** @typedef {import("./Dependency").DependencyLocation} DependencyLocation */ +/** @typedef {import("./Entrypoint")} Entrypoint */ +/** @typedef {import("./Module")} Module */ +/** @typedef {import("./ModuleGraph")} ModuleGraph */ - moduleGraph.setResolvedModule(originModule, dependency, module); - } +/** @typedef {{id: number}} HasId */ +/** @typedef {{module: Module, loc: DependencyLocation, request: string}} OriginRecord */ + +/** + * @typedef {Object} RawChunkGroupOptions + * @property {number=} preloadOrder + * @property {number=} prefetchOrder + */ + +/** @typedef {RawChunkGroupOptions & { name?: string }} ChunkGroupOptions */ + +let debugId = 5000; + +/** + * @template T + * @param {SortableSet} set set to convert to array. + * @returns {T[]} the array format of existing set + */ +const getArray = set => Array.from(set); + +/** + * A convenience method used to sort chunks based on their id's + * @param {ChunkGroup} a first sorting comparator + * @param {ChunkGroup} b second sorting comparator + * @returns {1|0|-1} a sorting index to determine order + */ +const sortById = (a, b) => { + if (a.id < b.id) return -1; + if (b.id < a.id) return 1; + return 0; +}; + +/** + * @param {OriginRecord} a the first comparator in sort + * @param {OriginRecord} b the second comparator in sort + * @returns {1|-1|0} returns sorting order as index + */ +const sortOrigin = (a, b) => { + const aIdent = a.module ? a.module.identifier() : ""; + const bIdent = b.module ? b.module.identifier() : ""; + if (aIdent < bIdent) return -1; + if (aIdent > bIdent) return 1; + return compareLocations(a.loc, b.loc); +}; +class ChunkGroup { /** - * @typedef {Object} HandleModuleCreationOptions - * @property {ModuleFactory} factory - * @property {Dependency[]} dependencies - * @property {Module | null} originModule - * @property {Partial=} contextInfo - * @property {string=} context - * @property {boolean=} recursive recurse into dependencies of the created module - * @property {boolean=} connectOrigin connect the resolved module with the origin module + * Creates an instance of ChunkGroup. + * @param {string|ChunkGroupOptions=} options chunk group options passed to chunkGroup */ + constructor(options) { + if (typeof options === "string") { + options = { name: options }; + } else if (!options) { + options = { name: undefined }; + } + /** @type {number} */ + this.groupDebugId = debugId++; + this.options = options; + /** @type {SortableSet} */ + this._children = new SortableSet(undefined, sortById); + /** @type {SortableSet} */ + this._parents = new SortableSet(undefined, sortById); + /** @type {SortableSet} */ + this._asyncEntrypoints = new SortableSet(undefined, sortById); + this._blocks = new SortableSet(); + /** @type {Chunk[]} */ + this.chunks = []; + /** @type {OriginRecord[]} */ + this.origins = []; + /** Indices in top-down order */ + /** @private @type {Map} */ + this._modulePreOrderIndices = new Map(); + /** Indices in bottom-up order */ + /** @private @type {Map} */ + this._modulePostOrderIndices = new Map(); + /** @type {number} */ + this.index = undefined; + } /** - * @param {HandleModuleCreationOptions} options options object - * @param {ModuleCallback} callback callback + * when a new chunk is added to a chunkGroup, addingOptions will occur. + * @param {ChunkGroupOptions} options the chunkGroup options passed to addOptions * @returns {void} */ - handleModuleCreation( - { - factory, - dependencies, - originModule, - contextInfo, - context, - recursive = true, - connectOrigin = recursive - }, - callback - ) { - const moduleGraph = this.moduleGraph; - - const currentProfile = this.profile ? new ModuleProfile() : undefined; - - this.factorizeModule( - { - currentProfile, - factory, - dependencies, - factoryResult: true, - originModule, - contextInfo, - context - }, - (err, factoryResult) => { - const applyFactoryResultDependencies = () => { - const { fileDependencies, contextDependencies, missingDependencies } = - factoryResult; - if (fileDependencies) { - this.fileDependencies.addAll(fileDependencies); - } - if (contextDependencies) { - this.contextDependencies.addAll(contextDependencies); - } - if (missingDependencies) { - this.missingDependencies.addAll(missingDependencies); - } - }; - if (err) { - if (factoryResult) applyFactoryResultDependencies(); - if (dependencies.every(d => d.optional)) { - this.warnings.push(err); - return callback(); - } else { - this.errors.push(err); - return callback(err); - } + addOptions(options) { + for (const key of Object.keys(options)) { + if (this.options[key] === undefined) { + this.options[key] = options[key]; + } else if (this.options[key] !== options[key]) { + if (key.endsWith("Order")) { + this.options[key] = Math.max(this.options[key], options[key]); + } else { + throw new Error( + `ChunkGroup.addOptions: No option merge strategy for ${key}` + ); } + } + } + } - const newModule = factoryResult.module; - - if (!newModule) { - applyFactoryResultDependencies(); - return callback(); - } + /** + * returns the name of current ChunkGroup + * @returns {string|undefined} returns the ChunkGroup name + */ + get name() { + return this.options.name; + } - if (currentProfile !== undefined) { - moduleGraph.setProfile(newModule, currentProfile); - } + /** + * sets a new name for current ChunkGroup + * @param {string} value the new name for ChunkGroup + * @returns {void} + */ + set name(value) { + this.options.name = value; + } - this.addModule(newModule, (err, module) => { - if (err) { - applyFactoryResultDependencies(); - if (!err.module) { - err.module = module; - } - this.errors.push(err); + /* istanbul ignore next */ + /** + * get a uniqueId for ChunkGroup, made up of its member Chunk debugId's + * @returns {string} a unique concatenation of chunk debugId's + */ + get debugId() { + return Array.from(this.chunks, x => x.debugId).join("+"); + } - return callback(err); - } + /** + * get a unique id for ChunkGroup, made up of its member Chunk id's + * @returns {string} a unique concatenation of chunk ids + */ + get id() { + return Array.from(this.chunks, x => x.id).join("+"); + } - if ( - this._unsafeCache && - factoryResult.cacheable !== false && - /** @type {any} */ (module).restoreFromUnsafeCache && - this._unsafeCachePredicate(module) - ) { - const unsafeCacheableModule = - /** @type {Module & { restoreFromUnsafeCache: Function }} */ ( - module - ); - for (let i = 0; i < dependencies.length; i++) { - const dependency = dependencies[i]; - moduleGraph.setResolvedModule( - connectOrigin ? originModule : null, - dependency, - unsafeCacheableModule - ); - unsafeCacheDependencies.set(dependency, unsafeCacheableModule); - } - if (!unsafeCacheData.has(unsafeCacheableModule)) { - unsafeCacheData.set( - unsafeCacheableModule, - unsafeCacheableModule.getUnsafeCacheData() - ); - } - } else { - applyFactoryResultDependencies(); - for (let i = 0; i < dependencies.length; i++) { - const dependency = dependencies[i]; - moduleGraph.setResolvedModule( - connectOrigin ? originModule : null, - dependency, - module - ); - } - } + /** + * Performs an unshift of a specific chunk + * @param {Chunk} chunk chunk being unshifted + * @returns {boolean} returns true if attempted chunk shift is accepted + */ + unshiftChunk(chunk) { + const oldIdx = this.chunks.indexOf(chunk); + if (oldIdx > 0) { + this.chunks.splice(oldIdx, 1); + this.chunks.unshift(chunk); + } else if (oldIdx < 0) { + this.chunks.unshift(chunk); + return true; + } + return false; + } - moduleGraph.setIssuerIfUnset( - module, - originModule !== undefined ? originModule : null - ); - if (module !== newModule) { - if (currentProfile !== undefined) { - const otherProfile = moduleGraph.getProfile(module); - if (otherProfile !== undefined) { - currentProfile.mergeInto(otherProfile); - } else { - moduleGraph.setProfile(module, currentProfile); - } - } - } + /** + * inserts a chunk before another existing chunk in group + * @param {Chunk} chunk Chunk being inserted + * @param {Chunk} before Placeholder/target chunk marking new chunk insertion point + * @returns {boolean} return true if insertion was successful + */ + insertChunk(chunk, before) { + const oldIdx = this.chunks.indexOf(chunk); + const idx = this.chunks.indexOf(before); + if (idx < 0) { + throw new Error("before chunk not found"); + } + if (oldIdx >= 0 && oldIdx > idx) { + this.chunks.splice(oldIdx, 1); + this.chunks.splice(idx, 0, chunk); + } else if (oldIdx < 0) { + this.chunks.splice(idx, 0, chunk); + return true; + } + return false; + } - this._handleModuleBuildAndDependencies( - originModule, - module, - recursive, - callback - ); - }); - } - ); + /** + * add a chunk into ChunkGroup. Is pushed on or prepended + * @param {Chunk} chunk chunk being pushed into ChunkGroupS + * @returns {boolean} returns true if chunk addition was successful. + */ + pushChunk(chunk) { + const oldIdx = this.chunks.indexOf(chunk); + if (oldIdx >= 0) { + return false; + } + this.chunks.push(chunk); + return true; } - _handleModuleBuildAndDependencies(originModule, module, recursive, callback) { - // Check for cycles when build is trigger inside another build - let creatingModuleDuringBuildSet = undefined; - if (!recursive && this.buildQueue.isProcessing(originModule)) { - // Track build dependency - creatingModuleDuringBuildSet = - this.creatingModuleDuringBuild.get(originModule); - if (creatingModuleDuringBuildSet === undefined) { - creatingModuleDuringBuildSet = new Set(); - this.creatingModuleDuringBuild.set( - originModule, - creatingModuleDuringBuildSet - ); - } - creatingModuleDuringBuildSet.add(module); + /** + * @param {Chunk} oldChunk chunk to be replaced + * @param {Chunk} newChunk New chunk that will be replaced with + * @returns {boolean} returns true if the replacement was successful + */ + replaceChunk(oldChunk, newChunk) { + const oldIdx = this.chunks.indexOf(oldChunk); + if (oldIdx < 0) return false; + const newIdx = this.chunks.indexOf(newChunk); + if (newIdx < 0) { + this.chunks[oldIdx] = newChunk; + return true; + } + if (newIdx < oldIdx) { + this.chunks.splice(oldIdx, 1); + return true; + } else if (newIdx !== oldIdx) { + this.chunks[oldIdx] = newChunk; + this.chunks.splice(newIdx, 1); + return true; + } + } - // When building is blocked by another module - // search for a cycle, cancel the cycle by throwing - // an error (otherwise this would deadlock) - const blockReasons = this.creatingModuleDuringBuild.get(module); - if (blockReasons !== undefined) { - const set = new Set(blockReasons); - for (const item of set) { - const blockReasons = this.creatingModuleDuringBuild.get(item); - if (blockReasons !== undefined) { - for (const m of blockReasons) { - if (m === module) { - return callback(new BuildCycleError(module)); - } - set.add(m); - } - } - } - } + /** + * @param {Chunk} chunk chunk to remove + * @returns {boolean} returns true if chunk was removed + */ + removeChunk(chunk) { + const idx = this.chunks.indexOf(chunk); + if (idx >= 0) { + this.chunks.splice(idx, 1); + return true; } + return false; + } - this.buildModule(module, err => { - if (creatingModuleDuringBuildSet !== undefined) { - creatingModuleDuringBuildSet.delete(module); - } - if (err) { - if (!err.module) { - err.module = module; - } - this.errors.push(err); + /** + * @returns {boolean} true, when this chunk group will be loaded on initial page load + */ + isInitial() { + return false; + } - return callback(err); - } + /** + * @param {ChunkGroup} group chunk group to add + * @returns {boolean} returns true if chunk group was added + */ + addChild(group) { + const size = this._children.size; + this._children.add(group); + return size !== this._children.size; + } - if (!recursive) { - this.processModuleDependenciesNonRecursive(module); - callback(null, module); - return; - } + /** + * @returns {ChunkGroup[]} returns the children of this group + */ + getChildren() { + return this._children.getFromCache(getArray); + } - // This avoids deadlocks for circular dependencies - if (this.processDependenciesQueue.isProcessing(module)) { - return callback(); - } + getNumberOfChildren() { + return this._children.size; + } - this.processModuleDependencies(module, err => { - if (err) { - return callback(err); - } - callback(null, module); - }); - }); + get childrenIterable() { + return this._children; } /** - * @param {FactorizeModuleOptions} options options object - * @param {ModuleOrFactoryResultCallback} callback callback - * @returns {void} + * @param {ChunkGroup} group the chunk group to remove + * @returns {boolean} returns true if the chunk group was removed */ - _factorizeModule( - { - currentProfile, - factory, - dependencies, - originModule, - factoryResult, - contextInfo, - context - }, - callback - ) { - if (currentProfile !== undefined) { - currentProfile.markFactoryStart(); + removeChild(group) { + if (!this._children.has(group)) { + return false; } - factory.create( - { - contextInfo: { - issuer: originModule ? originModule.nameForCondition() : "", - issuerLayer: originModule ? originModule.layer : null, - compiler: this.compiler.name, - ...contextInfo - }, - resolveOptions: originModule ? originModule.resolveOptions : undefined, - context: context - ? context - : originModule - ? originModule.context - : this.compiler.context, - dependencies: dependencies - }, - (err, result) => { - if (result) { - // TODO webpack 6: remove - // For backward-compat - if (result.module === undefined && result instanceof Module) { - result = { - module: result - }; - } - if (!factoryResult) { - const { - fileDependencies, - contextDependencies, - missingDependencies - } = result; - if (fileDependencies) { - this.fileDependencies.addAll(fileDependencies); - } - if (contextDependencies) { - this.contextDependencies.addAll(contextDependencies); - } - if (missingDependencies) { - this.missingDependencies.addAll(missingDependencies); - } - } - } - if (err) { - const notFoundError = new ModuleNotFoundError( - originModule, - err, - dependencies.map(d => d.loc).filter(Boolean)[0] - ); - return callback(notFoundError, factoryResult ? result : undefined); - } - if (!result) { - return callback(); - } - - if (currentProfile !== undefined) { - currentProfile.markFactoryEnd(); - } - callback(null, factoryResult ? result : result.module); - } - ); + this._children.delete(group); + group.removeParent(this); + return true; } /** - * @param {string} context context string path - * @param {Dependency} dependency dependency used to create Module chain - * @param {ModuleCallback} callback callback for when module chain is complete - * @returns {void} will throw if dependency instance is not a valid Dependency + * @param {ChunkGroup} parentChunk the parent group to be added into + * @returns {boolean} returns true if this chunk group was added to the parent group */ - addModuleChain(context, dependency, callback) { - return this.addModuleTree({ context, dependency }, callback); + addParent(parentChunk) { + if (!this._parents.has(parentChunk)) { + this._parents.add(parentChunk); + return true; + } + return false; } /** - * @param {Object} options options - * @param {string} options.context context string path - * @param {Dependency} options.dependency dependency used to create Module chain - * @param {Partial=} options.contextInfo additional context info for the root module - * @param {ModuleCallback} callback callback for when module chain is complete - * @returns {void} will throw if dependency instance is not a valid Dependency + * @returns {ChunkGroup[]} returns the parents of this group */ - addModuleTree({ context, dependency, contextInfo }, callback) { - if ( - typeof dependency !== "object" || - dependency === null || - !dependency.constructor - ) { - return callback( - new WebpackError("Parameter 'dependency' must be a Dependency") - ); - } - const Dep = /** @type {DepConstructor} */ (dependency.constructor); - const moduleFactory = this.dependencyFactories.get(Dep); - if (!moduleFactory) { - return callback( - new WebpackError( - `No dependency factory available for this dependency type: ${dependency.constructor.name}` - ) - ); - } + getParents() { + return this._parents.getFromCache(getArray); + } - this.handleModuleCreation( - { - factory: moduleFactory, - dependencies: [dependency], - originModule: null, - contextInfo, - context - }, - (err, result) => { - if (err && this.bail) { - callback(err); - this.buildQueue.stop(); - this.rebuildQueue.stop(); - this.processDependenciesQueue.stop(); - this.factorizeQueue.stop(); - } else if (!err && result) { - callback(null, result); - } else { - callback(); - } - } - ); + getNumberOfParents() { + return this._parents.size; } /** - * @param {string} context context path for entry - * @param {Dependency} entry entry dependency that should be followed - * @param {string | EntryOptions} optionsOrName options or deprecated name of entry - * @param {ModuleCallback} callback callback function - * @returns {void} returns + * @param {ChunkGroup} parent the parent group + * @returns {boolean} returns true if the parent group contains this group */ - addEntry(context, entry, optionsOrName, callback) { - // TODO webpack 6 remove - const options = - typeof optionsOrName === "object" - ? optionsOrName - : { name: optionsOrName }; + hasParent(parent) { + return this._parents.has(parent); + } - this._addEntryItem(context, entry, "dependencies", options, callback); + get parentsIterable() { + return this._parents; } /** - * @param {string} context context path for entry - * @param {Dependency} dependency dependency that should be followed - * @param {EntryOptions} options options - * @param {ModuleCallback} callback callback function - * @returns {void} returns + * @param {ChunkGroup} chunkGroup the parent group + * @returns {boolean} returns true if this group has been removed from the parent */ - addInclude(context, dependency, options, callback) { - this._addEntryItem( - context, - dependency, - "includeDependencies", - options, - callback - ); + removeParent(chunkGroup) { + if (this._parents.delete(chunkGroup)) { + chunkGroup.removeChild(this); + return true; + } + return false; } /** - * @param {string} context context path for entry - * @param {Dependency} entry entry dependency that should be followed - * @param {"dependencies" | "includeDependencies"} target type of entry - * @param {EntryOptions} options options - * @param {ModuleCallback} callback callback function - * @returns {void} returns + * @param {Entrypoint} entrypoint entrypoint to add + * @returns {boolean} returns true if entrypoint was added */ - _addEntryItem(context, entry, target, options, callback) { - const { name } = options; - let entryData = - name !== undefined ? this.entries.get(name) : this.globalEntry; - if (entryData === undefined) { - entryData = { - dependencies: [], - includeDependencies: [], - options: { - name: undefined, - ...options - } - }; - entryData[target].push(entry); - this.entries.set(name, entryData); - } else { - entryData[target].push(entry); - for (const key of Object.keys(options)) { - if (options[key] === undefined) continue; - if (entryData.options[key] === options[key]) continue; - if ( - Array.isArray(entryData.options[key]) && - Array.isArray(options[key]) && - arrayEquals(entryData.options[key], options[key]) - ) { - continue; - } - if (entryData.options[key] === undefined) { - entryData.options[key] = options[key]; - } else { - return callback( - new WebpackError( - `Conflicting entry option ${key} = ${entryData.options[key]} vs ${options[key]}` - ) - ); - } - } - } - - this.hooks.addEntry.call(entry, options); + addAsyncEntrypoint(entrypoint) { + const size = this._asyncEntrypoints.size; + this._asyncEntrypoints.add(entrypoint); + return size !== this._asyncEntrypoints.size; + } - this.addModuleTree( - { - context, - dependency: entry, - contextInfo: entryData.options.layer - ? { issuerLayer: entryData.options.layer } - : undefined - }, - (err, module) => { - if (err) { - this.hooks.failedEntry.call(entry, options, err); - return callback(err); - } - this.hooks.succeedEntry.call(entry, options, module); - return callback(null, module); - } - ); + get asyncEntrypointsIterable() { + return this._asyncEntrypoints; } /** - * @param {Module} module module to be rebuilt - * @param {ModuleCallback} callback callback when module finishes rebuilding - * @returns {void} + * @returns {Array} an array containing the blocks */ - rebuildModule(module, callback) { - this.rebuildQueue.add(module, callback); + getBlocks() { + return this._blocks.getFromCache(getArray); + } + + getNumberOfBlocks() { + return this._blocks.size; + } + + hasBlock(block) { + return this._blocks.has(block); } /** - * @param {Module} module module to be rebuilt - * @param {ModuleCallback} callback callback when module finishes rebuilding - * @returns {void} + * @returns {Iterable} blocks */ - _rebuildModule(module, callback) { - this.hooks.rebuildModule.call(module); - const oldDependencies = module.dependencies.slice(); - const oldBlocks = module.blocks.slice(); - module.invalidateBuild(); - this.buildQueue.invalidate(module); - this.buildModule(module, err => { - if (err) { - return this.hooks.finishRebuildingModule.callAsync(module, err2 => { - if (err2) { - callback( - makeWebpackError(err2, "Compilation.hooks.finishRebuildingModule") - ); - return; - } - callback(err); - }); - } - - this.processDependenciesQueue.invalidate(module); - this.moduleGraph.unfreeze(); - this.processModuleDependencies(module, err => { - if (err) return callback(err); - this.removeReasonsOfDependencyBlock(module, { - dependencies: oldDependencies, - blocks: oldBlocks - }); - this.hooks.finishRebuildingModule.callAsync(module, err2 => { - if (err2) { - callback( - makeWebpackError(err2, "Compilation.hooks.finishRebuildingModule") - ); - return; - } - callback(null, module); - }); - }); - }); + get blocksIterable() { + return this._blocks; } - _computeAffectedModules(modules) { - const moduleMemCacheCache = this.compiler.moduleMemCaches; - if (!moduleMemCacheCache) return; - if (!this.moduleMemCaches) { - this.moduleMemCaches = new Map(); - this.moduleGraph.setModuleMemCaches(this.moduleMemCaches); + /** + * @param {AsyncDependenciesBlock} block a block + * @returns {boolean} false, if block was already added + */ + addBlock(block) { + if (!this._blocks.has(block)) { + this._blocks.add(block); + return true; } - const { moduleGraph, moduleMemCaches } = this; - const affectedModules = new Set(); - const infectedModules = new Set(); - let statNew = 0; - let statChanged = 0; - let statUnchanged = 0; - let statReferencesChanged = 0; - let statWithoutBuild = 0; + return false; + } - const computeReferences = module => { - /** @type {WeakMap} */ - let references = undefined; - for (const connection of moduleGraph.getOutgoingConnections(module)) { - const d = connection.dependency; - const m = connection.module; - if (!d || !m || unsafeCacheDependencies.has(d)) continue; - if (references === undefined) references = new WeakMap(); - references.set(d, m); - } - return references; - }; + /** + * @param {Module} module origin module + * @param {DependencyLocation} loc location of the reference in the origin module + * @param {string} request request name of the reference + * @returns {void} + */ + addOrigin(module, loc, request) { + this.origins.push({ + module, + loc, + request + }); + } - /** - * @param {Module} module the module - * @param {WeakMap} references references - * @returns {boolean} true, when the references differ - */ - const compareReferences = (module, references) => { - if (references === undefined) return true; - for (const connection of moduleGraph.getOutgoingConnections(module)) { - const d = connection.dependency; - if (!d) continue; - const entry = references.get(d); - if (entry === undefined) continue; - if (entry !== connection.module) return false; - } - return true; - }; + /** + * @returns {string[]} the files contained this chunk group + */ + getFiles() { + const files = new Set(); - const modulesWithoutCache = new Set(modules); - for (const [module, cachedMemCache] of moduleMemCacheCache) { - if (modulesWithoutCache.has(module)) { - const buildInfo = module.buildInfo; - if (buildInfo) { - if (cachedMemCache.buildInfo !== buildInfo) { - // use a new one - const memCache = new WeakTupleMap(); - moduleMemCaches.set(module, memCache); - affectedModules.add(module); - cachedMemCache.buildInfo = buildInfo; - cachedMemCache.references = computeReferences(module); - cachedMemCache.memCache = memCache; - statChanged++; - } else if (!compareReferences(module, cachedMemCache.references)) { - // use a new one - const memCache = new WeakTupleMap(); - moduleMemCaches.set(module, memCache); - affectedModules.add(module); - cachedMemCache.references = computeReferences(module); - cachedMemCache.memCache = memCache; - statReferencesChanged++; - } else { - // keep the old mem cache - moduleMemCaches.set(module, cachedMemCache.memCache); - statUnchanged++; - } - } else { - infectedModules.add(module); - moduleMemCacheCache.delete(module); - statWithoutBuild++; - } - modulesWithoutCache.delete(module); - } else { - moduleMemCacheCache.delete(module); + for (const chunk of this.chunks) { + for (const file of chunk.files) { + files.add(file); } } - for (const module of modulesWithoutCache) { - const buildInfo = module.buildInfo; - if (buildInfo) { - // create a new entry - const memCache = new WeakTupleMap(); - moduleMemCacheCache.set(module, { - buildInfo, - references: computeReferences(module), - memCache - }); - moduleMemCaches.set(module, memCache); - affectedModules.add(module); - statNew++; - } else { - infectedModules.add(module); - statWithoutBuild++; + return Array.from(files); + } + + /** + * @returns {void} + */ + remove() { + // cleanup parents + for (const parentChunkGroup of this._parents) { + // remove this chunk from its parents + parentChunkGroup._children.delete(this); + + // cleanup "sub chunks" + for (const chunkGroup of this._children) { + /** + * remove this chunk as "intermediary" and connect + * it "sub chunks" and parents directly + */ + // add parent to each "sub chunk" + chunkGroup.addParent(parentChunkGroup); + // add "sub chunk" to parent + parentChunkGroup.addChild(chunkGroup); } } - const reduceAffectType = connections => { - let affected = false; - for (const { dependency } of connections) { - if (!dependency) continue; - const type = dependency.couldAffectReferencingModule(); - if (type === Dependency.TRANSITIVE) return Dependency.TRANSITIVE; - if (type === false) continue; - affected = true; - } - return affected; - }; - const directOnlyInfectedModules = new Set(); - for (const module of infectedModules) { - for (const [ - referencingModule, - connections - ] of moduleGraph.getIncomingConnectionsByOriginModule(module)) { - if (!referencingModule) continue; - if (infectedModules.has(referencingModule)) continue; - const type = reduceAffectType(connections); - if (!type) continue; - if (type === true) { - directOnlyInfectedModules.add(referencingModule); - } else { - infectedModules.add(referencingModule); - } - } + /** + * we need to iterate again over the children + * to remove this from the child's parents. + * This can not be done in the above loop + * as it is not guaranteed that `this._parents` contains anything. + */ + for (const chunkGroup of this._children) { + // remove this as parent of every "sub chunk" + chunkGroup._parents.delete(this); } - for (const module of directOnlyInfectedModules) infectedModules.add(module); - const directOnlyAffectModules = new Set(); - for (const module of affectedModules) { - for (const [ - referencingModule, - connections - ] of moduleGraph.getIncomingConnectionsByOriginModule(module)) { - if (!referencingModule) continue; - if (infectedModules.has(referencingModule)) continue; - if (affectedModules.has(referencingModule)) continue; - const type = reduceAffectType(connections); - if (!type) continue; - if (type === true) { - directOnlyAffectModules.add(referencingModule); - } else { - affectedModules.add(referencingModule); - } - const memCache = new WeakTupleMap(); - const cache = moduleMemCacheCache.get(referencingModule); - cache.memCache = memCache; - moduleMemCaches.set(referencingModule, memCache); - } + + // remove chunks + for (const chunk of this.chunks) { + chunk.removeGroup(this); } - for (const module of directOnlyAffectModules) affectedModules.add(module); - this.logger.log( - `${Math.round( - (100 * (affectedModules.size + infectedModules.size)) / - this.modules.size - )}% (${affectedModules.size} affected + ${ - infectedModules.size - } infected of ${ - this.modules.size - }) modules flagged as affected (${statNew} new modules, ${statChanged} changed, ${statReferencesChanged} references changed, ${statUnchanged} unchanged, ${statWithoutBuild} were not built)` + } + + sortItems() { + this.origins.sort(sortOrigin); + } + + /** + * Sorting predicate which allows current ChunkGroup to be compared against another. + * Sorting values are based off of number of chunks in ChunkGroup. + * + * @param {ChunkGraph} chunkGraph the chunk graph + * @param {ChunkGroup} otherGroup the chunkGroup to compare this against + * @returns {-1|0|1} sort position for comparison + */ + compareTo(chunkGraph, otherGroup) { + if (this.chunks.length > otherGroup.chunks.length) return -1; + if (this.chunks.length < otherGroup.chunks.length) return 1; + return compareIterables(compareChunks(chunkGraph))( + this.chunks, + otherGroup.chunks ); } - _computeAffectedModulesWithChunkGraph() { - const { moduleMemCaches } = this; - if (!moduleMemCaches) return; - const moduleMemCaches2 = (this.moduleMemCaches2 = new Map()); - const { moduleGraph, chunkGraph } = this; - const key = "memCache2"; - let statUnchanged = 0; - let statChanged = 0; - let statNew = 0; - /** - * @param {Module} module module - * @returns {{ id: string | number, modules?: Map, blocks?: (string | number)[] }} references - */ - const computeReferences = module => { - const id = chunkGraph.getModuleId(module); - /** @type {Map} */ - let modules = undefined; - /** @type {(string | number)[] | undefined} */ - let blocks = undefined; - const outgoing = moduleGraph.getOutgoingConnectionsByModule(module); - if (outgoing !== undefined) { - for (const m of outgoing.keys()) { - if (!m) continue; - if (modules === undefined) modules = new Map(); - modules.set(m, chunkGraph.getModuleId(m)); - } - } - if (module.blocks.length > 0) { - blocks = []; - const queue = Array.from(module.blocks); - for (const block of queue) { - const chunkGroup = chunkGraph.getBlockChunkGroup(block); - if (chunkGroup) { - for (const chunk of chunkGroup.chunks) { - blocks.push(chunk.id); - } - } else { - blocks.push(null); - } - queue.push.apply(queue, block.blocks); - } - } - return { id, modules, blocks }; - }; - /** - * @param {Module} module module - * @param {Object} references references - * @param {string | number} references.id id - * @param {Map=} references.modules modules - * @param {(string | number)[]=} references.blocks blocks - * @returns {boolean} ok? - */ - const compareReferences = (module, { id, modules, blocks }) => { - if (id !== chunkGraph.getModuleId(module)) return false; - if (modules !== undefined) { - for (const [module, id] of modules) { - if (chunkGraph.getModuleId(module) !== id) return false; - } - } - if (blocks !== undefined) { - const queue = Array.from(module.blocks); - let i = 0; - for (const block of queue) { - const chunkGroup = chunkGraph.getBlockChunkGroup(block); - if (chunkGroup) { - for (const chunk of chunkGroup.chunks) { - if (i >= blocks.length || blocks[i++] !== chunk.id) return false; - } - } else { - if (i >= blocks.length || blocks[i++] !== null) return false; + /** + * @param {ModuleGraph} moduleGraph the module graph + * @param {ChunkGraph} chunkGraph the chunk graph + * @returns {Record} mapping from children type to ordered list of ChunkGroups + */ + getChildrenByOrders(moduleGraph, chunkGraph) { + /** @type {Map} */ + const lists = new Map(); + for (const childGroup of this._children) { + for (const key of Object.keys(childGroup.options)) { + if (key.endsWith("Order")) { + const name = key.substr(0, key.length - "Order".length); + let list = lists.get(name); + if (list === undefined) { + lists.set(name, (list = [])); } - queue.push.apply(queue, block.blocks); + list.push({ + order: childGroup.options[key], + group: childGroup + }); } - if (i !== blocks.length) return false; - } - return true; - }; - - for (const [module, memCache] of moduleMemCaches) { - /** @type {{ references: { id: string | number, modules?: Map, blocks?: (string | number)[]}, memCache: WeakTupleMap }} */ - const cache = memCache.get(key); - if (cache === undefined) { - const memCache2 = new WeakTupleMap(); - memCache.set(key, { - references: computeReferences(module), - memCache: memCache2 - }); - moduleMemCaches2.set(module, memCache2); - statNew++; - } else if (!compareReferences(module, cache.references)) { - const memCache = new WeakTupleMap(); - cache.references = computeReferences(module); - cache.memCache = memCache; - moduleMemCaches2.set(module, memCache); - statChanged++; - } else { - moduleMemCaches2.set(module, cache.memCache); - statUnchanged++; } } + /** @type {Record} */ + const result = Object.create(null); + for (const [name, list] of lists) { + list.sort((a, b) => { + const cmp = b.order - a.order; + if (cmp !== 0) return cmp; + return a.group.compareTo(chunkGraph, b.group); + }); + result[name] = list.map(i => i.group); + } + return result; + } - this.logger.log( - `${Math.round( - (100 * statChanged) / (statNew + statChanged + statUnchanged) - )}% modules flagged as affected by chunk graph (${statNew} new modules, ${statChanged} changed, ${statUnchanged} unchanged)` - ); + /** + * Sets the top-down index of a module in this ChunkGroup + * @param {Module} module module for which the index should be set + * @param {number} index the index of the module + * @returns {void} + */ + setModulePreOrderIndex(module, index) { + this._modulePreOrderIndices.set(module, index); } - finish(callback) { - this.factorizeQueue.clear(); - if (this.profile) { - this.logger.time("finish module profiles"); - const ParallelismFactorCalculator = __webpack_require__(67491); - const p = new ParallelismFactorCalculator(); - const moduleGraph = this.moduleGraph; - const modulesWithProfiles = new Map(); - for (const module of this.modules) { - const profile = moduleGraph.getProfile(module); - if (!profile) continue; - modulesWithProfiles.set(module, profile); - p.range( - profile.buildingStartTime, - profile.buildingEndTime, - f => (profile.buildingParallelismFactor = f) - ); - p.range( - profile.factoryStartTime, - profile.factoryEndTime, - f => (profile.factoryParallelismFactor = f) - ); - p.range( - profile.integrationStartTime, - profile.integrationEndTime, - f => (profile.integrationParallelismFactor = f) + /** + * Gets the top-down index of a module in this ChunkGroup + * @param {Module} module the module + * @returns {number} index + */ + getModulePreOrderIndex(module) { + return this._modulePreOrderIndices.get(module); + } + + /** + * Sets the bottom-up index of a module in this ChunkGroup + * @param {Module} module module for which the index should be set + * @param {number} index the index of the module + * @returns {void} + */ + setModulePostOrderIndex(module, index) { + this._modulePostOrderIndices.set(module, index); + } + + /** + * Gets the bottom-up index of a module in this ChunkGroup + * @param {Module} module the module + * @returns {number} index + */ + getModulePostOrderIndex(module) { + return this._modulePostOrderIndices.get(module); + } + + /* istanbul ignore next */ + checkConstraints() { + const chunk = this; + for (const child of chunk._children) { + if (!child._parents.has(chunk)) { + throw new Error( + `checkConstraints: child missing parent ${chunk.debugId} -> ${child.debugId}` ); - p.range( - profile.storingStartTime, - profile.storingEndTime, - f => (profile.storingParallelismFactor = f) + } + } + for (const parentChunk of chunk._parents) { + if (!parentChunk._children.has(chunk)) { + throw new Error( + `checkConstraints: parent missing child ${parentChunk.debugId} <- ${chunk.debugId}` ); - p.range( - profile.restoringStartTime, - profile.restoringEndTime, - f => (profile.restoringParallelismFactor = f) - ); - if (profile.additionalFactoryTimes) { - for (const { start, end } of profile.additionalFactoryTimes) { - const influence = (end - start) / profile.additionalFactories; - p.range( - start, - end, - f => - (profile.additionalFactoriesParallelismFactor += f * influence) - ); - } - } } - p.calculate(); - - const logger = this.getLogger("webpack.Compilation.ModuleProfile"); - const logByValue = (value, msg) => { - if (value > 1000) { - logger.error(msg); - } else if (value > 500) { - logger.warn(msg); - } else if (value > 200) { - logger.info(msg); - } else if (value > 30) { - logger.log(msg); - } else { - logger.debug(msg); - } - }; - const logNormalSummary = (category, getDuration, getParallelism) => { - let sum = 0; - let max = 0; - for (const [module, profile] of modulesWithProfiles) { - const p = getParallelism(profile); - const d = getDuration(profile); - if (d === 0 || p === 0) continue; - const t = d / p; - sum += t; - if (t <= 10) continue; - logByValue( - t, - ` | ${Math.round(t)} ms${ - p >= 1.1 ? ` (parallelism ${Math.round(p * 10) / 10})` : "" - } ${category} > ${module.readableIdentifier(this.requestShortener)}` - ); - max = Math.max(max, t); - } - if (sum <= 10) return; - logByValue( - Math.max(sum / 10, max), - `${Math.round(sum)} ms ${category}` - ); - }; - const logByLoadersSummary = (category, getDuration, getParallelism) => { - const map = new Map(); - for (const [module, profile] of modulesWithProfiles) { - const list = provide( - map, - module.type + "!" + module.identifier().replace(/(!|^)[^!]*$/, ""), - () => [] - ); - list.push({ module, profile }); - } - - let sum = 0; - let max = 0; - for (const [key, modules] of map) { - let innerSum = 0; - let innerMax = 0; - for (const { module, profile } of modules) { - const p = getParallelism(profile); - const d = getDuration(profile); - if (d === 0 || p === 0) continue; - const t = d / p; - innerSum += t; - if (t <= 10) continue; - logByValue( - t, - ` | | ${Math.round(t)} ms${ - p >= 1.1 ? ` (parallelism ${Math.round(p * 10) / 10})` : "" - } ${category} > ${module.readableIdentifier( - this.requestShortener - )}` - ); - innerMax = Math.max(innerMax, t); - } - sum += innerSum; - if (innerSum <= 10) continue; - const idx = key.indexOf("!"); - const loaders = key.slice(idx + 1); - const moduleType = key.slice(0, idx); - const t = Math.max(innerSum / 10, innerMax); - logByValue( - t, - ` | ${Math.round(innerSum)} ms ${category} > ${ - loaders - ? `${ - modules.length - } x ${moduleType} with ${this.requestShortener.shorten( - loaders - )}` - : `${modules.length} x ${moduleType}` - }` - ); - max = Math.max(max, t); - } - if (sum <= 10) return; - logByValue( - Math.max(sum / 10, max), - `${Math.round(sum)} ms ${category}` - ); - }; - logNormalSummary( - "resolve to new modules", - p => p.factory, - p => p.factoryParallelismFactor - ); - logNormalSummary( - "resolve to existing modules", - p => p.additionalFactories, - p => p.additionalFactoriesParallelismFactor - ); - logNormalSummary( - "integrate modules", - p => p.restoring, - p => p.restoringParallelismFactor - ); - logByLoadersSummary( - "build modules", - p => p.building, - p => p.buildingParallelismFactor - ); - logNormalSummary( - "store modules", - p => p.storing, - p => p.storingParallelismFactor - ); - logNormalSummary( - "restore modules", - p => p.restoring, - p => p.restoringParallelismFactor - ); - this.logger.timeEnd("finish module profiles"); } - this.logger.time("compute affected modules"); - this._computeAffectedModules(this.modules); - this.logger.timeEnd("compute affected modules"); - this.logger.time("finish modules"); - const { modules, moduleMemCaches } = this; - this.hooks.finishModules.callAsync(modules, err => { - this.logger.timeEnd("finish modules"); - if (err) return callback(err); - - // extract warnings and errors from modules - this.moduleGraph.freeze("dependency errors"); - // TODO keep a cacheToken (= {}) for each module in the graph - // create a new one per compilation and flag all updated files - // and parents with it - this.logger.time("report dependency errors and warnings"); - for (const module of modules) { - // TODO only run for modules with changed cacheToken - // global WeakMap> to keep modules without errors/warnings - const memCache = moduleMemCaches && moduleMemCaches.get(module); - if (memCache && memCache.get("noWarningsOrErrors")) continue; - let hasProblems = this.reportDependencyErrorsAndWarnings(module, [ - module - ]); - const errors = module.getErrors(); - if (errors !== undefined) { - for (const error of errors) { - if (!error.module) { - error.module = module; - } - this.errors.push(error); - hasProblems = true; - } - } - const warnings = module.getWarnings(); - if (warnings !== undefined) { - for (const warning of warnings) { - if (!warning.module) { - warning.module = module; - } - this.warnings.push(warning); - hasProblems = true; - } - } - if (!hasProblems && memCache) memCache.set("noWarningsOrErrors", true); - } - this.moduleGraph.unfreeze(); - this.logger.timeEnd("report dependency errors and warnings"); - - callback(); - }); - } - - unseal() { - this.hooks.unseal.call(); - this.chunks.clear(); - this.chunkGroups.length = 0; - this.namedChunks.clear(); - this.namedChunkGroups.clear(); - this.entrypoints.clear(); - this.additionalChunkAssets.length = 0; - this.assets = {}; - this.assetsInfo.clear(); - this.moduleGraph.removeAllModuleAttributes(); - this.moduleGraph.unfreeze(); - this.moduleMemCaches2 = undefined; } +} - /** - * @param {Callback} callback signals when the call finishes - * @returns {void} - */ - seal(callback) { - const finalCallback = err => { - this.factorizeQueue.clear(); - this.buildQueue.clear(); - this.rebuildQueue.clear(); - this.processDependenciesQueue.clear(); - this.addModuleQueue.clear(); - return callback(err); - }; - const chunkGraph = new ChunkGraph( - this.moduleGraph, - this.outputOptions.hashFunction - ); - this.chunkGraph = chunkGraph; - - if (this._backCompat) { - for (const module of this.modules) { - ChunkGraph.setChunkGraphForModule(module, chunkGraph); - } - } - - this.hooks.seal.call(); - - this.logger.time("optimize dependencies"); - while (this.hooks.optimizeDependencies.call(this.modules)) { - /* empty */ - } - this.hooks.afterOptimizeDependencies.call(this.modules); - this.logger.timeEnd("optimize dependencies"); - - this.logger.time("create chunks"); - this.hooks.beforeChunks.call(); - this.moduleGraph.freeze("seal"); - /** @type {Map} */ - const chunkGraphInit = new Map(); - for (const [name, { dependencies, includeDependencies, options }] of this - .entries) { - const chunk = this.addChunk(name); - if (options.filename) { - chunk.filenameTemplate = options.filename; - } - const entrypoint = new Entrypoint(options); - if (!options.dependOn && !options.runtime) { - entrypoint.setRuntimeChunk(chunk); - } - entrypoint.setEntrypointChunk(chunk); - this.namedChunkGroups.set(name, entrypoint); - this.entrypoints.set(name, entrypoint); - this.chunkGroups.push(entrypoint); - connectChunkGroupAndChunk(entrypoint, chunk); - - const entryModules = new Set(); - for (const dep of [...this.globalEntry.dependencies, ...dependencies]) { - entrypoint.addOrigin(null, { name }, /** @type {any} */ (dep).request); - - const module = this.moduleGraph.getModule(dep); - if (module) { - chunkGraph.connectChunkAndEntryModule(chunk, module, entrypoint); - entryModules.add(module); - const modulesList = chunkGraphInit.get(entrypoint); - if (modulesList === undefined) { - chunkGraphInit.set(entrypoint, [module]); - } else { - modulesList.push(module); - } - } - } - - this.assignDepths(entryModules); - - const mapAndSort = deps => - deps - .map(dep => this.moduleGraph.getModule(dep)) - .filter(Boolean) - .sort(compareModulesByIdentifier); - const includedModules = [ - ...mapAndSort(this.globalEntry.includeDependencies), - ...mapAndSort(includeDependencies) - ]; +ChunkGroup.prototype.getModuleIndex = util.deprecate( + ChunkGroup.prototype.getModulePreOrderIndex, + "ChunkGroup.getModuleIndex was renamed to getModulePreOrderIndex", + "DEP_WEBPACK_CHUNK_GROUP_GET_MODULE_INDEX" +); - let modulesList = chunkGraphInit.get(entrypoint); - if (modulesList === undefined) { - chunkGraphInit.set(entrypoint, (modulesList = [])); - } - for (const module of includedModules) { - this.assignDepth(module); - modulesList.push(module); - } - } - const runtimeChunks = new Set(); - outer: for (const [ - name, - { - options: { dependOn, runtime } - } - ] of this.entries) { - if (dependOn && runtime) { - const err = - new WebpackError(`Entrypoint '${name}' has 'dependOn' and 'runtime' specified. This is not valid. -Entrypoints that depend on other entrypoints do not have their own runtime. -They will use the runtime(s) from referenced entrypoints instead. -Remove the 'runtime' option from the entrypoint.`); - const entry = this.entrypoints.get(name); - err.chunk = entry.getEntrypointChunk(); - this.errors.push(err); - } - if (dependOn) { - const entry = this.entrypoints.get(name); - const referencedChunks = entry - .getEntrypointChunk() - .getAllReferencedChunks(); - const dependOnEntries = []; - for (const dep of dependOn) { - const dependency = this.entrypoints.get(dep); - if (!dependency) { - throw new Error( - `Entry ${name} depends on ${dep}, but this entry was not found` - ); - } - if (referencedChunks.has(dependency.getEntrypointChunk())) { - const err = new WebpackError( - `Entrypoints '${name}' and '${dep}' use 'dependOn' to depend on each other in a circular way.` - ); - const entryChunk = entry.getEntrypointChunk(); - err.chunk = entryChunk; - this.errors.push(err); - entry.setRuntimeChunk(entryChunk); - continue outer; - } - dependOnEntries.push(dependency); - } - for (const dependency of dependOnEntries) { - connectChunkGroupParentAndChild(dependency, entry); - } - } else if (runtime) { - const entry = this.entrypoints.get(name); - let chunk = this.namedChunks.get(runtime); - if (chunk) { - if (!runtimeChunks.has(chunk)) { - const err = - new WebpackError(`Entrypoint '${name}' has a 'runtime' option which points to another entrypoint named '${runtime}'. -It's not valid to use other entrypoints as runtime chunk. -Did you mean to use 'dependOn: ${JSON.stringify( - runtime - )}' instead to allow using entrypoint '${name}' within the runtime of entrypoint '${runtime}'? For this '${runtime}' must always be loaded when '${name}' is used. -Or do you want to use the entrypoints '${name}' and '${runtime}' independently on the same page with a shared runtime? In this case give them both the same value for the 'runtime' option. It must be a name not already used by an entrypoint.`); - const entryChunk = entry.getEntrypointChunk(); - err.chunk = entryChunk; - this.errors.push(err); - entry.setRuntimeChunk(entryChunk); - continue; - } - } else { - chunk = this.addChunk(runtime); - chunk.preventIntegration = true; - runtimeChunks.add(chunk); - } - entry.unshiftChunk(chunk); - chunk.addGroup(entry); - entry.setRuntimeChunk(chunk); - } - } - buildChunkGraph(this, chunkGraphInit); - this.hooks.afterChunks.call(this.chunks); - this.logger.timeEnd("create chunks"); +ChunkGroup.prototype.getModuleIndex2 = util.deprecate( + ChunkGroup.prototype.getModulePostOrderIndex, + "ChunkGroup.getModuleIndex2 was renamed to getModulePostOrderIndex", + "DEP_WEBPACK_CHUNK_GROUP_GET_MODULE_INDEX_2" +); - this.logger.time("optimize"); - this.hooks.optimize.call(); +module.exports = ChunkGroup; - while (this.hooks.optimizeModules.call(this.modules)) { - /* empty */ - } - this.hooks.afterOptimizeModules.call(this.modules); - while (this.hooks.optimizeChunks.call(this.chunks, this.chunkGroups)) { - /* empty */ - } - this.hooks.afterOptimizeChunks.call(this.chunks, this.chunkGroups); +/***/ }), - this.hooks.optimizeTree.callAsync(this.chunks, this.modules, err => { - if (err) { - return finalCallback( - makeWebpackError(err, "Compilation.hooks.optimizeTree") - ); - } +/***/ 80187: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - this.hooks.afterOptimizeTree.call(this.chunks, this.modules); +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ - this.hooks.optimizeChunkModules.callAsync( - this.chunks, - this.modules, - err => { - if (err) { - return finalCallback( - makeWebpackError(err, "Compilation.hooks.optimizeChunkModules") - ); - } - this.hooks.afterOptimizeChunkModules.call(this.chunks, this.modules); - const shouldRecord = this.hooks.shouldRecord.call() !== false; +const WebpackError = __webpack_require__(68422); - this.hooks.reviveModules.call(this.modules, this.records); - this.hooks.beforeModuleIds.call(this.modules); - this.hooks.moduleIds.call(this.modules); - this.hooks.optimizeModuleIds.call(this.modules); - this.hooks.afterOptimizeModuleIds.call(this.modules); +/** @typedef {import("./Chunk")} Chunk */ - this.hooks.reviveChunks.call(this.chunks, this.records); - this.hooks.beforeChunkIds.call(this.chunks); - this.hooks.chunkIds.call(this.chunks); - this.hooks.optimizeChunkIds.call(this.chunks); - this.hooks.afterOptimizeChunkIds.call(this.chunks); +class ChunkRenderError extends WebpackError { + /** + * Create a new ChunkRenderError + * @param {Chunk} chunk A chunk + * @param {string} file Related file + * @param {Error} error Original error + */ + constructor(chunk, file, error) { + super(); - this.assignRuntimeIds(); + this.name = "ChunkRenderError"; + this.error = error; + this.message = error.message; + this.details = error.stack; + this.file = file; + this.chunk = chunk; + } +} - this.logger.time("compute affected modules with chunk graph"); - this._computeAffectedModulesWithChunkGraph(); - this.logger.timeEnd("compute affected modules with chunk graph"); +module.exports = ChunkRenderError; - this.sortItemsWithChunkIds(); - if (shouldRecord) { - this.hooks.recordModules.call(this.modules, this.records); - this.hooks.recordChunks.call(this.chunks, this.records); - } +/***/ }), - this.hooks.optimizeCodeGeneration.call(this.modules); - this.logger.timeEnd("optimize"); +/***/ 50527: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - this.logger.time("module hashing"); - this.hooks.beforeModuleHash.call(); - this.createModuleHashes(); - this.hooks.afterModuleHash.call(); - this.logger.timeEnd("module hashing"); +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ - this.logger.time("code generation"); - this.hooks.beforeCodeGeneration.call(); - this.codeGeneration(err => { - if (err) { - return finalCallback(err); - } - this.hooks.afterCodeGeneration.call(); - this.logger.timeEnd("code generation"); - this.logger.time("runtime requirements"); - this.hooks.beforeRuntimeRequirements.call(); - this.processRuntimeRequirements(); - this.hooks.afterRuntimeRequirements.call(); - this.logger.timeEnd("runtime requirements"); - this.logger.time("hashing"); - this.hooks.beforeHash.call(); - const codeGenerationJobs = this.createHash(); - this.hooks.afterHash.call(); - this.logger.timeEnd("hashing"); +const util = __webpack_require__(31669); +const memoize = __webpack_require__(84297); - this._runCodeGenerationJobs(codeGenerationJobs, err => { - if (err) { - return finalCallback(err); - } +/** @typedef {import("../declarations/WebpackOptions").Output} OutputOptions */ +/** @typedef {import("./Compilation")} Compilation */ - if (shouldRecord) { - this.logger.time("record hash"); - this.hooks.recordHash.call(this.records); - this.logger.timeEnd("record hash"); - } +const getJavascriptModulesPlugin = memoize(() => + __webpack_require__(76767) +); - this.logger.time("module assets"); - this.clearAssets(); +// TODO webpack 6 remove this class +class ChunkTemplate { + /** + * @param {OutputOptions} outputOptions output options + * @param {Compilation} compilation the compilation + */ + constructor(outputOptions, compilation) { + this._outputOptions = outputOptions || {}; + this.hooks = Object.freeze({ + renderManifest: { + tap: util.deprecate( + (options, fn) => { + compilation.hooks.renderManifest.tap( + options, + (entries, options) => { + if (options.chunk.hasRuntime()) return entries; + return fn(entries, options); + } + ); + }, + "ChunkTemplate.hooks.renderManifest is deprecated (use Compilation.hooks.renderManifest instead)", + "DEP_WEBPACK_CHUNK_TEMPLATE_RENDER_MANIFEST" + ) + }, + modules: { + tap: util.deprecate( + (options, fn) => { + getJavascriptModulesPlugin() + .getCompilationHooks(compilation) + .renderChunk.tap(options, (source, renderContext) => + fn( + source, + compilation.moduleTemplates.javascript, + renderContext + ) + ); + }, + "ChunkTemplate.hooks.modules is deprecated (use JavascriptModulesPlugin.getCompilationHooks().renderChunk instead)", + "DEP_WEBPACK_CHUNK_TEMPLATE_MODULES" + ) + }, + render: { + tap: util.deprecate( + (options, fn) => { + getJavascriptModulesPlugin() + .getCompilationHooks(compilation) + .renderChunk.tap(options, (source, renderContext) => + fn( + source, + compilation.moduleTemplates.javascript, + renderContext + ) + ); + }, + "ChunkTemplate.hooks.render is deprecated (use JavascriptModulesPlugin.getCompilationHooks().renderChunk instead)", + "DEP_WEBPACK_CHUNK_TEMPLATE_RENDER" + ) + }, + renderWithEntry: { + tap: util.deprecate( + (options, fn) => { + getJavascriptModulesPlugin() + .getCompilationHooks(compilation) + .render.tap(options, (source, renderContext) => { + if ( + renderContext.chunkGraph.getNumberOfEntryModules( + renderContext.chunk + ) === 0 || + renderContext.chunk.hasRuntime() + ) { + return source; + } + return fn(source, renderContext.chunk); + }); + }, + "ChunkTemplate.hooks.renderWithEntry is deprecated (use JavascriptModulesPlugin.getCompilationHooks().render instead)", + "DEP_WEBPACK_CHUNK_TEMPLATE_RENDER_WITH_ENTRY" + ) + }, + hash: { + tap: util.deprecate( + (options, fn) => { + compilation.hooks.fullHash.tap(options, fn); + }, + "ChunkTemplate.hooks.hash is deprecated (use Compilation.hooks.fullHash instead)", + "DEP_WEBPACK_CHUNK_TEMPLATE_HASH" + ) + }, + hashForChunk: { + tap: util.deprecate( + (options, fn) => { + getJavascriptModulesPlugin() + .getCompilationHooks(compilation) + .chunkHash.tap(options, (chunk, hash, context) => { + if (chunk.hasRuntime()) return; + fn(hash, chunk, context); + }); + }, + "ChunkTemplate.hooks.hashForChunk is deprecated (use JavascriptModulesPlugin.getCompilationHooks().chunkHash instead)", + "DEP_WEBPACK_CHUNK_TEMPLATE_HASH_FOR_CHUNK" + ) + } + }); + } +} - this.hooks.beforeModuleAssets.call(); - this.createModuleAssets(); - this.logger.timeEnd("module assets"); +Object.defineProperty(ChunkTemplate.prototype, "outputOptions", { + get: util.deprecate( + /** + * @this {ChunkTemplate} + * @returns {OutputOptions} output options + */ + function () { + return this._outputOptions; + }, + "ChunkTemplate.outputOptions is deprecated (use Compilation.outputOptions instead)", + "DEP_WEBPACK_CHUNK_TEMPLATE_OUTPUT_OPTIONS" + ) +}); - const cont = () => { - this.logger.time("process assets"); - this.hooks.processAssets.callAsync(this.assets, err => { - if (err) { - return finalCallback( - makeWebpackError(err, "Compilation.hooks.processAssets") - ); - } - this.hooks.afterProcessAssets.call(this.assets); - this.logger.timeEnd("process assets"); - this.assets = this._backCompat - ? soonFrozenObjectDeprecation( - this.assets, - "Compilation.assets", - "DEP_WEBPACK_COMPILATION_ASSETS", - `BREAKING CHANGE: No more changes should happen to Compilation.assets after sealing the Compilation. - Do changes to assets earlier, e. g. in Compilation.hooks.processAssets. - Make sure to select an appropriate stage from Compilation.PROCESS_ASSETS_STAGE_*.` - ) - : Object.freeze(this.assets); +module.exports = ChunkTemplate; - this.summarizeDependencies(); - if (shouldRecord) { - this.hooks.record.call(this, this.records); - } - if (this.hooks.needAdditionalSeal.call()) { - this.unseal(); - return this.seal(callback); - } - return this.hooks.afterSeal.callAsync(err => { - if (err) { - return finalCallback( - makeWebpackError(err, "Compilation.hooks.afterSeal") - ); - } - this.fileSystemInfo.logStatistics(); - finalCallback(); - }); - }); - }; +/***/ }), - this.logger.time("create chunk assets"); - if (this.hooks.shouldGenerateChunkAssets.call() !== false) { - this.hooks.beforeChunkAssets.call(); - this.createChunkAssets(err => { - this.logger.timeEnd("create chunk assets"); - if (err) { - return finalCallback(err); - } - cont(); - }); - } else { - this.logger.timeEnd("create chunk assets"); - cont(); - } - }); - }); - } - ); - }); - } +/***/ 49129: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - /** - * @param {Module} module module to report from - * @param {DependenciesBlock[]} blocks blocks to report from - * @returns {boolean} true, when it has warnings or errors - */ - reportDependencyErrorsAndWarnings(module, blocks) { - let hasProblems = false; - for (let indexBlock = 0; indexBlock < blocks.length; indexBlock++) { - const block = blocks[indexBlock]; - const dependencies = block.dependencies; +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Sergey Melyukov @smelukov +*/ - for (let indexDep = 0; indexDep < dependencies.length; indexDep++) { - const d = dependencies[indexDep]; - const warnings = d.getWarnings(this.moduleGraph); - if (warnings) { - for (let indexWar = 0; indexWar < warnings.length; indexWar++) { - const w = warnings[indexWar]; - const warning = new ModuleDependencyWarning(module, w, d.loc); - this.warnings.push(warning); - hasProblems = true; - } - } - const errors = d.getErrors(this.moduleGraph); - if (errors) { - for (let indexErr = 0; indexErr < errors.length; indexErr++) { - const e = errors[indexErr]; +const asyncLib = __webpack_require__(36386); +const { SyncBailHook } = __webpack_require__(34718); +const Compilation = __webpack_require__(59622); +const createSchemaValidation = __webpack_require__(77695); +const { join } = __webpack_require__(93204); +const processAsyncTree = __webpack_require__(76815); - const error = new ModuleDependencyError(module, e, d.loc); - this.errors.push(error); - hasProblems = true; - } - } - } +/** @typedef {import("../declarations/WebpackOptions").CleanOptions} CleanOptions */ +/** @typedef {import("./Compiler")} Compiler */ +/** @typedef {import("./logging/Logger").Logger} Logger */ +/** @typedef {import("./util/fs").OutputFileSystem} OutputFileSystem */ +/** @typedef {import("./util/fs").StatsCallback} StatsCallback */ - if (this.reportDependencyErrorsAndWarnings(module, block.blocks)) - hasProblems = true; - } - return hasProblems; - } +/** @typedef {(function(string):boolean)|RegExp} IgnoreItem */ +/** @typedef {function(IgnoreItem): void} AddToIgnoreCallback */ - codeGeneration(callback) { - const { chunkGraph } = this; - this.codeGenerationResults = new CodeGenerationResults( - this.outputOptions.hashFunction - ); - /** @type {{module: Module, hash: string, runtime: RuntimeSpec, runtimes: RuntimeSpec[]}[]} */ - const jobs = []; - for (const module of this.modules) { - const runtimes = chunkGraph.getModuleRuntimes(module); - if (runtimes.size === 1) { - for (const runtime of runtimes) { - const hash = chunkGraph.getModuleHash(module, runtime); - jobs.push({ module, hash, runtime, runtimes: [runtime] }); - } - } else if (runtimes.size > 1) { - /** @type {Map} */ - const map = new Map(); - for (const runtime of runtimes) { - const hash = chunkGraph.getModuleHash(module, runtime); - const job = map.get(hash); - if (job === undefined) { - const newJob = { module, hash, runtime, runtimes: [runtime] }; - jobs.push(newJob); - map.set(hash, newJob); - } else { - job.runtimes.push(runtime); - } - } - } - } +/** + * @typedef {Object} CleanPluginCompilationHooks + * @property {SyncBailHook<[string], boolean>} keep when returning true the file/directory will be kept during cleaning, returning false will clean it and ignore the following plugins and config + */ - this._runCodeGenerationJobs(jobs, callback); +const validate = createSchemaValidation( + undefined, + () => { + const { definitions } = __webpack_require__(1863); + return { + definitions, + oneOf: [{ $ref: "#/definitions/CleanOptions" }] + }; + }, + { + name: "Clean Plugin", + baseDataPath: "options" } +); - _runCodeGenerationJobs(jobs, callback) { - let statModulesFromCache = 0; - let statModulesGenerated = 0; - const { chunkGraph, moduleGraph, dependencyTemplates, runtimeTemplate } = - this; - const results = this.codeGenerationResults; - const errors = []; - asyncLib.eachLimit( - jobs, - this.options.parallelism, - ({ module, hash, runtime, runtimes }, callback) => { - this._codeGenerationModule( - module, - runtime, - runtimes, - hash, - dependencyTemplates, - chunkGraph, - moduleGraph, - runtimeTemplate, - errors, - results, - (err, codeGenerated) => { - if (codeGenerated) statModulesGenerated++; - else statModulesFromCache++; - callback(err); +/** + * @param {OutputFileSystem} fs filesystem + * @param {string} outputPath output path + * @param {Set} currentAssets filename of the current assets (must not start with .. or ., must only use / as path separator) + * @param {function(Error=, Set=): void} callback returns the filenames of the assets that shouldn't be there + * @returns {void} + */ +const getDiffToFs = (fs, outputPath, currentAssets, callback) => { + const directories = new Set(); + // get directories of assets + for (const asset of currentAssets) { + directories.add(asset.replace(/(^|\/)[^/]*$/, "")); + } + // and all parent directories + for (const directory of directories) { + directories.add(directory.replace(/(^|\/)[^/]*$/, "")); + } + const diff = new Set(); + asyncLib.forEachLimit( + directories, + 10, + (directory, callback) => { + fs.readdir(join(fs, outputPath, directory), (err, entries) => { + if (err) { + if (err.code === "ENOENT") return callback(); + if (err.code === "ENOTDIR") { + diff.add(directory); + return callback(); } - ); - }, - err => { - if (err) return callback(err); - if (errors.length > 0) { - errors.sort( - compareSelect(err => err.module, compareModulesByIdentifier) - ); - for (const error of errors) { - this.errors.push(error); + return callback(err); + } + for (const entry of entries) { + const file = /** @type {string} */ (entry); + const filename = directory ? `${directory}/${file}` : file; + if (!directories.has(filename) && !currentAssets.has(filename)) { + diff.add(filename); } } - this.logger.log( - `${Math.round( - (100 * statModulesGenerated) / - (statModulesGenerated + statModulesFromCache) - )}% code generated (${statModulesGenerated} generated, ${statModulesFromCache} from cache)` - ); callback(); - } - ); - } - - /** - * @param {Module} module module - * @param {RuntimeSpec} runtime runtime - * @param {RuntimeSpec[]} runtimes runtimes - * @param {string} hash hash - * @param {DependencyTemplates} dependencyTemplates dependencyTemplates - * @param {ChunkGraph} chunkGraph chunkGraph - * @param {ModuleGraph} moduleGraph moduleGraph - * @param {RuntimeTemplate} runtimeTemplate runtimeTemplate - * @param {WebpackError[]} errors errors - * @param {CodeGenerationResults} results results - * @param {function(WebpackError=, boolean=): void} callback callback - */ - _codeGenerationModule( - module, - runtime, - runtimes, - hash, - dependencyTemplates, - chunkGraph, - moduleGraph, - runtimeTemplate, - errors, - results, - callback - ) { - let codeGenerated = false; - const cache = new MultiItemCache( - runtimes.map(runtime => - this._codeGenerationCache.getItemCache( - `${module.identifier()}|${getRuntimeKey(runtime)}`, - `${hash}|${dependencyTemplates.getHash()}` - ) - ) - ); - cache.get((err, cachedResult) => { + }); + }, + err => { if (err) return callback(err); - let result; - if (!cachedResult) { - try { - codeGenerated = true; - this.codeGeneratedModules.add(module); - result = module.codeGeneration({ - chunkGraph, - moduleGraph, - dependencyTemplates, - runtimeTemplate, - runtime - }); - } catch (err) { - errors.push(new CodeGenerationError(module, err)); - result = cachedResult = { - sources: new Map(), - runtimeRequirements: null - }; - } - } else { - result = cachedResult; - } - for (const runtime of runtimes) { - results.add(module, runtime, result); - } - if (!cachedResult) { - cache.store(result, err => callback(err, codeGenerated)); - } else { - callback(null, codeGenerated); - } - }); - } - _getChunkGraphEntries() { - /** @type {Set} */ - const treeEntries = new Set(); - for (const ep of this.entrypoints.values()) { - const chunk = ep.getRuntimeChunk(); - if (chunk) treeEntries.add(chunk); - } - for (const ep of this.asyncEntrypoints) { - const chunk = ep.getRuntimeChunk(); - if (chunk) treeEntries.add(chunk); + callback(null, diff); } - return treeEntries; + ); +}; + +/** + * @param {Set} currentAssets assets list + * @param {Set} oldAssets old assets list + * @returns {Set} diff + */ +const getDiffToOldAssets = (currentAssets, oldAssets) => { + const diff = new Set(); + for (const asset of oldAssets) { + if (!currentAssets.has(asset)) diff.add(asset); } + return diff; +}; - /** - * @param {Object} options options - * @param {ChunkGraph=} options.chunkGraph the chunk graph - * @param {Iterable=} options.modules modules - * @param {Iterable=} options.chunks chunks - * @param {CodeGenerationResults=} options.codeGenerationResults codeGenerationResults - * @param {Iterable=} options.chunkGraphEntries chunkGraphEntries - * @returns {void} - */ - processRuntimeRequirements({ - chunkGraph = this.chunkGraph, - modules = this.modules, - chunks = this.chunks, - codeGenerationResults = this.codeGenerationResults, - chunkGraphEntries = this._getChunkGraphEntries() - } = {}) { - const context = { chunkGraph, codeGenerationResults }; - const { moduleMemCaches2 } = this; - this.logger.time("runtime requirements.modules"); - const additionalModuleRuntimeRequirements = - this.hooks.additionalModuleRuntimeRequirements; - const runtimeRequirementInModule = this.hooks.runtimeRequirementInModule; - for (const module of modules) { - if (chunkGraph.getNumberOfModuleChunks(module) > 0) { - const memCache = moduleMemCaches2 && moduleMemCaches2.get(module); - for (const runtime of chunkGraph.getModuleRuntimes(module)) { - if (memCache) { - const cached = memCache.get( - `moduleRuntimeRequirements-${getRuntimeKey(runtime)}` - ); - if (cached !== undefined) { - if (cached !== null) { - chunkGraph.addModuleRuntimeRequirements( - module, - runtime, - cached, - false - ); - } - continue; - } - } - let set; - const runtimeRequirements = - codeGenerationResults.getRuntimeRequirements(module, runtime); - if (runtimeRequirements && runtimeRequirements.size > 0) { - set = new Set(runtimeRequirements); - } else if (additionalModuleRuntimeRequirements.isUsed()) { - set = new Set(); - } else { - if (memCache) { - memCache.set( - `moduleRuntimeRequirements-${getRuntimeKey(runtime)}`, - null - ); - } - continue; - } - additionalModuleRuntimeRequirements.call(module, set, context); +/** + * @param {OutputFileSystem} fs filesystem + * @param {string} filename path to file + * @param {StatsCallback} callback callback for provided filename + * @returns {void} + */ +const doStat = (fs, filename, callback) => { + if ("lstat" in fs) { + fs.lstat(filename, callback); + } else { + fs.stat(filename, callback); + } +}; - for (const r of set) { - const hook = runtimeRequirementInModule.get(r); - if (hook !== undefined) hook.call(module, set, context); +/** + * @param {OutputFileSystem} fs filesystem + * @param {string} outputPath output path + * @param {boolean} dry only log instead of fs modification + * @param {Logger} logger logger + * @param {Set} diff filenames of the assets that shouldn't be there + * @param {function(string): boolean} isKept check if the entry is ignored + * @param {function(Error=): void} callback callback + * @returns {void} + */ +const applyDiff = (fs, outputPath, dry, logger, diff, isKept, callback) => { + const log = msg => { + if (dry) { + logger.info(msg); + } else { + logger.log(msg); + } + }; + /** @typedef {{ type: "check" | "unlink" | "rmdir", filename: string, parent: { remaining: number, job: Job } | undefined }} Job */ + /** @type {Job[]} */ + const jobs = Array.from(diff, filename => ({ + type: "check", + filename, + parent: undefined + })); + processAsyncTree( + jobs, + 10, + ({ type, filename, parent }, push, callback) => { + const handleError = err => { + if (err.code === "ENOENT") { + log(`${filename} was removed during cleaning by something else`); + handleParent(); + return callback(); + } + return callback(err); + }; + const handleParent = () => { + if (parent && --parent.remaining === 0) push(parent.job); + }; + const path = join(fs, outputPath, filename); + switch (type) { + case "check": + if (isKept(filename)) { + // do not decrement parent entry as we don't want to delete the parent + log(`${filename} will be kept`); + return process.nextTick(callback); } - if (set.size === 0) { - if (memCache) { - memCache.set( - `moduleRuntimeRequirements-${getRuntimeKey(runtime)}`, - null - ); - } - } else { - if (memCache) { - memCache.set( - `moduleRuntimeRequirements-${getRuntimeKey(runtime)}`, - set - ); - chunkGraph.addModuleRuntimeRequirements( - module, - runtime, - set, - false - ); - } else { - chunkGraph.addModuleRuntimeRequirements(module, runtime, set); + doStat(fs, path, (err, stats) => { + if (err) return handleError(err); + if (!stats.isDirectory()) { + push({ + type: "unlink", + filename, + parent + }); + return callback(); } + fs.readdir(path, (err, entries) => { + if (err) return handleError(err); + /** @type {Job} */ + const deleteJob = { + type: "rmdir", + filename, + parent + }; + if (entries.length === 0) { + push(deleteJob); + } else { + const parentToken = { + remaining: entries.length, + job: deleteJob + }; + for (const entry of entries) { + const file = /** @type {string} */ (entry); + if (file.startsWith(".")) { + log( + `${filename} will be kept (dot-files will never be removed)` + ); + continue; + } + push({ + type: "check", + filename: `${filename}/${file}`, + parent: parentToken + }); + } + } + return callback(); + }); + }); + break; + case "rmdir": + log(`${filename} will be removed`); + if (dry) { + handleParent(); + return process.nextTick(callback); } - } - } - } - this.logger.timeEnd("runtime requirements.modules"); - - this.logger.time("runtime requirements.chunks"); - for (const chunk of chunks) { - const set = new Set(); - for (const module of chunkGraph.getChunkModulesIterable(chunk)) { - const runtimeRequirements = chunkGraph.getModuleRuntimeRequirements( - module, - chunk.runtime - ); - for (const r of runtimeRequirements) set.add(r); - } - this.hooks.additionalChunkRuntimeRequirements.call(chunk, set, context); - - for (const r of set) { - this.hooks.runtimeRequirementInChunk.for(r).call(chunk, set, context); + if (!fs.rmdir) { + logger.warn( + `${filename} can't be removed because output file system doesn't support removing directories (rmdir)` + ); + return process.nextTick(callback); + } + fs.rmdir(path, err => { + if (err) return handleError(err); + handleParent(); + callback(); + }); + break; + case "unlink": + log(`${filename} will be removed`); + if (dry) { + handleParent(); + return process.nextTick(callback); + } + if (!fs.unlink) { + logger.warn( + `${filename} can't be removed because output file system doesn't support removing files (rmdir)` + ); + return process.nextTick(callback); + } + fs.unlink(path, err => { + if (err) return handleError(err); + handleParent(); + callback(); + }); + break; } + }, + callback + ); +}; - chunkGraph.addChunkRuntimeRequirements(chunk, set); - } - this.logger.timeEnd("runtime requirements.chunks"); - - this.logger.time("runtime requirements.entries"); - for (const treeEntry of chunkGraphEntries) { - const set = new Set(); - for (const chunk of treeEntry.getAllReferencedChunks()) { - const runtimeRequirements = - chunkGraph.getChunkRuntimeRequirements(chunk); - for (const r of runtimeRequirements) set.add(r); - } +/** @type {WeakMap} */ +const compilationHooksMap = new WeakMap(); - this.hooks.additionalTreeRuntimeRequirements.call( - treeEntry, - set, - context +class CleanPlugin { + /** + * @param {Compilation} compilation the compilation + * @returns {CleanPluginCompilationHooks} the attached hooks + */ + static getCompilationHooks(compilation) { + if (!(compilation instanceof Compilation)) { + throw new TypeError( + "The 'compilation' argument must be an instance of Compilation" ); - - for (const r of set) { - this.hooks.runtimeRequirementInTree - .for(r) - .call(treeEntry, set, context); - } - - chunkGraph.addTreeRuntimeRequirements(treeEntry, set); } - this.logger.timeEnd("runtime requirements.entries"); + let hooks = compilationHooksMap.get(compilation); + if (hooks === undefined) { + hooks = { + /** @type {SyncBailHook<[string], boolean>} */ + keep: new SyncBailHook(["ignore"]) + }; + compilationHooksMap.set(compilation, hooks); + } + return hooks; + } + + /** @param {CleanOptions} options options */ + constructor(options = {}) { + validate(options); + this.options = { dry: false, ...options }; } - // TODO webpack 6 make chunkGraph argument non-optional /** - * @param {Chunk} chunk target chunk - * @param {RuntimeModule} module runtime module - * @param {ChunkGraph} chunkGraph the chunk graph + * Apply the plugin + * @param {Compiler} compiler the compiler instance * @returns {void} */ - addRuntimeModule(chunk, module, chunkGraph = this.chunkGraph) { - // Deprecated ModuleGraph association - if (this._backCompat) - ModuleGraph.setModuleGraphForModule(module, this.moduleGraph); - - // add it to the list - this.modules.add(module); - this._modules.set(module.identifier(), module); - - // connect to the chunk graph - chunkGraph.connectChunkAndModule(chunk, module); - chunkGraph.connectChunkAndRuntimeModule(chunk, module); - if (module.fullHash) { - chunkGraph.addFullHashModuleToChunk(chunk, module); - } else if (module.dependentHash) { - chunkGraph.addDependentHashModuleToChunk(chunk, module); - } - - // attach runtime module - module.attach(this, chunk, chunkGraph); + apply(compiler) { + const { dry, keep } = this.options; - // Setup internals - const exportsInfo = this.moduleGraph.getExportsInfo(module); - exportsInfo.setHasProvideInfo(); - if (typeof chunk.runtime === "string") { - exportsInfo.setUsedForSideEffectsOnly(chunk.runtime); - } else if (chunk.runtime === undefined) { - exportsInfo.setUsedForSideEffectsOnly(undefined); - } else { - for (const runtime of chunk.runtime) { - exportsInfo.setUsedForSideEffectsOnly(runtime); - } - } - chunkGraph.addModuleRuntimeRequirements( - module, - chunk.runtime, - new Set([RuntimeGlobals.requireScope]) - ); + const keepFn = + typeof keep === "function" + ? keep + : typeof keep === "string" + ? path => path.startsWith(keep) + : typeof keep === "object" && keep.test + ? path => keep.test(path) + : () => false; - // runtime modules don't need ids - chunkGraph.setModuleId(module, ""); + // We assume that no external modification happens while the compiler is active + // So we can store the old assets and only diff to them to avoid fs access on + // incremental builds + let oldAssets; - // Call hook - this.hooks.runtimeModule.call(module, chunk); - } + compiler.hooks.emit.tapAsync( + { + name: "CleanPlugin", + stage: 100 + }, + (compilation, callback) => { + const hooks = CleanPlugin.getCompilationHooks(compilation); + const logger = compilation.getLogger("webpack.CleanPlugin"); + const fs = compiler.outputFileSystem; - /** - * @param {string | ChunkGroupOptions} groupOptions options for the chunk group - * @param {Module} module the module the references the chunk group - * @param {DependencyLocation} loc the location from with the chunk group is referenced (inside of module) - * @param {string} request the request from which the the chunk group is referenced - * @returns {ChunkGroup} the new or existing chunk group - */ - addChunkInGroup(groupOptions, module, loc, request) { - if (typeof groupOptions === "string") { - groupOptions = { name: groupOptions }; - } - const name = groupOptions.name; + if (!fs.readdir) { + return callback( + new Error( + "CleanPlugin: Output filesystem doesn't support listing directories (readdir)" + ) + ); + } - if (name) { - const chunkGroup = this.namedChunkGroups.get(name); - if (chunkGroup !== undefined) { - chunkGroup.addOptions(groupOptions); - if (module) { - chunkGroup.addOrigin(module, loc, request); + const currentAssets = new Set(); + for (const asset of Object.keys(compilation.assets)) { + if (/^[A-Za-z]:\\|^\/|^\\\\/.test(asset)) continue; + let normalizedAsset; + let newNormalizedAsset = asset.replace(/\\/g, "/"); + do { + normalizedAsset = newNormalizedAsset; + newNormalizedAsset = normalizedAsset.replace( + /(^|\/)(?!\.\.)[^/]+\/\.\.\//g, + "$1" + ); + } while (newNormalizedAsset !== normalizedAsset); + if (normalizedAsset.startsWith("../")) continue; + currentAssets.add(normalizedAsset); } - return chunkGroup; - } - } - const chunkGroup = new ChunkGroup(groupOptions); - if (module) chunkGroup.addOrigin(module, loc, request); - const chunk = this.addChunk(name); - connectChunkGroupAndChunk(chunkGroup, chunk); + const outputPath = compilation.getPath(compiler.outputPath, {}); - this.chunkGroups.push(chunkGroup); - if (name) { - this.namedChunkGroups.set(name, chunkGroup); - } - return chunkGroup; - } + const isKept = path => { + const result = hooks.keep.call(path); + if (result !== undefined) return result; + return keepFn(path); + }; - /** - * @param {EntryOptions} options options for the entrypoint - * @param {Module} module the module the references the chunk group - * @param {DependencyLocation} loc the location from with the chunk group is referenced (inside of module) - * @param {string} request the request from which the the chunk group is referenced - * @returns {Entrypoint} the new or existing entrypoint - */ - addAsyncEntrypoint(options, module, loc, request) { - const name = options.name; - if (name) { - const entrypoint = this.namedChunkGroups.get(name); - if (entrypoint instanceof Entrypoint) { - if (entrypoint !== undefined) { - if (module) { - entrypoint.addOrigin(module, loc, request); + const diffCallback = (err, diff) => { + if (err) { + oldAssets = undefined; + return callback(err); } - return entrypoint; + applyDiff(fs, outputPath, dry, logger, diff, isKept, err => { + if (err) { + oldAssets = undefined; + } else { + oldAssets = currentAssets; + } + callback(err); + }); + }; + + if (oldAssets) { + diffCallback(null, getDiffToOldAssets(currentAssets, oldAssets)); + } else { + getDiffToFs(fs, outputPath, currentAssets, diffCallback); } - } else if (entrypoint) { - throw new Error( - `Cannot add an async entrypoint with the name '${name}', because there is already an chunk group with this name` - ); } - } - const chunk = this.addChunk(name); - if (options.filename) { - chunk.filenameTemplate = options.filename; - } - const entrypoint = new Entrypoint(options, false); - entrypoint.setRuntimeChunk(chunk); - entrypoint.setEntrypointChunk(chunk); - if (name) { - this.namedChunkGroups.set(name, entrypoint); - } - this.chunkGroups.push(entrypoint); - this.asyncEntrypoints.push(entrypoint); - connectChunkGroupAndChunk(entrypoint, chunk); - if (module) { - entrypoint.addOrigin(module, loc, request); - } - return entrypoint; + ); } +} - /** - * This method first looks to see if a name is provided for a new chunk, - * and first looks to see if any named chunks already exist and reuse that chunk instead. - * - * @param {string=} name optional chunk name to be provided - * @returns {Chunk} create a chunk (invoked during seal event) - */ - addChunk(name) { - if (name) { - const chunk = this.namedChunks.get(name); - if (chunk !== undefined) { - return chunk; - } - } - const chunk = new Chunk(name, this._backCompat); - this.chunks.add(chunk); - if (this._backCompat) - ChunkGraph.setChunkGraphForChunk(chunk, this.chunkGraph); - if (name) { - this.namedChunks.set(name, chunk); - } - return chunk; - } +module.exports = CleanPlugin; - /** - * @deprecated - * @param {Module} module module to assign depth - * @returns {void} - */ - assignDepth(module) { - const moduleGraph = this.moduleGraph; - const queue = new Set([module]); - let depth; +/***/ }), - moduleGraph.setDepth(module, 0); +/***/ 43604: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - /** - * @param {Module} module module for processing - * @returns {void} - */ - const processModule = module => { - if (!moduleGraph.setDepthIfLower(module, depth)) return; - queue.add(module); - }; +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ - for (module of queue) { - queue.delete(module); - depth = moduleGraph.getDepth(module) + 1; - for (const connection of moduleGraph.getOutgoingConnections(module)) { - const refModule = connection.module; - if (refModule) { - processModule(refModule); - } - } - } - } +const WebpackError = __webpack_require__(68422); + +/** @typedef {import("./Module")} Module */ + +class CodeGenerationError extends WebpackError { /** - * @param {Set} modules module to assign depth - * @returns {void} + * Create a new CodeGenerationError + * @param {Module} module related module + * @param {Error} error Original error */ - assignDepths(modules) { - const moduleGraph = this.moduleGraph; + constructor(module, error) { + super(); - /** @type {Set} */ - const queue = new Set(modules); - queue.add(1); - let depth = 0; - - let i = 0; - for (const module of queue) { - i++; - if (typeof module === "number") { - depth = module; - if (queue.size === i) return; - queue.add(depth + 1); - } else { - moduleGraph.setDepth(module, depth); - for (const { module: refModule } of moduleGraph.getOutgoingConnections( - module - )) { - if (refModule) { - queue.add(refModule); - } - } - } - } + this.name = "CodeGenerationError"; + this.error = error; + this.message = error.message; + this.details = error.stack; + this.module = module; } +} + +module.exports = CodeGenerationError; + + +/***/ }), + +/***/ 74841: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ + + + +const { provide } = __webpack_require__(30498); +const { first } = __webpack_require__(34715); +const createHash = __webpack_require__(24123); +const { runtimeToString, RuntimeSpecMap } = __webpack_require__(19655); + +/** @typedef {import("webpack-sources").Source} Source */ +/** @typedef {import("./Module")} Module */ +/** @typedef {import("./Module").CodeGenerationResult} CodeGenerationResult */ +/** @typedef {typeof import("./util/Hash")} Hash */ +/** @typedef {import("./util/runtime").RuntimeSpec} RuntimeSpec */ +class CodeGenerationResults { /** - * @param {Dependency} dependency the dependency - * @param {RuntimeSpec} runtime the runtime - * @returns {(string[] | ReferencedExport)[]} referenced exports + * @param {string | Hash} hashFunction the hash function to use */ - getDependencyReferencedExports(dependency, runtime) { - const referencedExports = dependency.getReferencedExports( - this.moduleGraph, - runtime - ); - return this.hooks.dependencyReferencedExports.call( - referencedExports, - dependency, - runtime - ); + constructor(hashFunction = "md4") { + /** @type {Map>} */ + this.map = new Map(); + this._hashFunction = hashFunction; } /** - * - * @param {Module} module module relationship for removal - * @param {DependenciesBlockLike} block //TODO: good description - * @returns {void} + * @param {Module} module the module + * @param {RuntimeSpec} runtime runtime(s) + * @returns {CodeGenerationResult} the CodeGenerationResult */ - removeReasonsOfDependencyBlock(module, block) { - if (block.blocks) { - for (const b of block.blocks) { - this.removeReasonsOfDependencyBlock(module, b); - } + get(module, runtime) { + const entry = this.map.get(module); + if (entry === undefined) { + throw new Error( + `No code generation entry for ${module.identifier()} (existing entries: ${Array.from( + this.map.keys(), + m => m.identifier() + ).join(", ")})` + ); } - - if (block.dependencies) { - for (const dep of block.dependencies) { - const originalModule = this.moduleGraph.getModule(dep); - if (originalModule) { - this.moduleGraph.removeConnection(dep); - - if (this.chunkGraph) { - for (const chunk of this.chunkGraph.getModuleChunks( - originalModule - )) { - this.patchChunksAfterReasonRemoval(originalModule, chunk); - } - } + if (runtime === undefined) { + if (entry.size > 1) { + const results = new Set(entry.values()); + if (results.size !== 1) { + throw new Error( + `No unique code generation entry for unspecified runtime for ${module.identifier()} (existing runtimes: ${Array.from( + entry.keys(), + r => runtimeToString(r) + ).join(", ")}). +Caller might not support runtime-dependent code generation (opt-out via optimization.usedExports: "global").` + ); } + return first(results); } + return entry.values().next().value; + } + const result = entry.get(runtime); + if (result === undefined) { + throw new Error( + `No code generation entry for runtime ${runtimeToString( + runtime + )} for ${module.identifier()} (existing runtimes: ${Array.from( + entry.keys(), + r => runtimeToString(r) + ).join(", ")})` + ); } + return result; } /** - * @param {Module} module module to patch tie - * @param {Chunk} chunk chunk to patch tie - * @returns {void} + * @param {Module} module the module + * @param {RuntimeSpec} runtime runtime(s) + * @returns {boolean} true, when we have data for this */ - patchChunksAfterReasonRemoval(module, chunk) { - if (!module.hasReasons(this.moduleGraph, chunk.runtime)) { - this.removeReasonsOfDependencyBlock(module, module); + has(module, runtime) { + const entry = this.map.get(module); + if (entry === undefined) { + return false; } - if (!module.hasReasonForChunk(chunk, this.moduleGraph, this.chunkGraph)) { - if (this.chunkGraph.isModuleInChunk(module, chunk)) { - this.chunkGraph.disconnectChunkAndModule(chunk, module); - this.removeChunkFromDependencies(module, chunk); - } + if (runtime !== undefined) { + return entry.has(runtime); + } else if (entry.size > 1) { + const results = new Set(entry.values()); + return results.size === 1; + } else { + return entry.size === 1; } } /** - * - * @param {DependenciesBlock} block block tie for Chunk - * @param {Chunk} chunk chunk to remove from dep - * @returns {void} + * @param {Module} module the module + * @param {RuntimeSpec} runtime runtime(s) + * @param {string} sourceType the source type + * @returns {Source} a source */ - removeChunkFromDependencies(block, chunk) { - /** - * @param {Dependency} d dependency to (maybe) patch up - */ - const iteratorDependency = d => { - const depModule = this.moduleGraph.getModule(d); - if (!depModule) { - return; - } - this.patchChunksAfterReasonRemoval(depModule, chunk); - }; + getSource(module, runtime, sourceType) { + return this.get(module, runtime).sources.get(sourceType); + } - const blocks = block.blocks; - for (let indexBlock = 0; indexBlock < blocks.length; indexBlock++) { - const asyncBlock = blocks[indexBlock]; - const chunkGroup = this.chunkGraph.getBlockChunkGroup(asyncBlock); - // Grab all chunks from the first Block's AsyncDepBlock - const chunks = chunkGroup.chunks; - // For each chunk in chunkGroup - for (let indexChunk = 0; indexChunk < chunks.length; indexChunk++) { - const iteratedChunk = chunks[indexChunk]; - chunkGroup.removeChunk(iteratedChunk); - // Recurse - this.removeChunkFromDependencies(block, iteratedChunk); - } - } + /** + * @param {Module} module the module + * @param {RuntimeSpec} runtime runtime(s) + * @returns {ReadonlySet} runtime requirements + */ + getRuntimeRequirements(module, runtime) { + return this.get(module, runtime).runtimeRequirements; + } - if (block.dependencies) { - for (const dep of block.dependencies) iteratorDependency(dep); - } + /** + * @param {Module} module the module + * @param {RuntimeSpec} runtime runtime(s) + * @param {string} key data key + * @returns {any} data generated by code generation + */ + getData(module, runtime, key) { + const data = this.get(module, runtime).data; + return data === undefined ? undefined : data.get(key); } - assignRuntimeIds() { - const { chunkGraph } = this; - const processEntrypoint = ep => { - const runtime = ep.options.runtime || ep.name; - const chunk = ep.getRuntimeChunk(); - chunkGraph.setRuntimeId(runtime, chunk.id); - }; - for (const ep of this.entrypoints.values()) { - processEntrypoint(ep); + /** + * @param {Module} module the module + * @param {RuntimeSpec} runtime runtime(s) + * @returns {any} hash of the code generation + */ + getHash(module, runtime) { + const info = this.get(module, runtime); + if (info.hash !== undefined) return info.hash; + const hash = createHash(this._hashFunction); + for (const [type, source] of info.sources) { + hash.update(type); + source.updateHash(hash); } - for (const ep of this.asyncEntrypoints) { - processEntrypoint(ep); + if (info.runtimeRequirements) { + for (const rr of info.runtimeRequirements) hash.update(rr); } + return (info.hash = /** @type {string} */ (hash.digest("hex"))); } - sortItemsWithChunkIds() { - for (const chunkGroup of this.chunkGroups) { - chunkGroup.sortItems(); - } - - this.errors.sort(compareErrors); - this.warnings.sort(compareErrors); - this.children.sort(byNameOrHash); + /** + * @param {Module} module the module + * @param {RuntimeSpec} runtime runtime(s) + * @param {CodeGenerationResult} result result from module + * @returns {void} + */ + add(module, runtime, result) { + const map = provide(this.map, module, () => new RuntimeSpecMap()); + map.set(runtime, result); } +} - summarizeDependencies() { - for ( - let indexChildren = 0; - indexChildren < this.children.length; - indexChildren++ - ) { - const child = this.children[indexChildren]; +module.exports = CodeGenerationResults; - this.fileDependencies.addAll(child.fileDependencies); - this.contextDependencies.addAll(child.contextDependencies); - this.missingDependencies.addAll(child.missingDependencies); - this.buildDependencies.addAll(child.buildDependencies); - } - for (const module of this.modules) { - module.addCacheDependencies( - this.fileDependencies, - this.contextDependencies, - this.missingDependencies, - this.buildDependencies - ); - } - } +/***/ }), - createModuleHashes() { - let statModulesHashed = 0; - let statModulesFromCache = 0; - const { chunkGraph, runtimeTemplate, moduleMemCaches2 } = this; - const { hashFunction, hashDigest, hashDigestLength } = this.outputOptions; - for (const module of this.modules) { - const memCache = moduleMemCaches2 && moduleMemCaches2.get(module); - for (const runtime of chunkGraph.getModuleRuntimes(module)) { - if (memCache) { - const digest = memCache.get(`moduleHash-${getRuntimeKey(runtime)}`); - if (digest !== undefined) { - chunkGraph.setModuleHashes( - module, - runtime, - digest, - digest.substr(0, hashDigestLength) - ); - statModulesFromCache++; - continue; - } - } - statModulesHashed++; - const digest = this._createModuleHash( - module, - chunkGraph, - runtime, - hashFunction, - runtimeTemplate, - hashDigest, - hashDigestLength - ); - if (memCache) { - memCache.set(`moduleHash-${getRuntimeKey(runtime)}`, digest); - } - } - } - this.logger.log( - `${statModulesHashed} modules hashed, ${statModulesFromCache} from cache (${ - Math.round( - (100 * (statModulesHashed + statModulesFromCache)) / this.modules.size - ) / 100 - } variants per module in average)` - ); - } +/***/ 28151: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - _createModuleHash( - module, - chunkGraph, - runtime, - hashFunction, - runtimeTemplate, - hashDigest, - hashDigestLength - ) { - const moduleHash = createHash(hashFunction); - module.updateHash(moduleHash, { - chunkGraph, - runtime, - runtimeTemplate - }); - const moduleHashDigest = /** @type {string} */ ( - moduleHash.digest(hashDigest) - ); - chunkGraph.setModuleHashes( - module, - runtime, - moduleHashDigest, - moduleHashDigest.substr(0, hashDigestLength) - ); - return moduleHashDigest; - } +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ - createHash() { - this.logger.time("hashing: initialize hash"); - const chunkGraph = this.chunkGraph; - const runtimeTemplate = this.runtimeTemplate; - const outputOptions = this.outputOptions; - const hashFunction = outputOptions.hashFunction; - const hashDigest = outputOptions.hashDigest; - const hashDigestLength = outputOptions.hashDigestLength; - const hash = createHash(hashFunction); - if (outputOptions.hashSalt) { - hash.update(outputOptions.hashSalt); - } - this.logger.timeEnd("hashing: initialize hash"); - if (this.children.length > 0) { - this.logger.time("hashing: hash child compilations"); - for (const child of this.children) { - hash.update(child.hash); - } - this.logger.timeEnd("hashing: hash child compilations"); - } - if (this.warnings.length > 0) { - this.logger.time("hashing: hash warnings"); - for (const warning of this.warnings) { - hash.update(`${warning.message}`); - } - this.logger.timeEnd("hashing: hash warnings"); - } - if (this.errors.length > 0) { - this.logger.time("hashing: hash errors"); - for (const error of this.errors) { - hash.update(`${error.message}`); - } - this.logger.timeEnd("hashing: hash errors"); - } - this.logger.time("hashing: sort chunks"); - /* - * all non-runtime chunks need to be hashes first, - * since runtime chunk might use their hashes. - * runtime chunks need to be hashed in the correct order - * since they may depend on each other (for async entrypoints). - * So we put all non-runtime chunks first and hash them in any order. - * And order runtime chunks according to referenced between each other. - * Chunks need to be in deterministic order since we add hashes to full chunk - * during these hashing. - */ - /** @type {Chunk[]} */ - const unorderedRuntimeChunks = []; - /** @type {Chunk[]} */ - const otherChunks = []; - for (const c of this.chunks) { - if (c.hasRuntime()) { - unorderedRuntimeChunks.push(c); - } else { - otherChunks.push(c); - } - } - unorderedRuntimeChunks.sort(byId); - otherChunks.sort(byId); - /** @typedef {{ chunk: Chunk, referencedBy: RuntimeChunkInfo[], remaining: number }} RuntimeChunkInfo */ - /** @type {Map} */ - const runtimeChunksMap = new Map(); - for (const chunk of unorderedRuntimeChunks) { - runtimeChunksMap.set(chunk, { - chunk, - referencedBy: [], - remaining: 0 - }); - } - let remaining = 0; - for (const info of runtimeChunksMap.values()) { - for (const other of new Set( - Array.from(info.chunk.getAllReferencedAsyncEntrypoints()).map( - e => e.chunks[e.chunks.length - 1] - ) - )) { - const otherInfo = runtimeChunksMap.get(other); - otherInfo.referencedBy.push(info); - info.remaining++; - remaining++; - } - } - /** @type {Chunk[]} */ - const runtimeChunks = []; - for (const info of runtimeChunksMap.values()) { - if (info.remaining === 0) { - runtimeChunks.push(info.chunk); - } - } - // If there are any references between chunks - // make sure to follow these chains - if (remaining > 0) { - const readyChunks = []; - for (const chunk of runtimeChunks) { - const hasFullHashModules = - chunkGraph.getNumberOfChunkFullHashModules(chunk) !== 0; - const info = runtimeChunksMap.get(chunk); - for (const otherInfo of info.referencedBy) { - if (hasFullHashModules) { - chunkGraph.upgradeDependentToFullHashModules(otherInfo.chunk); - } - remaining--; - if (--otherInfo.remaining === 0) { - readyChunks.push(otherInfo.chunk); - } - } - if (readyChunks.length > 0) { - // This ensures deterministic ordering, since referencedBy is non-deterministic - readyChunks.sort(byId); - for (const c of readyChunks) runtimeChunks.push(c); - readyChunks.length = 0; - } - } - } - // If there are still remaining references we have cycles and want to create a warning - if (remaining > 0) { - let circularRuntimeChunkInfo = []; - for (const info of runtimeChunksMap.values()) { - if (info.remaining !== 0) { - circularRuntimeChunkInfo.push(info); - } - } - circularRuntimeChunkInfo.sort(compareSelect(i => i.chunk, byId)); - const err = - new WebpackError(`Circular dependency between chunks with runtime (${Array.from( - circularRuntimeChunkInfo, - c => c.chunk.name || c.chunk.id - ).join(", ")}) -This prevents using hashes of each other and should be avoided.`); - err.chunk = circularRuntimeChunkInfo[0].chunk; - this.warnings.push(err); - for (const i of circularRuntimeChunkInfo) runtimeChunks.push(i.chunk); - } - this.logger.timeEnd("hashing: sort chunks"); +const WebpackError = __webpack_require__(68422); +const makeSerializable = __webpack_require__(26522); - const fullHashChunks = new Set(); - /** @type {{module: Module, hash: string, runtime: RuntimeSpec, runtimes: RuntimeSpec[]}[]} */ - const codeGenerationJobs = []; - /** @type {Map>} */ - const codeGenerationJobsMap = new Map(); +/** @typedef {import("./Dependency").DependencyLocation} DependencyLocation */ - const processChunk = chunk => { - // Last minute module hash generation for modules that depend on chunk hashes - this.logger.time("hashing: hash runtime modules"); - const runtime = chunk.runtime; - for (const module of chunkGraph.getChunkModulesIterable(chunk)) { - if (!chunkGraph.hasModuleHashes(module, runtime)) { - const hash = this._createModuleHash( - module, - chunkGraph, - runtime, - hashFunction, - runtimeTemplate, - hashDigest, - hashDigestLength - ); - let hashMap = codeGenerationJobsMap.get(hash); - if (hashMap) { - const moduleJob = hashMap.get(module); - if (moduleJob) { - moduleJob.runtimes.push(runtime); - continue; - } - } else { - hashMap = new Map(); - codeGenerationJobsMap.set(hash, hashMap); - } - const job = { - module, - hash, - runtime, - runtimes: [runtime] - }; - hashMap.set(module, job); - codeGenerationJobs.push(job); - } - } - this.logger.timeAggregate("hashing: hash runtime modules"); - this.logger.time("hashing: hash chunks"); - const chunkHash = createHash(hashFunction); - try { - if (outputOptions.hashSalt) { - chunkHash.update(outputOptions.hashSalt); - } - chunk.updateHash(chunkHash, chunkGraph); - this.hooks.chunkHash.call(chunk, chunkHash, { - chunkGraph, - moduleGraph: this.moduleGraph, - runtimeTemplate: this.runtimeTemplate - }); - const chunkHashDigest = /** @type {string} */ ( - chunkHash.digest(hashDigest) - ); - hash.update(chunkHashDigest); - chunk.hash = chunkHashDigest; - chunk.renderedHash = chunk.hash.substr(0, hashDigestLength); - const fullHashModules = - chunkGraph.getChunkFullHashModulesIterable(chunk); - if (fullHashModules) { - fullHashChunks.add(chunk); - } else { - this.hooks.contentHash.call(chunk); - } - } catch (err) { - this.errors.push(new ChunkRenderError(chunk, "", err)); - } - this.logger.timeAggregate("hashing: hash chunks"); - }; - otherChunks.forEach(processChunk); - for (const chunk of runtimeChunks) processChunk(chunk); +class CommentCompilationWarning extends WebpackError { + /** + * + * @param {string} message warning message + * @param {DependencyLocation} loc affected lines of code + */ + constructor(message, loc) { + super(message); - this.logger.timeAggregateEnd("hashing: hash runtime modules"); - this.logger.timeAggregateEnd("hashing: hash chunks"); - this.logger.time("hashing: hash digest"); - this.hooks.fullHash.call(hash); - this.fullHash = /** @type {string} */ (hash.digest(hashDigest)); - this.hash = this.fullHash.substr(0, hashDigestLength); - this.logger.timeEnd("hashing: hash digest"); + this.name = "CommentCompilationWarning"; - this.logger.time("hashing: process full hash modules"); - for (const chunk of fullHashChunks) { - for (const module of chunkGraph.getChunkFullHashModulesIterable(chunk)) { - const moduleHash = createHash(hashFunction); - module.updateHash(moduleHash, { - chunkGraph, - runtime: chunk.runtime, - runtimeTemplate - }); - const moduleHashDigest = /** @type {string} */ ( - moduleHash.digest(hashDigest) - ); - const oldHash = chunkGraph.getModuleHash(module, chunk.runtime); - chunkGraph.setModuleHashes( - module, - chunk.runtime, - moduleHashDigest, - moduleHashDigest.substr(0, hashDigestLength) - ); - codeGenerationJobsMap.get(oldHash).get(module).hash = moduleHashDigest; - } - const chunkHash = createHash(hashFunction); - chunkHash.update(chunk.hash); - chunkHash.update(this.hash); - const chunkHashDigest = /** @type {string} */ ( - chunkHash.digest(hashDigest) - ); - chunk.hash = chunkHashDigest; - chunk.renderedHash = chunk.hash.substr(0, hashDigestLength); - this.hooks.contentHash.call(chunk); - } - this.logger.timeEnd("hashing: process full hash modules"); - return codeGenerationJobs; + this.loc = loc; } +} + +makeSerializable( + CommentCompilationWarning, + "webpack/lib/CommentCompilationWarning" +); + +module.exports = CommentCompilationWarning; + + +/***/ }), + +/***/ 27847: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ + + +const ConstDependency = __webpack_require__(60864); + +/** @typedef {import("./Compiler")} Compiler */ +/** @typedef {import("./javascript/JavascriptParser")} JavascriptParser */ + +const nestedWebpackRequireTag = Symbol("nested __webpack_require__"); + +class CompatibilityPlugin { /** - * @param {string} file file name - * @param {Source} source asset source - * @param {AssetInfo} assetInfo extra asset information + * Apply the plugin + * @param {Compiler} compiler the compiler instance * @returns {void} */ - emitAsset(file, source, assetInfo = {}) { - if (this.assets[file]) { - if (!isSourceEqual(this.assets[file], source)) { - this.errors.push( - new WebpackError( - `Conflict: Multiple assets emit different content to the same filename ${file}` - ) + apply(compiler) { + compiler.hooks.compilation.tap( + "CompatibilityPlugin", + (compilation, { normalModuleFactory }) => { + compilation.dependencyTemplates.set( + ConstDependency, + new ConstDependency.Template() ); - this.assets[file] = source; - this._setAssetInfo(file, assetInfo); - return; - } - const oldInfo = this.assetsInfo.get(file); - const newInfo = Object.assign({}, oldInfo, assetInfo); - this._setAssetInfo(file, newInfo, oldInfo); - return; - } - this.assets[file] = source; - this._setAssetInfo(file, assetInfo, undefined); - } - _setAssetInfo(file, newInfo, oldInfo = this.assetsInfo.get(file)) { - if (newInfo === undefined) { - this.assetsInfo.delete(file); - } else { - this.assetsInfo.set(file, newInfo); - } - const oldRelated = oldInfo && oldInfo.related; - const newRelated = newInfo && newInfo.related; - if (oldRelated) { - for (const key of Object.keys(oldRelated)) { - const remove = name => { - const relatedIn = this._assetsRelatedIn.get(name); - if (relatedIn === undefined) return; - const entry = relatedIn.get(key); - if (entry === undefined) return; - entry.delete(file); - if (entry.size !== 0) return; - relatedIn.delete(key); - if (relatedIn.size === 0) this._assetsRelatedIn.delete(name); - }; - const entry = oldRelated[key]; - if (Array.isArray(entry)) { - entry.forEach(remove); - } else if (entry) { - remove(entry); - } - } - } - if (newRelated) { - for (const key of Object.keys(newRelated)) { - const add = name => { - let relatedIn = this._assetsRelatedIn.get(name); - if (relatedIn === undefined) { - this._assetsRelatedIn.set(name, (relatedIn = new Map())); - } - let entry = relatedIn.get(key); - if (entry === undefined) { - relatedIn.set(key, (entry = new Set())); - } - entry.add(file); - }; - const entry = newRelated[key]; - if (Array.isArray(entry)) { - entry.forEach(add); - } else if (entry) { - add(entry); - } - } - } - } + normalModuleFactory.hooks.parser + .for("javascript/auto") + .tap("CompatibilityPlugin", (parser, parserOptions) => { + if ( + parserOptions.browserify !== undefined && + !parserOptions.browserify + ) + return; - /** - * @param {string} file file name - * @param {Source | function(Source): Source} newSourceOrFunction new asset source or function converting old to new - * @param {AssetInfo | function(AssetInfo | undefined): AssetInfo} assetInfoUpdateOrFunction new asset info or function converting old to new - */ - updateAsset( - file, - newSourceOrFunction, - assetInfoUpdateOrFunction = undefined - ) { - if (!this.assets[file]) { - throw new Error( - `Called Compilation.updateAsset for not existing filename ${file}` - ); - } - if (typeof newSourceOrFunction === "function") { - this.assets[file] = newSourceOrFunction(this.assets[file]); - } else { - this.assets[file] = newSourceOrFunction; - } - if (assetInfoUpdateOrFunction !== undefined) { - const oldInfo = this.assetsInfo.get(file) || EMPTY_ASSET_INFO; - if (typeof assetInfoUpdateOrFunction === "function") { - this._setAssetInfo(file, assetInfoUpdateOrFunction(oldInfo), oldInfo); - } else { - this._setAssetInfo( - file, - cachedCleverMerge(oldInfo, assetInfoUpdateOrFunction), - oldInfo - ); - } - } - } + parser.hooks.call + .for("require") + .tap("CompatibilityPlugin", expr => { + // support for browserify style require delegator: "require(o, !0)" + if (expr.arguments.length !== 2) return; + const second = parser.evaluateExpression(expr.arguments[1]); + if (!second.isBoolean()) return; + if (second.asBool() !== true) return; + const dep = new ConstDependency("require", expr.callee.range); + dep.loc = expr.loc; + if (parser.state.current.dependencies.length > 0) { + const last = + parser.state.current.dependencies[ + parser.state.current.dependencies.length - 1 + ]; + if ( + last.critical && + last.options && + last.options.request === "." && + last.userRequest === "." && + last.options.recursive + ) + parser.state.current.dependencies.pop(); + } + parser.state.module.addPresentationalDependency(dep); + return true; + }); + }); - renameAsset(file, newFile) { - const source = this.assets[file]; - if (!source) { - throw new Error( - `Called Compilation.renameAsset for not existing filename ${file}` - ); - } - if (this.assets[newFile]) { - if (!isSourceEqual(this.assets[file], source)) { - this.errors.push( - new WebpackError( - `Conflict: Called Compilation.renameAsset for already existing filename ${newFile} with different content` - ) - ); - } - } - const assetInfo = this.assetsInfo.get(file); - // Update related in all other assets - const relatedInInfo = this._assetsRelatedIn.get(file); - if (relatedInInfo) { - for (const [key, assets] of relatedInInfo) { - for (const name of assets) { - const info = this.assetsInfo.get(name); - if (!info) continue; - const related = info.related; - if (!related) continue; - const entry = related[key]; - let newEntry; - if (Array.isArray(entry)) { - newEntry = entry.map(x => (x === file ? newFile : x)); - } else if (entry === file) { - newEntry = newFile; - } else continue; - this.assetsInfo.set(name, { - ...info, - related: { - ...related, - [key]: newEntry + /** + * @param {JavascriptParser} parser the parser + * @returns {void} + */ + const handler = parser => { + // Handle nested requires + parser.hooks.preStatement.tap("CompatibilityPlugin", statement => { + if ( + statement.type === "FunctionDeclaration" && + statement.id && + statement.id.name === "__webpack_require__" + ) { + const newName = `__nested_webpack_require_${statement.range[0]}__`; + parser.tagVariable(statement.id.name, nestedWebpackRequireTag, { + name: newName, + declaration: { + updated: false, + loc: statement.id.loc, + range: statement.id.range + } + }); + return true; } }); - } - } - } - this._setAssetInfo(file, undefined, assetInfo); - this._setAssetInfo(newFile, assetInfo); - delete this.assets[file]; - this.assets[newFile] = source; - for (const chunk of this.chunks) { - { - const size = chunk.files.size; - chunk.files.delete(file); - if (size !== chunk.files.size) { - chunk.files.add(newFile); - } - } - { - const size = chunk.auxiliaryFiles.size; - chunk.auxiliaryFiles.delete(file); - if (size !== chunk.auxiliaryFiles.size) { - chunk.auxiliaryFiles.add(newFile); - } - } - } - } + parser.hooks.pattern + .for("__webpack_require__") + .tap("CompatibilityPlugin", pattern => { + const newName = `__nested_webpack_require_${pattern.range[0]}__`; + parser.tagVariable(pattern.name, nestedWebpackRequireTag, { + name: newName, + declaration: { + updated: false, + loc: pattern.loc, + range: pattern.range + } + }); + return true; + }); + parser.hooks.expression + .for(nestedWebpackRequireTag) + .tap("CompatibilityPlugin", expr => { + const { name, declaration } = parser.currentTagData; + if (!declaration.updated) { + const dep = new ConstDependency(name, declaration.range); + dep.loc = declaration.loc; + parser.state.module.addPresentationalDependency(dep); + declaration.updated = true; + } + const dep = new ConstDependency(name, expr.range); + dep.loc = expr.loc; + parser.state.module.addPresentationalDependency(dep); + return true; + }); - /** - * @param {string} file file name - */ - deleteAsset(file) { - if (!this.assets[file]) { - return; - } - delete this.assets[file]; - const assetInfo = this.assetsInfo.get(file); - this._setAssetInfo(file, undefined, assetInfo); - const related = assetInfo && assetInfo.related; - if (related) { - for (const key of Object.keys(related)) { - const checkUsedAndDelete = file => { - if (!this._assetsRelatedIn.has(file)) { - this.deleteAsset(file); - } + // Handle hashbang + parser.hooks.program.tap( + "CompatibilityPlugin", + (program, comments) => { + if (comments.length === 0) return; + const c = comments[0]; + if (c.type === "Line" && c.range[0] === 0) { + if (parser.state.source.slice(0, 2).toString() !== "#!") return; + // this is a hashbang comment + const dep = new ConstDependency("//", 0); + dep.loc = c.loc; + parser.state.module.addPresentationalDependency(dep); + } + } + ); }; - const items = related[key]; - if (Array.isArray(items)) { - items.forEach(checkUsedAndDelete); - } else if (items) { - checkUsedAndDelete(items); - } - } - } - // TODO If this becomes a performance problem - // store a reverse mapping from asset to chunk - for (const chunk of this.chunks) { - chunk.files.delete(file); - chunk.auxiliaryFiles.delete(file); - } - } - getAssets() { - /** @type {Readonly[]} */ - const array = []; - for (const assetName of Object.keys(this.assets)) { - if (Object.prototype.hasOwnProperty.call(this.assets, assetName)) { - array.push({ - name: assetName, - source: this.assets[assetName], - info: this.assetsInfo.get(assetName) || EMPTY_ASSET_INFO - }); + normalModuleFactory.hooks.parser + .for("javascript/auto") + .tap("CompatibilityPlugin", handler); + normalModuleFactory.hooks.parser + .for("javascript/dynamic") + .tap("CompatibilityPlugin", handler); + normalModuleFactory.hooks.parser + .for("javascript/esm") + .tap("CompatibilityPlugin", handler); } - } - return array; + ); } +} +module.exports = CompatibilityPlugin; - /** - * @param {string} name the name of the asset - * @returns {Readonly | undefined} the asset or undefined when not found - */ - getAsset(name) { - if (!Object.prototype.hasOwnProperty.call(this.assets, name)) - return undefined; - return { - name, - source: this.assets[name], - info: this.assetsInfo.get(name) || EMPTY_ASSET_INFO - }; - } - clearAssets() { - for (const chunk of this.chunks) { - chunk.files.clear(); - chunk.auxiliaryFiles.clear(); - } - } +/***/ }), - createModuleAssets() { - const { chunkGraph } = this; - for (const module of this.modules) { - if (module.buildInfo.assets) { - const assetsInfo = module.buildInfo.assetsInfo; - for (const assetName of Object.keys(module.buildInfo.assets)) { - const fileName = this.getPath(assetName, { - chunkGraph: this.chunkGraph, - module - }); - for (const chunk of chunkGraph.getModuleChunksIterable(module)) { - chunk.auxiliaryFiles.add(fileName); - } - this.emitAsset( - fileName, - module.buildInfo.assets[assetName], - assetsInfo ? assetsInfo.get(assetName) : undefined - ); - this.hooks.moduleAsset.call(module, fileName); - } - } - } - } - - /** - * @param {RenderManifestOptions} options options object - * @returns {RenderManifestEntry[]} manifest entries - */ - getRenderManifest(options) { - return this.hooks.renderManifest.call([], options); - } - - /** - * @param {Callback} callback signals when the call finishes - * @returns {void} - */ - createChunkAssets(callback) { - const outputOptions = this.outputOptions; - const cachedSourceMap = new WeakMap(); - /** @type {Map} */ - const alreadyWrittenFiles = new Map(); +/***/ 59622: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - asyncLib.forEachLimit( - this.chunks, - 15, - (chunk, callback) => { - /** @type {RenderManifestEntry[]} */ - let manifest; - try { - manifest = this.getRenderManifest({ - chunk, - hash: this.hash, - fullHash: this.fullHash, - outputOptions, - codeGenerationResults: this.codeGenerationResults, - moduleTemplates: this.moduleTemplates, - dependencyTemplates: this.dependencyTemplates, - chunkGraph: this.chunkGraph, - moduleGraph: this.moduleGraph, - runtimeTemplate: this.runtimeTemplate - }); - } catch (err) { - this.errors.push(new ChunkRenderError(chunk, "", err)); - return callback(); - } - asyncLib.forEach( - manifest, - (fileManifest, callback) => { - const ident = fileManifest.identifier; - const usedHash = fileManifest.hash; +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ - const assetCacheItem = this._assetsCache.getItemCache( - ident, - usedHash - ); - assetCacheItem.get((err, sourceFromCache) => { - /** @type {string | function(PathData, AssetInfo=): string} */ - let filenameTemplate; - /** @type {string} */ - let file; - /** @type {AssetInfo} */ - let assetInfo; - let inTry = true; - const errorAndCallback = err => { - const filename = - file || - (typeof file === "string" - ? file - : typeof filenameTemplate === "string" - ? filenameTemplate - : ""); +const asyncLib = __webpack_require__(36386); +const { + HookMap, + SyncHook, + SyncBailHook, + SyncWaterfallHook, + AsyncSeriesHook, + AsyncSeriesBailHook, + AsyncParallelHook +} = __webpack_require__(34718); +const util = __webpack_require__(31669); +const { CachedSource } = __webpack_require__(96192); +const { MultiItemCache } = __webpack_require__(67014); +const Chunk = __webpack_require__(65574); +const ChunkGraph = __webpack_require__(97860); +const ChunkGroup = __webpack_require__(96975); +const ChunkRenderError = __webpack_require__(80187); +const ChunkTemplate = __webpack_require__(50527); +const CodeGenerationError = __webpack_require__(43604); +const CodeGenerationResults = __webpack_require__(74841); +const Dependency = __webpack_require__(50384); +const DependencyTemplates = __webpack_require__(31002); +const Entrypoint = __webpack_require__(86695); +const ErrorHelpers = __webpack_require__(22569); +const FileSystemInfo = __webpack_require__(13679); +const { + connectChunkGroupAndChunk, + connectChunkGroupParentAndChild +} = __webpack_require__(76652); +const { + makeWebpackError, + tryRunOrWebpackError +} = __webpack_require__(89935); +const MainTemplate = __webpack_require__(30518); +const Module = __webpack_require__(85887); +const ModuleDependencyError = __webpack_require__(30549); +const ModuleDependencyWarning = __webpack_require__(61528); +const ModuleGraph = __webpack_require__(20258); +const ModuleNotFoundError = __webpack_require__(82908); +const ModuleProfile = __webpack_require__(69631); +const ModuleRestoreError = __webpack_require__(93106); +const ModuleStoreError = __webpack_require__(84521); +const ModuleTemplate = __webpack_require__(38256); +const RuntimeGlobals = __webpack_require__(49404); +const RuntimeTemplate = __webpack_require__(23974); +const Stats = __webpack_require__(87797); +const WebpackError = __webpack_require__(68422); +const buildChunkGraph = __webpack_require__(21743); +const BuildCycleError = __webpack_require__(1808); +const { Logger, LogType } = __webpack_require__(54667); +const StatsFactory = __webpack_require__(69646); +const StatsPrinter = __webpack_require__(61025); +const { equals: arrayEquals } = __webpack_require__(21537); +const AsyncQueue = __webpack_require__(55531); +const LazySet = __webpack_require__(59534); +const { provide } = __webpack_require__(30498); +const WeakTupleMap = __webpack_require__(73963); +const { cachedCleverMerge } = __webpack_require__(11217); +const { + compareLocations, + concatComparators, + compareSelect, + compareIds, + compareStringsNumeric, + compareModulesByIdentifier +} = __webpack_require__(26296); +const createHash = __webpack_require__(24123); +const { + arrayToSetDeprecation, + soonFrozenObjectDeprecation, + createFakeHook +} = __webpack_require__(2594); +const processAsyncTree = __webpack_require__(76815); +const { getRuntimeKey } = __webpack_require__(19655); +const { isSourceEqual } = __webpack_require__(4002); - this.errors.push(new ChunkRenderError(chunk, filename, err)); - inTry = false; - return callback(); - }; +/** @template T @typedef {import("tapable").AsArray} AsArray */ +/** @typedef {import("webpack-sources").Source} Source */ +/** @typedef {import("../declarations/WebpackOptions").EntryDescriptionNormalized} EntryDescription */ +/** @typedef {import("../declarations/WebpackOptions").OutputNormalized} OutputOptions */ +/** @typedef {import("../declarations/WebpackOptions").StatsOptions} StatsOptions */ +/** @typedef {import("../declarations/WebpackOptions").WebpackPluginFunction} WebpackPluginFunction */ +/** @typedef {import("../declarations/WebpackOptions").WebpackPluginInstance} WebpackPluginInstance */ +/** @typedef {import("./AsyncDependenciesBlock")} AsyncDependenciesBlock */ +/** @typedef {import("./Cache")} Cache */ +/** @typedef {import("./CacheFacade")} CacheFacade */ +/** @typedef {import("./ChunkGroup").ChunkGroupOptions} ChunkGroupOptions */ +/** @typedef {import("./Compiler")} Compiler */ +/** @typedef {import("./Compiler").CompilationParams} CompilationParams */ +/** @typedef {import("./DependenciesBlock")} DependenciesBlock */ +/** @typedef {import("./Dependency").DependencyLocation} DependencyLocation */ +/** @typedef {import("./Dependency").ReferencedExport} ReferencedExport */ +/** @typedef {import("./DependencyTemplate")} DependencyTemplate */ +/** @typedef {import("./Entrypoint").EntryOptions} EntryOptions */ +/** @typedef {import("./Module").CodeGenerationResult} CodeGenerationResult */ +/** @typedef {import("./ModuleFactory")} ModuleFactory */ +/** @typedef {import("./ModuleFactory").ModuleFactoryCreateDataContextInfo} ModuleFactoryCreateDataContextInfo */ +/** @typedef {import("./ModuleFactory").ModuleFactoryResult} ModuleFactoryResult */ +/** @typedef {import("./RequestShortener")} RequestShortener */ +/** @typedef {import("./RuntimeModule")} RuntimeModule */ +/** @typedef {import("./Template").RenderManifestEntry} RenderManifestEntry */ +/** @typedef {import("./Template").RenderManifestOptions} RenderManifestOptions */ +/** @typedef {import("./stats/DefaultStatsFactoryPlugin").StatsAsset} StatsAsset */ +/** @typedef {import("./stats/DefaultStatsFactoryPlugin").StatsError} StatsError */ +/** @typedef {import("./stats/DefaultStatsFactoryPlugin").StatsModule} StatsModule */ +/** @typedef {import("./util/Hash")} Hash */ +/** @template T @typedef {import("./util/deprecation").FakeHook} FakeHook */ +/** @typedef {import("./util/runtime").RuntimeSpec} RuntimeSpec */ - try { - if ("filename" in fileManifest) { - file = fileManifest.filename; - assetInfo = fileManifest.info; - } else { - filenameTemplate = fileManifest.filenameTemplate; - const pathAndInfo = this.getPathWithInfo( - filenameTemplate, - fileManifest.pathOptions - ); - file = pathAndInfo.path; - assetInfo = fileManifest.info - ? { - ...pathAndInfo.info, - ...fileManifest.info - } - : pathAndInfo.info; - } +/** + * @callback Callback + * @param {WebpackError=} err + * @returns {void} + */ - if (err) { - return errorAndCallback(err); - } +/** + * @callback ModuleCallback + * @param {WebpackError=} err + * @param {Module=} result + * @returns {void} + */ - let source = sourceFromCache; +/** + * @callback ModuleFactoryResultCallback + * @param {WebpackError=} err + * @param {ModuleFactoryResult=} result + * @returns {void} + */ - // check if the same filename was already written by another chunk - const alreadyWritten = alreadyWrittenFiles.get(file); - if (alreadyWritten !== undefined) { - if (alreadyWritten.hash !== usedHash) { - inTry = false; - return callback( - new WebpackError( - `Conflict: Multiple chunks emit assets to the same filename ${file}` + - ` (chunks ${alreadyWritten.chunk.id} and ${chunk.id})` - ) - ); - } else { - source = alreadyWritten.source; - } - } else if (!source) { - // render the asset - source = fileManifest.render(); +/** + * @callback ModuleOrFactoryResultCallback + * @param {WebpackError=} err + * @param {Module | ModuleFactoryResult=} result + * @returns {void} + */ - // Ensure that source is a cached source to avoid additional cost because of repeated access - if (!(source instanceof CachedSource)) { - const cacheEntry = cachedSourceMap.get(source); - if (cacheEntry) { - source = cacheEntry; - } else { - const cachedSource = new CachedSource(source); - cachedSourceMap.set(source, cachedSource); - source = cachedSource; - } - } - } - this.emitAsset(file, source, assetInfo); - if (fileManifest.auxiliary) { - chunk.auxiliaryFiles.add(file); - } else { - chunk.files.add(file); - } - this.hooks.chunkAsset.call(chunk, file); - alreadyWrittenFiles.set(file, { - hash: usedHash, - source, - chunk - }); - if (source !== sourceFromCache) { - assetCacheItem.store(source, err => { - if (err) return errorAndCallback(err); - inTry = false; - return callback(); - }); - } else { - inTry = false; - callback(); - } - } catch (err) { - if (!inTry) throw err; - errorAndCallback(err); - } - }); - }, - callback - ); - }, - callback - ); - } +/** + * @callback ExecuteModuleCallback + * @param {WebpackError=} err + * @param {ExecuteModuleResult=} result + * @returns {void} + */ - /** - * @param {string | function(PathData, AssetInfo=): string} filename used to get asset path with hash - * @param {PathData} data context data - * @returns {string} interpolated path - */ - getPath(filename, data = {}) { - if (!data.hash) { - data = { - hash: this.hash, - ...data - }; - } - return this.getAssetPath(filename, data); - } +/** + * @callback DepBlockVarDependenciesCallback + * @param {Dependency} dependency + * @returns {any} + */ - /** - * @param {string | function(PathData, AssetInfo=): string} filename used to get asset path with hash - * @param {PathData} data context data - * @returns {{ path: string, info: AssetInfo }} interpolated path and asset info - */ - getPathWithInfo(filename, data = {}) { - if (!data.hash) { - data = { - hash: this.hash, - ...data - }; - } - return this.getAssetPathWithInfo(filename, data); - } +/** @typedef {new (...args: any[]) => Dependency} DepConstructor */ +/** @typedef {Record} CompilationAssets */ - /** - * @param {string | function(PathData, AssetInfo=): string} filename used to get asset path with hash - * @param {PathData} data context data - * @returns {string} interpolated path - */ - getAssetPath(filename, data) { - return this.hooks.assetPath.call( - typeof filename === "function" ? filename(data) : filename, - data, - undefined - ); - } +/** + * @typedef {Object} AvailableModulesChunkGroupMapping + * @property {ChunkGroup} chunkGroup + * @property {Set} availableModules + * @property {boolean} needCopy + */ - /** - * @param {string | function(PathData, AssetInfo=): string} filename used to get asset path with hash - * @param {PathData} data context data - * @returns {{ path: string, info: AssetInfo }} interpolated path and asset info - */ - getAssetPathWithInfo(filename, data) { - const assetInfo = {}; - // TODO webpack 5: refactor assetPath hook to receive { path, info } object - const newPath = this.hooks.assetPath.call( - typeof filename === "function" ? filename(data, assetInfo) : filename, - data, - assetInfo - ); - return { path: newPath, info: assetInfo }; - } +/** + * @typedef {Object} DependenciesBlockLike + * @property {Dependency[]} dependencies + * @property {AsyncDependenciesBlock[]} blocks + */ - getWarnings() { - return this.hooks.processWarnings.call(this.warnings); - } +/** + * @typedef {Object} ChunkPathData + * @property {string|number} id + * @property {string=} name + * @property {string} hash + * @property {function(number): string=} hashWithLength + * @property {(Record)=} contentHash + * @property {(Record string>)=} contentHashWithLength + */ - getErrors() { - return this.hooks.processErrors.call(this.errors); - } +/** + * @typedef {Object} ChunkHashContext + * @property {RuntimeTemplate} runtimeTemplate the runtime template + * @property {ModuleGraph} moduleGraph the module graph + * @property {ChunkGraph} chunkGraph the chunk graph + */ - /** - * This function allows you to run another instance of webpack inside of webpack however as - * a child with different settings and configurations (if desired) applied. It copies all hooks, plugins - * from parent (or top level compiler) and creates a child Compilation - * - * @param {string} name name of the child compiler - * @param {OutputOptions=} outputOptions // Need to convert config schema to types for this - * @param {Array=} plugins webpack plugins that will be applied - * @returns {Compiler} creates a child Compiler instance - */ - createChildCompiler(name, outputOptions, plugins) { - const idx = this.childrenCounters[name] || 0; - this.childrenCounters[name] = idx + 1; - return this.compiler.createChildCompiler( - this, - name, - idx, - outputOptions, - plugins - ); - } +/** + * @typedef {Object} RuntimeRequirementsContext + * @property {ChunkGraph} chunkGraph the chunk graph + * @property {CodeGenerationResults} codeGenerationResults the code generation results + */ - /** - * @param {Module} module the module - * @param {ExecuteModuleOptions} options options - * @param {ExecuteModuleCallback} callback callback - */ - executeModule(module, options, callback) { - // Aggregate all referenced modules and ensure they are ready - const modules = new Set([module]); - processAsyncTree( - modules, - 10, - /** - * @param {Module} module the module - * @param {function(Module): void} push push more jobs - * @param {Callback} callback callback - * @returns {void} - */ - (module, push, callback) => { - this.buildQueue.waitFor(module, err => { - if (err) return callback(err); - this.processDependenciesQueue.waitFor(module, err => { - if (err) return callback(err); - for (const { module: m } of this.moduleGraph.getOutgoingConnections( - module - )) { - const size = modules.size; - modules.add(m); - if (modules.size !== size) push(m); - } - callback(); - }); - }); - }, - err => { - if (err) return callback(err); +/** + * @typedef {Object} ExecuteModuleOptions + * @property {EntryOptions=} entryOptions + */ - // Create new chunk graph, chunk and entrypoint for the build time execution - const chunkGraph = new ChunkGraph( - this.moduleGraph, - this.outputOptions.hashFunction - ); - const runtime = "build time"; - const { hashFunction, hashDigest, hashDigestLength } = - this.outputOptions; - const runtimeTemplate = this.runtimeTemplate; +/** + * @typedef {Object} ExecuteModuleResult + * @property {any} exports + * @property {boolean} cacheable + * @property {Map} assets + * @property {LazySet} fileDependencies + * @property {LazySet} contextDependencies + * @property {LazySet} missingDependencies + * @property {LazySet} buildDependencies + */ - const chunk = new Chunk("build time chunk", this._backCompat); - chunk.id = chunk.name; - chunk.ids = [chunk.id]; - chunk.runtime = runtime; +/** + * @typedef {Object} ExecuteModuleArgument + * @property {Module} module + * @property {{ id: string, exports: any, loaded: boolean }=} moduleObject + * @property {any} preparedInfo + * @property {CodeGenerationResult} codeGenerationResult + */ - const entrypoint = new Entrypoint({ - runtime, - chunkLoading: false, - ...options.entryOptions - }); - chunkGraph.connectChunkAndEntryModule(chunk, module, entrypoint); - connectChunkGroupAndChunk(entrypoint, chunk); - entrypoint.setRuntimeChunk(chunk); - entrypoint.setEntrypointChunk(chunk); +/** + * @typedef {Object} ExecuteModuleContext + * @property {Map} assets + * @property {Chunk} chunk + * @property {ChunkGraph} chunkGraph + * @property {function(string): any=} __webpack_require__ + */ - const chunks = new Set([chunk]); - - // Assign ids to modules and modules to the chunk - for (const module of modules) { - const id = module.identifier(); - chunkGraph.setModuleId(module, id); - chunkGraph.connectChunkAndModule(chunk, module); - } - - // Hash modules - for (const module of modules) { - this._createModuleHash( - module, - chunkGraph, - runtime, - hashFunction, - runtimeTemplate, - hashDigest, - hashDigestLength - ); - } - - const codeGenerationResults = new CodeGenerationResults( - this.outputOptions.hashFunction - ); - /** @type {WebpackError[]} */ - const errors = []; - /** - * @param {Module} module the module - * @param {Callback} callback callback - * @returns {void} - */ - const codeGen = (module, callback) => { - this._codeGenerationModule( - module, - runtime, - [runtime], - chunkGraph.getModuleHash(module, runtime), - this.dependencyTemplates, - chunkGraph, - this.moduleGraph, - runtimeTemplate, - errors, - codeGenerationResults, - (err, codeGenerated) => { - callback(err); - } - ); - }; - - const reportErrors = () => { - if (errors.length > 0) { - errors.sort( - compareSelect(err => err.module, compareModulesByIdentifier) - ); - for (const error of errors) { - this.errors.push(error); - } - errors.length = 0; - } - }; - - // Generate code for all aggregated modules - asyncLib.eachLimit(modules, 10, codeGen, err => { - if (err) return callback(err); - reportErrors(); - - // for backward-compat temporary set the chunk graph - // TODO webpack 6 - const old = this.chunkGraph; - this.chunkGraph = chunkGraph; - this.processRuntimeRequirements({ - chunkGraph, - modules, - chunks, - codeGenerationResults, - chunkGraphEntries: chunks - }); - this.chunkGraph = old; - - const runtimeModules = - chunkGraph.getChunkRuntimeModulesIterable(chunk); - - // Hash runtime modules - for (const module of runtimeModules) { - modules.add(module); - this._createModuleHash( - module, - chunkGraph, - runtime, - hashFunction, - runtimeTemplate, - hashDigest, - hashDigestLength - ); - } - - // Generate code for all runtime modules - asyncLib.eachLimit(runtimeModules, 10, codeGen, err => { - if (err) return callback(err); - reportErrors(); - - /** @type {Map} */ - const moduleArgumentsMap = new Map(); - /** @type {Map} */ - const moduleArgumentsById = new Map(); - - /** @type {ExecuteModuleResult["fileDependencies"]} */ - const fileDependencies = new LazySet(); - /** @type {ExecuteModuleResult["contextDependencies"]} */ - const contextDependencies = new LazySet(); - /** @type {ExecuteModuleResult["missingDependencies"]} */ - const missingDependencies = new LazySet(); - /** @type {ExecuteModuleResult["buildDependencies"]} */ - const buildDependencies = new LazySet(); - - /** @type {ExecuteModuleResult["assets"]} */ - const assets = new Map(); - - let cacheable = true; - - /** @type {ExecuteModuleContext} */ - const context = { - assets, - __webpack_require__: undefined, - chunk, - chunkGraph - }; - - // Prepare execution - asyncLib.eachLimit( - modules, - 10, - (module, callback) => { - const codeGenerationResult = codeGenerationResults.get( - module, - runtime - ); - /** @type {ExecuteModuleArgument} */ - const moduleArgument = { - module, - codeGenerationResult, - preparedInfo: undefined, - moduleObject: undefined - }; - moduleArgumentsMap.set(module, moduleArgument); - moduleArgumentsById.set(module.identifier(), moduleArgument); - module.addCacheDependencies( - fileDependencies, - contextDependencies, - missingDependencies, - buildDependencies - ); - if (module.buildInfo.cacheable === false) { - cacheable = false; - } - if (module.buildInfo && module.buildInfo.assets) { - const { assets: moduleAssets, assetsInfo } = module.buildInfo; - for (const assetName of Object.keys(moduleAssets)) { - assets.set(assetName, { - source: moduleAssets[assetName], - info: assetsInfo ? assetsInfo.get(assetName) : undefined - }); - } - } - this.hooks.prepareModuleExecution.callAsync( - moduleArgument, - context, - callback - ); - }, - err => { - if (err) return callback(err); - - let exports; - try { - const { - strictModuleErrorHandling, - strictModuleExceptionHandling - } = this.outputOptions; - const __nested_webpack_require_150834__ = id => { - const cached = moduleCache[id]; - if (cached !== undefined) { - if (cached.error) throw cached.error; - return cached.exports; - } - const moduleArgument = moduleArgumentsById.get(id); - return __webpack_require_module__(moduleArgument, id); - }; - const interceptModuleExecution = (__nested_webpack_require_150834__[ - RuntimeGlobals.interceptModuleExecution.replace( - "__webpack_require__.", - "" - ) - ] = []); - const moduleCache = (__nested_webpack_require_150834__[ - RuntimeGlobals.moduleCache.replace( - "__webpack_require__.", - "" - ) - ] = {}); - - context.__webpack_require__ = __nested_webpack_require_150834__; - - /** - * @param {ExecuteModuleArgument} moduleArgument the module argument - * @param {string=} id id - * @returns {any} exports - */ - const __webpack_require_module__ = (moduleArgument, id) => { - var execOptions = { - id, - module: { - id, - exports: {}, - loaded: false, - error: undefined - }, - require: __nested_webpack_require_150834__ - }; - interceptModuleExecution.forEach(handler => - handler(execOptions) - ); - const module = moduleArgument.module; - this.buildTimeExecutedModules.add(module); - const moduleObject = execOptions.module; - moduleArgument.moduleObject = moduleObject; - try { - if (id) moduleCache[id] = moduleObject; - - tryRunOrWebpackError( - () => - this.hooks.executeModule.call( - moduleArgument, - context - ), - "Compilation.hooks.executeModule" - ); - moduleObject.loaded = true; - return moduleObject.exports; - } catch (e) { - if (strictModuleExceptionHandling) { - if (id) delete moduleCache[id]; - } else if (strictModuleErrorHandling) { - moduleObject.error = e; - } - if (!e.module) e.module = module; - throw e; - } - }; - - for (const runtimeModule of chunkGraph.getChunkRuntimeModulesInOrder( - chunk - )) { - __webpack_require_module__( - moduleArgumentsMap.get(runtimeModule) - ); - } - exports = __nested_webpack_require_150834__(module.identifier()); - } catch (e) { - const err = new WebpackError( - `Execution of module code from module graph (${module.readableIdentifier( - this.requestShortener - )}) failed: ${e.message}` - ); - err.stack = e.stack; - err.module = e.module; - return callback(err); - } - - callback(null, { - exports, - assets, - cacheable, - fileDependencies, - contextDependencies, - missingDependencies, - buildDependencies - }); - } - ); - }); - }); - } - ); - } - - checkConstraints() { - const chunkGraph = this.chunkGraph; - - /** @type {Set} */ - const usedIds = new Set(); - - for (const module of this.modules) { - if (module.type === "runtime") continue; - const moduleId = chunkGraph.getModuleId(module); - if (moduleId === null) continue; - if (usedIds.has(moduleId)) { - throw new Error(`checkConstraints: duplicate module id ${moduleId}`); - } - usedIds.add(moduleId); - } - - for (const chunk of this.chunks) { - for (const module of chunkGraph.getChunkModulesIterable(chunk)) { - if (!this.modules.has(module)) { - throw new Error( - "checkConstraints: module in chunk but not in compilation " + - ` ${chunk.debugId} ${module.debugId}` - ); - } - } - for (const module of chunkGraph.getChunkEntryModulesIterable(chunk)) { - if (!this.modules.has(module)) { - throw new Error( - "checkConstraints: entry module in chunk but not in compilation " + - ` ${chunk.debugId} ${module.debugId}` - ); - } - } - } - - for (const chunkGroup of this.chunkGroups) { - chunkGroup.checkConstraints(); - } - } -} +/** + * @typedef {Object} EntryData + * @property {Dependency[]} dependencies dependencies of the entrypoint that should be evaluated at startup + * @property {Dependency[]} includeDependencies dependencies of the entrypoint that should be included but not evaluated + * @property {EntryOptions} options options of the entrypoint + */ /** - * @typedef {Object} FactorizeModuleOptions - * @property {ModuleProfile} currentProfile - * @property {ModuleFactory} factory - * @property {Dependency[]} dependencies - * @property {boolean=} factoryResult return full ModuleFactoryResult instead of only module - * @property {Module | null} originModule - * @property {Partial=} contextInfo - * @property {string=} context + * @typedef {Object} LogEntry + * @property {string} type + * @property {any[]} args + * @property {number} time + * @property {string[]=} trace */ /** - * @param {FactorizeModuleOptions} options options object - * @param {ModuleCallback | ModuleFactoryResultCallback} callback callback - * @returns {void} + * @typedef {Object} KnownAssetInfo + * @property {boolean=} immutable true, if the asset can be long term cached forever (contains a hash) + * @property {boolean=} minimized whether the asset is minimized + * @property {string | string[]=} fullhash the value(s) of the full hash used for this asset + * @property {string | string[]=} chunkhash the value(s) of the chunk hash used for this asset + * @property {string | string[]=} modulehash the value(s) of the module hash used for this asset + * @property {string | string[]=} contenthash the value(s) of the content hash used for this asset + * @property {string=} sourceFilename when asset was created from a source file (potentially transformed), the original filename relative to compilation context + * @property {number=} size size in bytes, only set after asset has been emitted + * @property {boolean=} development true, when asset is only used for development and doesn't count towards user-facing assets + * @property {boolean=} hotModuleReplacement true, when asset ships data for updating an existing application (HMR) + * @property {boolean=} javascriptModule true, when asset is javascript and an ESM + * @property {Record=} related object of pointers to other assets, keyed by type of relation (only points from parent to child) */ -// Workaround for typescript as it doesn't support function overloading in jsdoc within a class -Compilation.prototype.factorizeModule = /** @type {{ - (options: FactorizeModuleOptions & { factoryResult?: false }, callback: ModuleCallback): void; - (options: FactorizeModuleOptions & { factoryResult: true }, callback: ModuleFactoryResultCallback): void; -}} */ ( - function (options, callback) { - this.factorizeQueue.add(options, callback); - } -); - -// Hide from typescript -const compilationPrototype = Compilation.prototype; - -// TODO webpack 6 remove -Object.defineProperty(compilationPrototype, "modifyHash", { - writable: false, - enumerable: false, - configurable: false, - value: () => { - throw new Error( - "Compilation.modifyHash was removed in favor of Compilation.hooks.fullHash" - ); - } -}); - -// TODO webpack 6 remove -Object.defineProperty(compilationPrototype, "cache", { - enumerable: false, - configurable: false, - get: util.deprecate( - /** - * @this {Compilation} the compilation - * @returns {Cache} the cache - */ - function () { - return this.compiler.cache; - }, - "Compilation.cache was removed in favor of Compilation.getCache()", - "DEP_WEBPACK_COMPILATION_CACHE" - ), - set: util.deprecate( - v => {}, - "Compilation.cache was removed in favor of Compilation.getCache()", - "DEP_WEBPACK_COMPILATION_CACHE" - ) -}); +/** @typedef {KnownAssetInfo & Record} AssetInfo */ /** - * Add additional assets to the compilation. + * @typedef {Object} Asset + * @property {string} name the filename of the asset + * @property {Source} source source of the asset + * @property {AssetInfo} info info about the asset */ -Compilation.PROCESS_ASSETS_STAGE_ADDITIONAL = -2000; /** - * Basic preprocessing of assets. + * @typedef {Object} ModulePathData + * @property {string|number} id + * @property {string} hash + * @property {function(number): string=} hashWithLength */ -Compilation.PROCESS_ASSETS_STAGE_PRE_PROCESS = -1000; /** - * Derive new assets from existing assets. - * Existing assets should not be treated as complete. + * @typedef {Object} PathData + * @property {ChunkGraph=} chunkGraph + * @property {string=} hash + * @property {function(number): string=} hashWithLength + * @property {(Chunk|ChunkPathData)=} chunk + * @property {(Module|ModulePathData)=} module + * @property {RuntimeSpec=} runtime + * @property {string=} filename + * @property {string=} basename + * @property {string=} query + * @property {string=} contentHashType + * @property {string=} contentHash + * @property {function(number): string=} contentHashWithLength + * @property {boolean=} noChunkHash + * @property {string=} url */ -Compilation.PROCESS_ASSETS_STAGE_DERIVED = -200; /** - * Add additional sections to existing assets, like a banner or initialization code. + * @typedef {Object} KnownNormalizedStatsOptions + * @property {string} context + * @property {RequestShortener} requestShortener + * @property {string} chunksSort + * @property {string} modulesSort + * @property {string} chunkModulesSort + * @property {string} nestedModulesSort + * @property {string} assetsSort + * @property {boolean} ids + * @property {boolean} cachedAssets + * @property {boolean} groupAssetsByEmitStatus + * @property {boolean} groupAssetsByPath + * @property {boolean} groupAssetsByExtension + * @property {number} assetsSpace + * @property {((value: string, asset: StatsAsset) => boolean)[]} excludeAssets + * @property {((name: string, module: StatsModule, type: "module" | "chunk" | "root-of-chunk" | "nested") => boolean)[]} excludeModules + * @property {((warning: StatsError, textValue: string) => boolean)[]} warningsFilter + * @property {boolean} cachedModules + * @property {boolean} orphanModules + * @property {boolean} dependentModules + * @property {boolean} runtimeModules + * @property {boolean} groupModulesByCacheStatus + * @property {boolean} groupModulesByLayer + * @property {boolean} groupModulesByAttributes + * @property {boolean} groupModulesByPath + * @property {boolean} groupModulesByExtension + * @property {boolean} groupModulesByType + * @property {boolean | "auto"} entrypoints + * @property {boolean} chunkGroups + * @property {boolean} chunkGroupAuxiliary + * @property {boolean} chunkGroupChildren + * @property {number} chunkGroupMaxAssets + * @property {number} modulesSpace + * @property {number} chunkModulesSpace + * @property {number} nestedModulesSpace + * @property {false|"none"|"error"|"warn"|"info"|"log"|"verbose"} logging + * @property {((value: string) => boolean)[]} loggingDebug + * @property {boolean} loggingTrace + * @property {any} _env */ -Compilation.PROCESS_ASSETS_STAGE_ADDITIONS = -100; -/** - * Optimize existing assets in a general way. - */ -Compilation.PROCESS_ASSETS_STAGE_OPTIMIZE = 100; +/** @typedef {KnownNormalizedStatsOptions & Omit & Record} NormalizedStatsOptions */ /** - * Optimize the count of existing assets, e. g. by merging them. - * Only assets of the same type should be merged. - * For assets of different types see PROCESS_ASSETS_STAGE_OPTIMIZE_INLINE. + * @typedef {Object} KnownCreateStatsOptionsContext + * @property {boolean=} forToString */ -Compilation.PROCESS_ASSETS_STAGE_OPTIMIZE_COUNT = 200; -/** - * Optimize the compatibility of existing assets, e. g. add polyfills or vendor-prefixes. - */ -Compilation.PROCESS_ASSETS_STAGE_OPTIMIZE_COMPATIBILITY = 300; +/** @typedef {KnownCreateStatsOptionsContext & Record} CreateStatsOptionsContext */ -/** - * Optimize the size of existing assets, e. g. by minimizing or omitting whitespace. - */ -Compilation.PROCESS_ASSETS_STAGE_OPTIMIZE_SIZE = 400; +/** @type {AssetInfo} */ +const EMPTY_ASSET_INFO = Object.freeze({}); -/** - * Add development tooling to assets, e. g. by extracting a SourceMap. - */ -Compilation.PROCESS_ASSETS_STAGE_DEV_TOOLING = 500; +const esmDependencyCategory = "esm"; +// TODO webpack 6: remove +const deprecatedNormalModuleLoaderHook = util.deprecate( + compilation => { + return __webpack_require__(11026).getCompilationHooks(compilation).loader; + }, + "Compilation.hooks.normalModuleLoader was moved to NormalModule.getCompilationHooks(compilation).loader", + "DEP_WEBPACK_COMPILATION_NORMAL_MODULE_LOADER_HOOK" +); -/** - * Optimize the count of existing assets, e. g. by inlining assets of into other assets. - * Only assets of different types should be inlined. - * For assets of the same type see PROCESS_ASSETS_STAGE_OPTIMIZE_COUNT. - */ -Compilation.PROCESS_ASSETS_STAGE_OPTIMIZE_INLINE = 700; - -/** - * Summarize the list of existing assets - * e. g. creating an assets manifest of Service Workers. - */ -Compilation.PROCESS_ASSETS_STAGE_SUMMARIZE = 1000; - -/** - * Optimize the hashes of the assets, e. g. by generating real hashes of the asset content. - */ -Compilation.PROCESS_ASSETS_STAGE_OPTIMIZE_HASH = 2500; - -/** - * Optimize the transfer of existing assets, e. g. by preparing a compressed (gzip) file as separate asset. - */ -Compilation.PROCESS_ASSETS_STAGE_OPTIMIZE_TRANSFER = 3000; - -/** - * Analyse existing assets. - */ -Compilation.PROCESS_ASSETS_STAGE_ANALYSE = 4000; - -/** - * Creating assets for reporting purposes. - */ -Compilation.PROCESS_ASSETS_STAGE_REPORT = 5000; +// TODO webpack 6: remove +const defineRemovedModuleTemplates = moduleTemplates => { + Object.defineProperties(moduleTemplates, { + asset: { + enumerable: false, + configurable: false, + get: () => { + throw new WebpackError( + "Compilation.moduleTemplates.asset has been removed" + ); + } + }, + webassembly: { + enumerable: false, + configurable: false, + get: () => { + throw new WebpackError( + "Compilation.moduleTemplates.webassembly has been removed" + ); + } + } + }); + moduleTemplates = undefined; +}; -module.exports = Compilation; +const byId = compareSelect( + /** + * @param {Chunk} c chunk + * @returns {number | string} id + */ c => c.id, + compareIds +); +const byNameOrHash = concatComparators( + compareSelect( + /** + * @param {Compilation} c compilation + * @returns {string} name + */ + c => c.name, + compareIds + ), + compareSelect( + /** + * @param {Compilation} c compilation + * @returns {string} hash + */ c => c.fullHash, + compareIds + ) +); -/***/ }), +const byMessage = compareSelect(err => `${err.message}`, compareStringsNumeric); -/***/ 11777: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { +const byModule = compareSelect( + err => (err.module && err.module.identifier()) || "", + compareStringsNumeric +); -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ +const byLocation = compareSelect(err => err.loc, compareLocations); +const compareErrors = concatComparators(byModule, byLocation, byMessage); +/** @type {WeakMap} */ +const unsafeCacheDependencies = new WeakMap(); -const parseJson = __webpack_require__(48335); -const asyncLib = __webpack_require__(36386); -const { - SyncHook, - SyncBailHook, - AsyncParallelHook, - AsyncSeriesHook -} = __webpack_require__(34718); -const { SizeOnlySource } = __webpack_require__(96192); -const webpack = __webpack_require__(48169); -const Cache = __webpack_require__(99453); -const CacheFacade = __webpack_require__(67014); -const ChunkGraph = __webpack_require__(97860); -const Compilation = __webpack_require__(59622); -const ConcurrentCompilationError = __webpack_require__(51684); -const ContextModuleFactory = __webpack_require__(26268); -const ModuleGraph = __webpack_require__(20258); -const NormalModuleFactory = __webpack_require__(99063); -const RequestShortener = __webpack_require__(43157); -const ResolverFactory = __webpack_require__(88810); -const Stats = __webpack_require__(87797); -const Watching = __webpack_require__(49819); -const WebpackError = __webpack_require__(68422); -const { Logger } = __webpack_require__(54667); -const { join, dirname, mkdirp } = __webpack_require__(93204); -const { makePathsRelative } = __webpack_require__(96236); -const { isSourceEqual } = __webpack_require__(4002); +/** @type {WeakMap} */ +const unsafeCacheData = new WeakMap(); -/** @typedef {import("webpack-sources").Source} Source */ -/** @typedef {import("../declarations/WebpackOptions").EntryNormalized} Entry */ -/** @typedef {import("../declarations/WebpackOptions").OutputNormalized} OutputOptions */ -/** @typedef {import("../declarations/WebpackOptions").WatchOptions} WatchOptions */ -/** @typedef {import("../declarations/WebpackOptions").WebpackOptionsNormalized} WebpackOptions */ -/** @typedef {import("../declarations/WebpackOptions").WebpackPluginInstance} WebpackPluginInstance */ -/** @typedef {import("./Chunk")} Chunk */ -/** @typedef {import("./Dependency")} Dependency */ -/** @typedef {import("./FileSystemInfo").FileSystemInfoEntry} FileSystemInfoEntry */ -/** @typedef {import("./Module")} Module */ -/** @typedef {import("./util/WeakTupleMap")} WeakTupleMap */ -/** @typedef {import("./util/fs").InputFileSystem} InputFileSystem */ -/** @typedef {import("./util/fs").IntermediateFileSystem} IntermediateFileSystem */ -/** @typedef {import("./util/fs").OutputFileSystem} OutputFileSystem */ -/** @typedef {import("./util/fs").WatchFileSystem} WatchFileSystem */ +class Compilation { + /** + * Creates an instance of Compilation. + * @param {Compiler} compiler the compiler which created the compilation + * @param {CompilationParams} params the compilation parameters + */ + constructor(compiler, params) { + this._backCompat = compiler._backCompat; -/** - * @typedef {Object} CompilationParams - * @property {NormalModuleFactory} normalModuleFactory - * @property {ContextModuleFactory} contextModuleFactory - */ + const getNormalModuleLoader = () => deprecatedNormalModuleLoaderHook(this); + /** @typedef {{ additionalAssets?: true | Function }} ProcessAssetsAdditionalOptions */ + /** @type {AsyncSeriesHook<[CompilationAssets], ProcessAssetsAdditionalOptions>} */ + const processAssetsHook = new AsyncSeriesHook(["assets"]); -/** - * @template T - * @callback Callback - * @param {Error=} err - * @param {T=} result - */ + let savedAssets = new Set(); + const popNewAssets = assets => { + let newAssets = undefined; + for (const file of Object.keys(assets)) { + if (savedAssets.has(file)) continue; + if (newAssets === undefined) { + newAssets = Object.create(null); + } + newAssets[file] = assets[file]; + savedAssets.add(file); + } + return newAssets; + }; + processAssetsHook.intercept({ + name: "Compilation", + call: () => { + savedAssets = new Set(Object.keys(this.assets)); + }, + register: tap => { + const { type, name } = tap; + const { fn, additionalAssets, ...remainingTap } = tap; + const additionalAssetsFn = + additionalAssets === true ? fn : additionalAssets; + const processedAssets = additionalAssetsFn ? new WeakSet() : undefined; + switch (type) { + case "sync": + if (additionalAssetsFn) { + this.hooks.processAdditionalAssets.tap(name, assets => { + if (processedAssets.has(this.assets)) + additionalAssetsFn(assets); + }); + } + return { + ...remainingTap, + type: "async", + fn: (assets, callback) => { + try { + fn(assets); + } catch (e) { + return callback(e); + } + if (processedAssets !== undefined) + processedAssets.add(this.assets); + const newAssets = popNewAssets(assets); + if (newAssets !== undefined) { + this.hooks.processAdditionalAssets.callAsync( + newAssets, + callback + ); + return; + } + callback(); + } + }; + case "async": + if (additionalAssetsFn) { + this.hooks.processAdditionalAssets.tapAsync( + name, + (assets, callback) => { + if (processedAssets.has(this.assets)) + return additionalAssetsFn(assets, callback); + callback(); + } + ); + } + return { + ...remainingTap, + fn: (assets, callback) => { + fn(assets, err => { + if (err) return callback(err); + if (processedAssets !== undefined) + processedAssets.add(this.assets); + const newAssets = popNewAssets(assets); + if (newAssets !== undefined) { + this.hooks.processAdditionalAssets.callAsync( + newAssets, + callback + ); + return; + } + callback(); + }); + } + }; + case "promise": + if (additionalAssetsFn) { + this.hooks.processAdditionalAssets.tapPromise(name, assets => { + if (processedAssets.has(this.assets)) + return additionalAssetsFn(assets); + return Promise.resolve(); + }); + } + return { + ...remainingTap, + fn: assets => { + const p = fn(assets); + if (!p || !p.then) return p; + return p.then(() => { + if (processedAssets !== undefined) + processedAssets.add(this.assets); + const newAssets = popNewAssets(assets); + if (newAssets !== undefined) { + return this.hooks.processAdditionalAssets.promise( + newAssets + ); + } + }); + } + }; + } + } + }); -/** - * @callback RunAsChildCallback - * @param {Error=} err - * @param {Chunk[]=} entries - * @param {Compilation=} compilation - */ + /** @type {SyncHook<[CompilationAssets]>} */ + const afterProcessAssetsHook = new SyncHook(["assets"]); -/** - * @typedef {Object} AssetEmittedInfo - * @property {Buffer} content - * @property {Source} source - * @property {Compilation} compilation - * @property {string} outputPath - * @property {string} targetPath - */ + /** + * @template T + * @param {string} name name of the hook + * @param {number} stage new stage + * @param {function(): AsArray} getArgs get old hook function args + * @param {string=} code deprecation code (not deprecated when unset) + * @returns {FakeHook, "tap" | "tapAsync" | "tapPromise" | "name">>} fake hook which redirects + */ + const createProcessAssetsHook = (name, stage, getArgs, code) => { + if (!this._backCompat && code) return undefined; + const errorMessage = + reason => `Can't automatically convert plugin using Compilation.hooks.${name} to Compilation.hooks.processAssets because ${reason}. +BREAKING CHANGE: Asset processing hooks in Compilation has been merged into a single Compilation.hooks.processAssets hook.`; + const getOptions = options => { + if (typeof options === "string") options = { name: options }; + if (options.stage) { + throw new Error(errorMessage("it's using the 'stage' option")); + } + return { ...options, stage: stage }; + }; + return createFakeHook( + { + name, + /** @type {AsyncSeriesHook["intercept"]} */ + intercept(interceptor) { + throw new Error(errorMessage("it's using 'intercept'")); + }, + /** @type {AsyncSeriesHook["tap"]} */ + tap: (options, fn) => { + processAssetsHook.tap(getOptions(options), () => fn(...getArgs())); + }, + /** @type {AsyncSeriesHook["tapAsync"]} */ + tapAsync: (options, fn) => { + processAssetsHook.tapAsync( + getOptions(options), + (assets, callback) => + /** @type {any} */ (fn)(...getArgs(), callback) + ); + }, + /** @type {AsyncSeriesHook["tapPromise"]} */ + tapPromise: (options, fn) => { + processAssetsHook.tapPromise(getOptions(options), () => + fn(...getArgs()) + ); + } + }, + `${name} is deprecated (use Compilation.hooks.processAssets instead and use one of Compilation.PROCESS_ASSETS_STAGE_* as stage option)`, + code + ); + }; + this.hooks = Object.freeze({ + /** @type {SyncHook<[Module]>} */ + buildModule: new SyncHook(["module"]), + /** @type {SyncHook<[Module]>} */ + rebuildModule: new SyncHook(["module"]), + /** @type {SyncHook<[Module, WebpackError]>} */ + failedModule: new SyncHook(["module", "error"]), + /** @type {SyncHook<[Module]>} */ + succeedModule: new SyncHook(["module"]), + /** @type {SyncHook<[Module]>} */ + stillValidModule: new SyncHook(["module"]), -/** - * @param {string[]} array an array - * @returns {boolean} true, if the array is sorted - */ -const isSorted = array => { - for (let i = 1; i < array.length; i++) { - if (array[i - 1] > array[i]) return false; - } - return true; -}; + /** @type {SyncHook<[Dependency, EntryOptions]>} */ + addEntry: new SyncHook(["entry", "options"]), + /** @type {SyncHook<[Dependency, EntryOptions, Error]>} */ + failedEntry: new SyncHook(["entry", "options", "error"]), + /** @type {SyncHook<[Dependency, EntryOptions, Module]>} */ + succeedEntry: new SyncHook(["entry", "options", "module"]), -/** - * @param {Object} obj an object - * @param {string[]} keys the keys of the object - * @returns {Object} the object with properties sorted by property name - */ -const sortObject = (obj, keys) => { - const o = {}; - for (const k of keys.sort()) { - o[k] = obj[k]; - } - return o; -}; + /** @type {SyncWaterfallHook<[(string[] | ReferencedExport)[], Dependency, RuntimeSpec]>} */ + dependencyReferencedExports: new SyncWaterfallHook([ + "referencedExports", + "dependency", + "runtime" + ]), -/** - * @param {string} filename filename - * @param {string | string[] | undefined} hashes list of hashes - * @returns {boolean} true, if the filename contains any hash - */ -const includesHash = (filename, hashes) => { - if (!hashes) return false; - if (Array.isArray(hashes)) { - return hashes.some(hash => filename.includes(hash)); - } else { - return filename.includes(hashes); - } -}; + /** @type {SyncHook<[ExecuteModuleArgument, ExecuteModuleContext]>} */ + executeModule: new SyncHook(["options", "context"]), + /** @type {AsyncParallelHook<[ExecuteModuleArgument, ExecuteModuleContext]>} */ + prepareModuleExecution: new AsyncParallelHook(["options", "context"]), -class Compiler { - /** - * @param {string} context the compilation path - * @param {WebpackOptions} options options - */ - constructor(context, options = /** @type {WebpackOptions} */ ({})) { - this.hooks = Object.freeze({ + /** @type {AsyncSeriesHook<[Iterable]>} */ + finishModules: new AsyncSeriesHook(["modules"]), + /** @type {AsyncSeriesHook<[Module]>} */ + finishRebuildingModule: new AsyncSeriesHook(["module"]), /** @type {SyncHook<[]>} */ - initialize: new SyncHook([]), - - /** @type {SyncBailHook<[Compilation], boolean>} */ - shouldEmit: new SyncBailHook(["compilation"]), - /** @type {AsyncSeriesHook<[Stats]>} */ - done: new AsyncSeriesHook(["stats"]), - /** @type {SyncHook<[Stats]>} */ - afterDone: new SyncHook(["stats"]), - /** @type {AsyncSeriesHook<[]>} */ - additionalPass: new AsyncSeriesHook([]), - /** @type {AsyncSeriesHook<[Compiler]>} */ - beforeRun: new AsyncSeriesHook(["compiler"]), - /** @type {AsyncSeriesHook<[Compiler]>} */ - run: new AsyncSeriesHook(["compiler"]), - /** @type {AsyncSeriesHook<[Compilation]>} */ - emit: new AsyncSeriesHook(["compilation"]), - /** @type {AsyncSeriesHook<[string, AssetEmittedInfo]>} */ - assetEmitted: new AsyncSeriesHook(["file", "info"]), - /** @type {AsyncSeriesHook<[Compilation]>} */ - afterEmit: new AsyncSeriesHook(["compilation"]), - - /** @type {SyncHook<[Compilation, CompilationParams]>} */ - thisCompilation: new SyncHook(["compilation", "params"]), - /** @type {SyncHook<[Compilation, CompilationParams]>} */ - compilation: new SyncHook(["compilation", "params"]), - /** @type {SyncHook<[NormalModuleFactory]>} */ - normalModuleFactory: new SyncHook(["normalModuleFactory"]), - /** @type {SyncHook<[ContextModuleFactory]>} */ - contextModuleFactory: new SyncHook(["contextModuleFactory"]), - - /** @type {AsyncSeriesHook<[CompilationParams]>} */ - beforeCompile: new AsyncSeriesHook(["params"]), - /** @type {SyncHook<[CompilationParams]>} */ - compile: new SyncHook(["params"]), - /** @type {AsyncParallelHook<[Compilation]>} */ - make: new AsyncParallelHook(["compilation"]), - /** @type {AsyncParallelHook<[Compilation]>} */ - finishMake: new AsyncSeriesHook(["compilation"]), - /** @type {AsyncSeriesHook<[Compilation]>} */ - afterCompile: new AsyncSeriesHook(["compilation"]), + unseal: new SyncHook([]), + /** @type {SyncHook<[]>} */ + seal: new SyncHook([]), - /** @type {AsyncSeriesHook<[Compiler]>} */ - watchRun: new AsyncSeriesHook(["compiler"]), - /** @type {SyncHook<[Error]>} */ - failed: new SyncHook(["error"]), - /** @type {SyncHook<[string | null, number]>} */ - invalid: new SyncHook(["filename", "changeTime"]), /** @type {SyncHook<[]>} */ - watchClose: new SyncHook([]), - /** @type {AsyncSeriesHook<[]>} */ - shutdown: new AsyncSeriesHook([]), + beforeChunks: new SyncHook([]), + /** @type {SyncHook<[Iterable]>} */ + afterChunks: new SyncHook(["chunks"]), - /** @type {SyncBailHook<[string, string, any[]], true>} */ - infrastructureLog: new SyncBailHook(["origin", "type", "args"]), + /** @type {SyncBailHook<[Iterable]>} */ + optimizeDependencies: new SyncBailHook(["modules"]), + /** @type {SyncHook<[Iterable]>} */ + afterOptimizeDependencies: new SyncHook(["modules"]), - // TODO the following hooks are weirdly located here - // TODO move them for webpack 5 - /** @type {SyncHook<[]>} */ - environment: new SyncHook([]), /** @type {SyncHook<[]>} */ - afterEnvironment: new SyncHook([]), - /** @type {SyncHook<[Compiler]>} */ - afterPlugins: new SyncHook(["compiler"]), - /** @type {SyncHook<[Compiler]>} */ - afterResolvers: new SyncHook(["compiler"]), - /** @type {SyncBailHook<[string, Entry], boolean>} */ - entryOption: new SyncBailHook(["context", "entry"]) - }); + optimize: new SyncHook([]), + /** @type {SyncBailHook<[Iterable]>} */ + optimizeModules: new SyncBailHook(["modules"]), + /** @type {SyncHook<[Iterable]>} */ + afterOptimizeModules: new SyncHook(["modules"]), - this.webpack = webpack; + /** @type {SyncBailHook<[Iterable, ChunkGroup[]]>} */ + optimizeChunks: new SyncBailHook(["chunks", "chunkGroups"]), + /** @type {SyncHook<[Iterable, ChunkGroup[]]>} */ + afterOptimizeChunks: new SyncHook(["chunks", "chunkGroups"]), - /** @type {string=} */ - this.name = undefined; - /** @type {Compilation=} */ - this.parentCompilation = undefined; - /** @type {Compiler} */ - this.root = this; - /** @type {string} */ - this.outputPath = ""; - /** @type {Watching} */ - this.watching = undefined; + /** @type {AsyncSeriesHook<[Iterable, Iterable]>} */ + optimizeTree: new AsyncSeriesHook(["chunks", "modules"]), + /** @type {SyncHook<[Iterable, Iterable]>} */ + afterOptimizeTree: new SyncHook(["chunks", "modules"]), - /** @type {OutputFileSystem} */ - this.outputFileSystem = null; - /** @type {IntermediateFileSystem} */ - this.intermediateFileSystem = null; - /** @type {InputFileSystem} */ - this.inputFileSystem = null; - /** @type {WatchFileSystem} */ - this.watchFileSystem = null; + /** @type {AsyncSeriesBailHook<[Iterable, Iterable]>} */ + optimizeChunkModules: new AsyncSeriesBailHook(["chunks", "modules"]), + /** @type {SyncHook<[Iterable, Iterable]>} */ + afterOptimizeChunkModules: new SyncHook(["chunks", "modules"]), + /** @type {SyncBailHook<[], boolean>} */ + shouldRecord: new SyncBailHook([]), - /** @type {string|null} */ - this.recordsInputPath = null; - /** @type {string|null} */ - this.recordsOutputPath = null; - this.records = {}; - /** @type {Set} */ - this.managedPaths = new Set(); - /** @type {Set} */ - this.immutablePaths = new Set(); + /** @type {SyncHook<[Chunk, Set, RuntimeRequirementsContext]>} */ + additionalChunkRuntimeRequirements: new SyncHook([ + "chunk", + "runtimeRequirements", + "context" + ]), + /** @type {HookMap, RuntimeRequirementsContext]>>} */ + runtimeRequirementInChunk: new HookMap( + () => new SyncBailHook(["chunk", "runtimeRequirements", "context"]) + ), + /** @type {SyncHook<[Module, Set, RuntimeRequirementsContext]>} */ + additionalModuleRuntimeRequirements: new SyncHook([ + "module", + "runtimeRequirements", + "context" + ]), + /** @type {HookMap, RuntimeRequirementsContext]>>} */ + runtimeRequirementInModule: new HookMap( + () => new SyncBailHook(["module", "runtimeRequirements", "context"]) + ), + /** @type {SyncHook<[Chunk, Set, RuntimeRequirementsContext]>} */ + additionalTreeRuntimeRequirements: new SyncHook([ + "chunk", + "runtimeRequirements", + "context" + ]), + /** @type {HookMap, RuntimeRequirementsContext]>>} */ + runtimeRequirementInTree: new HookMap( + () => new SyncBailHook(["chunk", "runtimeRequirements", "context"]) + ), - /** @type {ReadonlySet} */ - this.modifiedFiles = undefined; - /** @type {ReadonlySet} */ - this.removedFiles = undefined; - /** @type {ReadonlyMap} */ - this.fileTimestamps = undefined; - /** @type {ReadonlyMap} */ - this.contextTimestamps = undefined; - /** @type {number} */ - this.fsStartTime = undefined; + /** @type {SyncHook<[RuntimeModule, Chunk]>} */ + runtimeModule: new SyncHook(["module", "chunk"]), - /** @type {ResolverFactory} */ - this.resolverFactory = new ResolverFactory(); + /** @type {SyncHook<[Iterable, any]>} */ + reviveModules: new SyncHook(["modules", "records"]), + /** @type {SyncHook<[Iterable]>} */ + beforeModuleIds: new SyncHook(["modules"]), + /** @type {SyncHook<[Iterable]>} */ + moduleIds: new SyncHook(["modules"]), + /** @type {SyncHook<[Iterable]>} */ + optimizeModuleIds: new SyncHook(["modules"]), + /** @type {SyncHook<[Iterable]>} */ + afterOptimizeModuleIds: new SyncHook(["modules"]), - this.infrastructureLogger = undefined; + /** @type {SyncHook<[Iterable, any]>} */ + reviveChunks: new SyncHook(["chunks", "records"]), + /** @type {SyncHook<[Iterable]>} */ + beforeChunkIds: new SyncHook(["chunks"]), + /** @type {SyncHook<[Iterable]>} */ + chunkIds: new SyncHook(["chunks"]), + /** @type {SyncHook<[Iterable]>} */ + optimizeChunkIds: new SyncHook(["chunks"]), + /** @type {SyncHook<[Iterable]>} */ + afterOptimizeChunkIds: new SyncHook(["chunks"]), - this.options = options; + /** @type {SyncHook<[Iterable, any]>} */ + recordModules: new SyncHook(["modules", "records"]), + /** @type {SyncHook<[Iterable, any]>} */ + recordChunks: new SyncHook(["chunks", "records"]), - this.context = context; + /** @type {SyncHook<[Iterable]>} */ + optimizeCodeGeneration: new SyncHook(["modules"]), - this.requestShortener = new RequestShortener(context, this.root); + /** @type {SyncHook<[]>} */ + beforeModuleHash: new SyncHook([]), + /** @type {SyncHook<[]>} */ + afterModuleHash: new SyncHook([]), - this.cache = new Cache(); + /** @type {SyncHook<[]>} */ + beforeCodeGeneration: new SyncHook([]), + /** @type {SyncHook<[]>} */ + afterCodeGeneration: new SyncHook([]), - /** @type {Map, memCache: WeakTupleMap }> | undefined} */ - this.moduleMemCaches = undefined; + /** @type {SyncHook<[]>} */ + beforeRuntimeRequirements: new SyncHook([]), + /** @type {SyncHook<[]>} */ + afterRuntimeRequirements: new SyncHook([]), - this.compilerPath = ""; + /** @type {SyncHook<[]>} */ + beforeHash: new SyncHook([]), + /** @type {SyncHook<[Chunk]>} */ + contentHash: new SyncHook(["chunk"]), + /** @type {SyncHook<[]>} */ + afterHash: new SyncHook([]), + /** @type {SyncHook<[any]>} */ + recordHash: new SyncHook(["records"]), + /** @type {SyncHook<[Compilation, any]>} */ + record: new SyncHook(["compilation", "records"]), - /** @type {boolean} */ - this.running = false; + /** @type {SyncHook<[]>} */ + beforeModuleAssets: new SyncHook([]), + /** @type {SyncBailHook<[], boolean>} */ + shouldGenerateChunkAssets: new SyncBailHook([]), + /** @type {SyncHook<[]>} */ + beforeChunkAssets: new SyncHook([]), + // TODO webpack 6 remove + /** @deprecated */ + additionalChunkAssets: createProcessAssetsHook( + "additionalChunkAssets", + Compilation.PROCESS_ASSETS_STAGE_ADDITIONAL, + () => [this.chunks], + "DEP_WEBPACK_COMPILATION_ADDITIONAL_CHUNK_ASSETS" + ), + + // TODO webpack 6 deprecate + /** @deprecated */ + additionalAssets: createProcessAssetsHook( + "additionalAssets", + Compilation.PROCESS_ASSETS_STAGE_ADDITIONAL, + () => [] + ), + // TODO webpack 6 remove + /** @deprecated */ + optimizeChunkAssets: createProcessAssetsHook( + "optimizeChunkAssets", + Compilation.PROCESS_ASSETS_STAGE_OPTIMIZE, + () => [this.chunks], + "DEP_WEBPACK_COMPILATION_OPTIMIZE_CHUNK_ASSETS" + ), + // TODO webpack 6 remove + /** @deprecated */ + afterOptimizeChunkAssets: createProcessAssetsHook( + "afterOptimizeChunkAssets", + Compilation.PROCESS_ASSETS_STAGE_OPTIMIZE + 1, + () => [this.chunks], + "DEP_WEBPACK_COMPILATION_AFTER_OPTIMIZE_CHUNK_ASSETS" + ), + // TODO webpack 6 deprecate + /** @deprecated */ + optimizeAssets: processAssetsHook, + // TODO webpack 6 deprecate + /** @deprecated */ + afterOptimizeAssets: afterProcessAssetsHook, + + processAssets: processAssetsHook, + afterProcessAssets: afterProcessAssetsHook, + /** @type {AsyncSeriesHook<[CompilationAssets]>} */ + processAdditionalAssets: new AsyncSeriesHook(["assets"]), + + /** @type {SyncBailHook<[], boolean>} */ + needAdditionalSeal: new SyncBailHook([]), + /** @type {AsyncSeriesHook<[]>} */ + afterSeal: new AsyncSeriesHook([]), + + /** @type {SyncWaterfallHook<[RenderManifestEntry[], RenderManifestOptions]>} */ + renderManifest: new SyncWaterfallHook(["result", "options"]), + + /** @type {SyncHook<[Hash]>} */ + fullHash: new SyncHook(["hash"]), + /** @type {SyncHook<[Chunk, Hash, ChunkHashContext]>} */ + chunkHash: new SyncHook(["chunk", "chunkHash", "ChunkHashContext"]), + + /** @type {SyncHook<[Module, string]>} */ + moduleAsset: new SyncHook(["module", "filename"]), + /** @type {SyncHook<[Chunk, string]>} */ + chunkAsset: new SyncHook(["chunk", "filename"]), + + /** @type {SyncWaterfallHook<[string, object, AssetInfo]>} */ + assetPath: new SyncWaterfallHook(["path", "options", "assetInfo"]), + /** @type {SyncBailHook<[], boolean>} */ + needAdditionalPass: new SyncBailHook([]), + + /** @type {SyncHook<[Compiler, string, number]>} */ + childCompiler: new SyncHook([ + "childCompiler", + "compilerName", + "compilerIndex" + ]), + + /** @type {SyncBailHook<[string, LogEntry], true>} */ + log: new SyncBailHook(["origin", "logEntry"]), + + /** @type {SyncWaterfallHook<[WebpackError[]]>} */ + processWarnings: new SyncWaterfallHook(["warnings"]), + /** @type {SyncWaterfallHook<[WebpackError[]]>} */ + processErrors: new SyncWaterfallHook(["errors"]), + + /** @type {HookMap, CreateStatsOptionsContext]>>} */ + statsPreset: new HookMap(() => new SyncHook(["options", "context"])), + /** @type {SyncHook<[Partial, CreateStatsOptionsContext]>} */ + statsNormalize: new SyncHook(["options", "context"]), + /** @type {SyncHook<[StatsFactory, NormalizedStatsOptions]>} */ + statsFactory: new SyncHook(["statsFactory", "options"]), + /** @type {SyncHook<[StatsPrinter, NormalizedStatsOptions]>} */ + statsPrinter: new SyncHook(["statsPrinter", "options"]), + + get normalModuleLoader() { + return getNormalModuleLoader(); + } + }); + /** @type {string=} */ + this.name = undefined; + this.startTime = undefined; + this.endTime = undefined; + /** @type {Compiler} */ + this.compiler = compiler; + this.resolverFactory = compiler.resolverFactory; + this.inputFileSystem = compiler.inputFileSystem; + this.fileSystemInfo = new FileSystemInfo(this.inputFileSystem, { + managedPaths: compiler.managedPaths, + immutablePaths: compiler.immutablePaths, + logger: this.getLogger("webpack.FileSystemInfo"), + hashFunction: compiler.options.output.hashFunction + }); + if (compiler.fileTimestamps) { + this.fileSystemInfo.addFileTimestamps(compiler.fileTimestamps, true); + } + if (compiler.contextTimestamps) { + this.fileSystemInfo.addContextTimestamps( + compiler.contextTimestamps, + true + ); + } + /** @type {Map>} */ + this.valueCacheVersions = new Map(); + this.requestShortener = compiler.requestShortener; + this.compilerPath = compiler.compilerPath; + + this.logger = this.getLogger("webpack.Compilation"); + + const options = compiler.options; + this.options = options; + this.outputOptions = options && options.output; /** @type {boolean} */ - this.idle = false; + this.bail = (options && options.bail) || false; + /** @type {boolean} */ + this.profile = (options && options.profile) || false; + + this.params = params; + this.mainTemplate = new MainTemplate(this.outputOptions, this); + this.chunkTemplate = new ChunkTemplate(this.outputOptions, this); + this.runtimeTemplate = new RuntimeTemplate( + this, + this.outputOptions, + this.requestShortener + ); + /** @type {{javascript: ModuleTemplate}} */ + this.moduleTemplates = { + javascript: new ModuleTemplate(this.runtimeTemplate, this) + }; + defineRemovedModuleTemplates(this.moduleTemplates); + + /** @type {Map> | undefined} */ + this.moduleMemCaches = undefined; + /** @type {Map> | undefined} */ + this.moduleMemCaches2 = undefined; + this.moduleGraph = new ModuleGraph(); + /** @type {ChunkGraph} */ + this.chunkGraph = undefined; + /** @type {CodeGenerationResults} */ + this.codeGenerationResults = undefined; + + /** @type {AsyncQueue} */ + this.processDependenciesQueue = new AsyncQueue({ + name: "processDependencies", + parallelism: options.parallelism || 100, + processor: this._processModuleDependencies.bind(this) + }); + /** @type {AsyncQueue} */ + this.addModuleQueue = new AsyncQueue({ + name: "addModule", + parent: this.processDependenciesQueue, + getKey: module => module.identifier(), + processor: this._addModule.bind(this) + }); + /** @type {AsyncQueue} */ + this.factorizeQueue = new AsyncQueue({ + name: "factorize", + parent: this.addModuleQueue, + processor: this._factorizeModule.bind(this) + }); + /** @type {AsyncQueue} */ + this.buildQueue = new AsyncQueue({ + name: "build", + parent: this.factorizeQueue, + processor: this._buildModule.bind(this) + }); + /** @type {AsyncQueue} */ + this.rebuildQueue = new AsyncQueue({ + name: "rebuild", + parallelism: options.parallelism || 100, + processor: this._rebuildModule.bind(this) + }); + + /** + * Modules in value are building during the build of Module in key. + * Means value blocking key from finishing. + * Needed to detect build cycles. + * @type {WeakMap>} + */ + this.creatingModuleDuringBuild = new WeakMap(); + /** @type {Map} */ + this.entries = new Map(); + /** @type {EntryData} */ + this.globalEntry = { + dependencies: [], + includeDependencies: [], + options: { + name: undefined + } + }; + /** @type {Map} */ + this.entrypoints = new Map(); + /** @type {Entrypoint[]} */ + this.asyncEntrypoints = []; + /** @type {Set} */ + this.chunks = new Set(); + /** @type {ChunkGroup[]} */ + this.chunkGroups = []; + /** @type {Map} */ + this.namedChunkGroups = new Map(); + /** @type {Map} */ + this.namedChunks = new Map(); + /** @type {Set} */ + this.modules = new Set(); + if (this._backCompat) { + arrayToSetDeprecation(this.chunks, "Compilation.chunks"); + arrayToSetDeprecation(this.modules, "Compilation.modules"); + } + /** @private @type {Map} */ + this._modules = new Map(); + this.records = null; + /** @type {string[]} */ + this.additionalChunkAssets = []; + /** @type {CompilationAssets} */ + this.assets = {}; + /** @type {Map} */ + this.assetsInfo = new Map(); + /** @type {Map>>} */ + this._assetsRelatedIn = new Map(); + /** @type {WebpackError[]} */ + this.errors = []; + /** @type {WebpackError[]} */ + this.warnings = []; + /** @type {Compilation[]} */ + this.children = []; + /** @type {Map} */ + this.logging = new Map(); + /** @type {Map} */ + this.dependencyFactories = new Map(); + /** @type {DependencyTemplates} */ + this.dependencyTemplates = new DependencyTemplates(); + this.childrenCounters = {}; + /** @type {Set} */ + this.usedChunkIds = null; + /** @type {Set} */ + this.usedModuleIds = null; /** @type {boolean} */ - this.watchMode = false; + this.needAdditionalPass = false; + /** @type {Set} */ + this._restoredUnsafeCacheModuleEntries = new Set(); + /** @type {Map} */ + this._restoredUnsafeCacheEntries = new Map(); + /** @type {WeakSet} */ + this.builtModules = new WeakSet(); + /** @type {WeakSet} */ + this.codeGeneratedModules = new WeakSet(); + /** @type {WeakSet} */ + this.buildTimeExecutedModules = new WeakSet(); + /** @private @type {Map} */ + this._rebuildingModules = new Map(); + /** @type {Set} */ + this.emittedAssets = new Set(); + /** @type {Set} */ + this.comparedForEmitAssets = new Set(); + /** @type {LazySet} */ + this.fileDependencies = new LazySet(); + /** @type {LazySet} */ + this.contextDependencies = new LazySet(); + /** @type {LazySet} */ + this.missingDependencies = new LazySet(); + /** @type {LazySet} */ + this.buildDependencies = new LazySet(); + // TODO webpack 6 remove + this.compilationDependencies = { + add: util.deprecate( + item => this.fileDependencies.add(item), + "Compilation.compilationDependencies is deprecated (used Compilation.fileDependencies instead)", + "DEP_WEBPACK_COMPILATION_COMPILATION_DEPENDENCIES" + ) + }; - this._backCompat = this.options.experiments.backCompat !== false; + this._modulesCache = this.getCache("Compilation/modules"); + this._assetsCache = this.getCache("Compilation/assets"); + this._codeGenerationCache = this.getCache("Compilation/codeGeneration"); - /** @type {Compilation} */ - this._lastCompilation = undefined; - /** @type {NormalModuleFactory} */ - this._lastNormalModuleFactory = undefined; + const unsafeCache = options.module.unsafeCache; + this._unsafeCache = !!unsafeCache; + this._unsafeCachePredicate = + typeof unsafeCache === "function" ? unsafeCache : () => true; + } - /** @private @type {WeakMap }>} */ - this._assetEmittingSourceCache = new WeakMap(); - /** @private @type {Map} */ - this._assetEmittingWrittenFiles = new Map(); - /** @private @type {Set} */ - this._assetEmittingPreviousFiles = new Set(); + getStats() { + return new Stats(this); + } + + /** + * @param {StatsOptions | string} optionsOrPreset stats option value + * @param {CreateStatsOptionsContext} context context + * @returns {NormalizedStatsOptions} normalized options + */ + createStatsOptions(optionsOrPreset, context = {}) { + if ( + typeof optionsOrPreset === "boolean" || + typeof optionsOrPreset === "string" + ) { + optionsOrPreset = { preset: optionsOrPreset }; + } + if (typeof optionsOrPreset === "object" && optionsOrPreset !== null) { + // We use this method of shallow cloning this object to include + // properties in the prototype chain + /** @type {Partial} */ + const options = {}; + for (const key in optionsOrPreset) { + options[key] = optionsOrPreset[key]; + } + if (options.preset !== undefined) { + this.hooks.statsPreset.for(options.preset).call(options, context); + } + this.hooks.statsNormalize.call(options, context); + return /** @type {NormalizedStatsOptions} */ (options); + } else { + /** @type {Partial} */ + const options = {}; + this.hooks.statsNormalize.call(options, context); + return /** @type {NormalizedStatsOptions} */ (options); + } + } + + createStatsFactory(options) { + const statsFactory = new StatsFactory(); + this.hooks.statsFactory.call(statsFactory, options); + return statsFactory; + } + + createStatsPrinter(options) { + const statsPrinter = new StatsPrinter(); + this.hooks.statsPrinter.call(statsPrinter, options); + return statsPrinter; } /** @@ -33514,48 +30974,80 @@ class Compiler { * @returns {CacheFacade} the cache facade instance */ getCache(name) { - return new CacheFacade( - this.cache, - `${this.compilerPath}${name}`, - this.options.output.hashFunction - ); + return this.compiler.getCache(name); } /** * @param {string | (function(): string)} name name of the logger, or function called once to get the logger name * @returns {Logger} a logger with that name */ - getInfrastructureLogger(name) { + getLogger(name) { if (!name) { - throw new TypeError( - "Compiler.getInfrastructureLogger(name) called without a name" - ); + throw new TypeError("Compilation.getLogger(name) called without a name"); } + /** @type {LogEntry[] | undefined} */ + let logEntries; return new Logger( (type, args) => { if (typeof name === "function") { name = name(); if (!name) { throw new TypeError( - "Compiler.getInfrastructureLogger(name) called with a function not returning a name" + "Compilation.getLogger(name) called with a function not returning a name" ); } } - if (this.hooks.infrastructureLog.call(name, type, args) === undefined) { - if (this.infrastructureLogger !== undefined) { - this.infrastructureLogger(name, type, args); - } + let trace; + switch (type) { + case LogType.warn: + case LogType.error: + case LogType.trace: + trace = ErrorHelpers.cutOffLoaderExecution(new Error("Trace").stack) + .split("\n") + .slice(3); + break; } - }, - childName => { - if (typeof name === "function") { + /** @type {LogEntry} */ + const logEntry = { + time: Date.now(), + type, + args, + trace + }; + if (this.hooks.log.call(name, logEntry) === undefined) { + if (logEntry.type === LogType.profileEnd) { + // eslint-disable-next-line node/no-unsupported-features/node-builtins + if (typeof console.profileEnd === "function") { + // eslint-disable-next-line node/no-unsupported-features/node-builtins + console.profileEnd(`[${name}] ${logEntry.args[0]}`); + } + } + if (logEntries === undefined) { + logEntries = this.logging.get(name); + if (logEntries === undefined) { + logEntries = []; + this.logging.set(name, logEntries); + } + } + logEntries.push(logEntry); + if (logEntry.type === LogType.profile) { + // eslint-disable-next-line node/no-unsupported-features/node-builtins + if (typeof console.profile === "function") { + // eslint-disable-next-line node/no-unsupported-features/node-builtins + console.profile(`[${name}] ${logEntry.args[0]}`); + } + } + } + }, + childName => { + if (typeof name === "function") { if (typeof childName === "function") { - return this.getInfrastructureLogger(() => { + return this.getLogger(() => { if (typeof name === "function") { name = name(); if (!name) { throw new TypeError( - "Compiler.getInfrastructureLogger(name) called with a function not returning a name" + "Compilation.getLogger(name) called with a function not returning a name" ); } } @@ -33570,12 +31062,12 @@ class Compiler { return `${name}/${childName}`; }); } else { - return this.getInfrastructureLogger(() => { + return this.getLogger(() => { if (typeof name === "function") { name = name(); if (!name) { throw new TypeError( - "Compiler.getInfrastructureLogger(name) called with a function not returning a name" + "Compilation.getLogger(name) called with a function not returning a name" ); } } @@ -33584,7 +31076,7 @@ class Compiler { } } else { if (typeof childName === "function") { - return this.getInfrastructureLogger(() => { + return this.getLogger(() => { if (typeof childName === "function") { childName = childName(); if (!childName) { @@ -33596,3927 +31088,3992 @@ class Compiler { return `${name}/${childName}`; }); } else { - return this.getInfrastructureLogger(`${name}/${childName}`); + return this.getLogger(`${name}/${childName}`); } } } ); } - // TODO webpack 6: solve this in a better way - // e.g. move compilation specific info from Modules into ModuleGraph - _cleanupLastCompilation() { - if (this._lastCompilation !== undefined) { - for (const module of this._lastCompilation.modules) { - ChunkGraph.clearChunkGraphForModule(module); - ModuleGraph.clearModuleGraphForModule(module); - module.cleanupForCache(); - } - for (const chunk of this._lastCompilation.chunks) { - ChunkGraph.clearChunkGraphForChunk(chunk); - } - this._lastCompilation = undefined; - } - } - - // TODO webpack 6: solve this in a better way - _cleanupLastNormalModuleFactory() { - if (this._lastNormalModuleFactory !== undefined) { - this._lastNormalModuleFactory.cleanupForCache(); - this._lastNormalModuleFactory = undefined; - } - } - /** - * @param {WatchOptions} watchOptions the watcher's options - * @param {Callback} handler signals when the call finishes - * @returns {Watching} a compiler watcher + * @param {Module} module module to be added that was created + * @param {ModuleCallback} callback returns the module in the compilation, + * it could be the passed one (if new), or an already existing in the compilation + * @returns {void} */ - watch(watchOptions, handler) { - if (this.running) { - return handler(new ConcurrentCompilationError()); - } - - this.running = true; - this.watchMode = true; - this.watching = new Watching(this, watchOptions, handler); - return this.watching; + addModule(module, callback) { + this.addModuleQueue.add(module, callback); } /** - * @param {Callback} callback signals when the call finishes + * @param {Module} module module to be added that was created + * @param {ModuleCallback} callback returns the module in the compilation, + * it could be the passed one (if new), or an already existing in the compilation * @returns {void} */ - run(callback) { - if (this.running) { - return callback(new ConcurrentCompilationError()); + _addModule(module, callback) { + const identifier = module.identifier(); + const alreadyAddedModule = this._modules.get(identifier); + if (alreadyAddedModule) { + return callback(null, alreadyAddedModule); } - let logger; + const currentProfile = this.profile + ? this.moduleGraph.getProfile(module) + : undefined; + if (currentProfile !== undefined) { + currentProfile.markRestoringStart(); + } - const finalCallback = (err, stats) => { - if (logger) logger.time("beginIdle"); - this.idle = true; - this.cache.beginIdle(); - this.idle = true; - if (logger) logger.timeEnd("beginIdle"); - this.running = false; - if (err) { - this.hooks.failed.call(err); + this._modulesCache.get(identifier, null, (err, cacheModule) => { + if (err) return callback(new ModuleRestoreError(module, err)); + + if (currentProfile !== undefined) { + currentProfile.markRestoringEnd(); + currentProfile.markIntegrationStart(); } - if (callback !== undefined) callback(err, stats); - this.hooks.afterDone.call(stats); - }; - const startTime = Date.now(); + if (cacheModule) { + cacheModule.updateCacheModule(module); - this.running = true; + module = cacheModule; + } + this._modules.set(identifier, module); + this.modules.add(module); + if (this._backCompat) + ModuleGraph.setModuleGraphForModule(module, this.moduleGraph); + if (currentProfile !== undefined) { + currentProfile.markIntegrationEnd(); + } + callback(null, module); + }); + } - const onCompiled = (err, compilation) => { - if (err) return finalCallback(err); + /** + * Fetches a module from a compilation by its identifier + * @param {Module} module the module provided + * @returns {Module} the module requested + */ + getModule(module) { + const identifier = module.identifier(); + return this._modules.get(identifier); + } - if (this.hooks.shouldEmit.call(compilation) === false) { - compilation.startTime = startTime; - compilation.endTime = Date.now(); - const stats = new Stats(compilation); - this.hooks.done.callAsync(stats, err => { - if (err) return finalCallback(err); - return finalCallback(null, stats); - }); - return; - } + /** + * Attempts to search for a module by its identifier + * @param {string} identifier identifier (usually path) for module + * @returns {Module|undefined} attempt to search for module and return it, else undefined + */ + findModule(identifier) { + return this._modules.get(identifier); + } - process.nextTick(() => { - logger = compilation.getLogger("webpack.Compiler"); - logger.time("emitAssets"); - this.emitAssets(compilation, err => { - logger.timeEnd("emitAssets"); - if (err) return finalCallback(err); + /** + * Schedules a build of the module object + * + * @param {Module} module module to be built + * @param {ModuleCallback} callback the callback + * @returns {void} + */ + buildModule(module, callback) { + this.buildQueue.add(module, callback); + } - if (compilation.hooks.needAdditionalPass.call()) { - compilation.needAdditionalPass = true; + /** + * Builds the module object + * + * @param {Module} module module to be built + * @param {ModuleCallback} callback the callback + * @returns {void} + */ + _buildModule(module, callback) { + const currentProfile = this.profile + ? this.moduleGraph.getProfile(module) + : undefined; + if (currentProfile !== undefined) { + currentProfile.markBuildingStart(); + } - compilation.startTime = startTime; - compilation.endTime = Date.now(); - logger.time("done hook"); - const stats = new Stats(compilation); - this.hooks.done.callAsync(stats, err => { - logger.timeEnd("done hook"); - if (err) return finalCallback(err); + module.needBuild( + { + compilation: this, + fileSystemInfo: this.fileSystemInfo, + valueCacheVersions: this.valueCacheVersions + }, + (err, needBuild) => { + if (err) return callback(err); - this.hooks.additionalPass.callAsync(err => { - if (err) return finalCallback(err); - this.compile(onCompiled); - }); - }); - return; + if (!needBuild) { + if (currentProfile !== undefined) { + currentProfile.markBuildingEnd(); } + this.hooks.stillValidModule.call(module); + return callback(); + } - logger.time("emitRecords"); - this.emitRecords(err => { - logger.timeEnd("emitRecords"); - if (err) return finalCallback(err); - - compilation.startTime = startTime; - compilation.endTime = Date.now(); - logger.time("done hook"); - const stats = new Stats(compilation); - this.hooks.done.callAsync(stats, err => { - logger.timeEnd("done hook"); - if (err) return finalCallback(err); - this.cache.storeBuildDependencies( - compilation.buildDependencies, - err => { - if (err) return finalCallback(err); - return finalCallback(null, stats); - } - ); + this.hooks.buildModule.call(module); + this.builtModules.add(module); + module.build( + this.options, + this, + this.resolverFactory.get("normal", module.resolveOptions), + this.inputFileSystem, + err => { + if (currentProfile !== undefined) { + currentProfile.markBuildingEnd(); + } + if (err) { + this.hooks.failedModule.call(module, err); + return callback(err); + } + if (currentProfile !== undefined) { + currentProfile.markStoringStart(); + } + this._modulesCache.store(module.identifier(), null, module, err => { + if (currentProfile !== undefined) { + currentProfile.markStoringEnd(); + } + if (err) { + this.hooks.failedModule.call(module, err); + return callback(new ModuleStoreError(module, err)); + } + this.hooks.succeedModule.call(module); + return callback(); }); - }); - }); - }); - }; - - const run = () => { - this.hooks.beforeRun.callAsync(this, err => { - if (err) return finalCallback(err); - - this.hooks.run.callAsync(this, err => { - if (err) return finalCallback(err); - - this.readRecords(err => { - if (err) return finalCallback(err); - - this.compile(onCompiled); - }); - }); - }); - }; - - if (this.idle) { - this.cache.endIdle(err => { - if (err) return finalCallback(err); - - this.idle = false; - run(); - }); - } else { - run(); - } + } + ); + } + ); } /** - * @param {RunAsChildCallback} callback signals when the call finishes + * @param {Module} module to be processed for deps + * @param {ModuleCallback} callback callback to be triggered * @returns {void} */ - runAsChild(callback) { - const startTime = Date.now(); - this.compile((err, compilation) => { - if (err) return callback(err); + processModuleDependencies(module, callback) { + this.processDependenciesQueue.add(module, callback); + } - this.parentCompilation.children.push(compilation); - for (const { name, source, info } of compilation.getAssets()) { - this.parentCompilation.emitAsset(name, source, info); + /** + * @param {Module} module to be processed for deps + * @returns {void} + */ + processModuleDependenciesNonRecursive(module) { + const processDependenciesBlock = block => { + if (block.dependencies) { + let i = 0; + for (const dep of block.dependencies) { + this.moduleGraph.setParents(dep, block, module, i++); + } } - - const entries = []; - for (const ep of compilation.entrypoints.values()) { - entries.push(...ep.chunks); + if (block.blocks) { + for (const b of block.blocks) processDependenciesBlock(b); } + }; - compilation.startTime = startTime; - compilation.endTime = Date.now(); - - return callback(null, entries, compilation); - }); - } - - purgeInputFileSystem() { - if (this.inputFileSystem && this.inputFileSystem.purge) { - this.inputFileSystem.purge(); - } + processDependenciesBlock(module); } /** - * @param {Compilation} compilation the compilation - * @param {Callback} callback signals when the assets are emitted + * @param {Module} module to be processed for deps + * @param {ModuleCallback} callback callback to be triggered * @returns {void} */ - emitAssets(compilation, callback) { - let outputPath; - - const emitFiles = err => { - if (err) return callback(err); + _processModuleDependencies(module, callback) { + /** @type {Array<{factory: ModuleFactory, dependencies: Dependency[], originModule: Module|null}>} */ + const sortedDependencies = []; - const assets = compilation.getAssets(); - compilation.assets = { ...compilation.assets }; - /** @type {Map} */ - const caseInsensitiveMap = new Map(); - /** @type {Set} */ - const allTargetPaths = new Set(); - asyncLib.forEachLimit( - assets, - 15, - ({ name: file, source, info }, callback) => { - let targetFile = file; - let immutable = info.immutable; - const queryStringIdx = targetFile.indexOf("?"); - if (queryStringIdx >= 0) { - targetFile = targetFile.substr(0, queryStringIdx); - // We may remove the hash, which is in the query string - // So we recheck if the file is immutable - // This doesn't cover all cases, but immutable is only a performance optimization anyway - immutable = - immutable && - (includesHash(targetFile, info.contenthash) || - includesHash(targetFile, info.chunkhash) || - includesHash(targetFile, info.modulehash) || - includesHash(targetFile, info.fullhash)); - } + /** @type {DependenciesBlock} */ + let currentBlock; - const writeOut = err => { - if (err) return callback(err); - const targetPath = join( - this.outputFileSystem, - outputPath, - targetFile - ); - allTargetPaths.add(targetPath); + /** @type {Map>} */ + let dependencies; + /** @type {DepConstructor} */ + let factoryCacheKey; + /** @type {ModuleFactory} */ + let factoryCacheKey2; + /** @type {Map} */ + let factoryCacheValue; + /** @type {string} */ + let listCacheKey1; + /** @type {string} */ + let listCacheKey2; + /** @type {Dependency[]} */ + let listCacheValue; - // check if the target file has already been written by this Compiler - const targetFileGeneration = - this._assetEmittingWrittenFiles.get(targetPath); + let inProgressSorting = 1; + let inProgressTransitive = 1; - // create an cache entry for this Source if not already existing - let cacheEntry = this._assetEmittingSourceCache.get(source); - if (cacheEntry === undefined) { - cacheEntry = { - sizeOnlySource: undefined, - writtenTo: new Map() - }; - this._assetEmittingSourceCache.set(source, cacheEntry); - } + const onDependenciesSorted = err => { + if (err) return callback(err); - let similarEntry; + // early exit without changing parallelism back and forth + if (sortedDependencies.length === 0 && inProgressTransitive === 1) { + return callback(); + } - const checkSimilarFile = () => { - const caseInsensitiveTargetPath = targetPath.toLowerCase(); - similarEntry = caseInsensitiveMap.get(caseInsensitiveTargetPath); - if (similarEntry !== undefined) { - const { path: other, source: otherSource } = similarEntry; - if (isSourceEqual(otherSource, source)) { - // Size may or may not be available at this point. - // If it's not available add to "waiting" list and it will be updated once available - if (similarEntry.size !== undefined) { - updateWithReplacementSource(similarEntry.size); - } else { - if (!similarEntry.waiting) similarEntry.waiting = []; - similarEntry.waiting.push({ file, cacheEntry }); - } - alreadyWritten(); - } else { - const err = - new WebpackError(`Prevent writing to file that only differs in casing or query string from already written file. -This will lead to a race-condition and corrupted files on case-insensitive file systems. -${targetPath} -${other}`); - err.file = file; - callback(err); - } - return true; - } else { - caseInsensitiveMap.set( - caseInsensitiveTargetPath, - (similarEntry = { - path: targetPath, - source, - size: undefined, - waiting: undefined - }) - ); - return false; - } - }; + // This is nested so we need to allow one additional task + this.processDependenciesQueue.increaseParallelism(); - /** - * get the binary (Buffer) content from the Source - * @returns {Buffer} content for the source - */ - const getContent = () => { - if (typeof source.buffer === "function") { - return source.buffer(); - } else { - const bufferOrString = source.source(); - if (Buffer.isBuffer(bufferOrString)) { - return bufferOrString; - } else { - return Buffer.from(bufferOrString, "utf8"); - } - } - }; + for (const item of sortedDependencies) { + inProgressTransitive++; + this.handleModuleCreation(item, err => { + // In V8, the Error objects keep a reference to the functions on the stack. These warnings & + // errors are created inside closures that keep a reference to the Compilation, so errors are + // leaking the Compilation object. + if (err && this.bail) { + if (inProgressTransitive <= 0) return; + inProgressTransitive = -1; + // eslint-disable-next-line no-self-assign + err.stack = err.stack; + onTransitiveTasksFinished(err); + return; + } + if (--inProgressTransitive === 0) onTransitiveTasksFinished(); + }); + } + if (--inProgressTransitive === 0) onTransitiveTasksFinished(); + }; - const alreadyWritten = () => { - // cache the information that the Source has been already been written to that location - if (targetFileGeneration === undefined) { - const newGeneration = 1; - this._assetEmittingWrittenFiles.set(targetPath, newGeneration); - cacheEntry.writtenTo.set(targetPath, newGeneration); - } else { - cacheEntry.writtenTo.set(targetPath, targetFileGeneration); - } - callback(); - }; - - /** - * Write the file to output file system - * @param {Buffer} content content to be written - * @returns {void} - */ - const doWrite = content => { - this.outputFileSystem.writeFile(targetPath, content, err => { - if (err) return callback(err); - - // information marker that the asset has been emitted - compilation.emittedAssets.add(file); + const onTransitiveTasksFinished = err => { + if (err) return callback(err); + this.processDependenciesQueue.decreaseParallelism(); - // cache the information that the Source has been written to that location - const newGeneration = - targetFileGeneration === undefined - ? 1 - : targetFileGeneration + 1; - cacheEntry.writtenTo.set(targetPath, newGeneration); - this._assetEmittingWrittenFiles.set(targetPath, newGeneration); - this.hooks.assetEmitted.callAsync( - file, - { - content, - source, - outputPath, - compilation, - targetPath - }, - callback - ); - }); - }; + return callback(); + }; - const updateWithReplacementSource = size => { - updateFileWithReplacementSource(file, cacheEntry, size); - similarEntry.size = size; - if (similarEntry.waiting !== undefined) { - for (const { file, cacheEntry } of similarEntry.waiting) { - updateFileWithReplacementSource(file, cacheEntry, size); - } + /** + * @param {Dependency} dep dependency + * @param {number} index index in block + * @returns {void} + */ + const processDependency = (dep, index) => { + this.moduleGraph.setParents(dep, currentBlock, module, index); + if (this._unsafeCache) { + try { + const unsafeCachedModule = unsafeCacheDependencies.get(dep); + if (unsafeCachedModule === null) return; + if (unsafeCachedModule !== undefined) { + if ( + this._restoredUnsafeCacheModuleEntries.has(unsafeCachedModule) + ) { + this._handleExistingModuleFromUnsafeCache( + module, + dep, + unsafeCachedModule + ); + return; + } + const identifier = unsafeCachedModule.identifier(); + const cachedModule = + this._restoredUnsafeCacheEntries.get(identifier); + if (cachedModule !== undefined) { + // update unsafe cache to new module + unsafeCacheDependencies.set(dep, cachedModule); + this._handleExistingModuleFromUnsafeCache( + module, + dep, + cachedModule + ); + return; + } + inProgressSorting++; + this._modulesCache.get(identifier, null, (err, cachedModule) => { + if (err) { + if (inProgressSorting <= 0) return; + inProgressSorting = -1; + onDependenciesSorted(err); + return; } - }; - - const updateFileWithReplacementSource = ( - file, - cacheEntry, - size - ) => { - // Create a replacement resource which only allows to ask for size - // This allows to GC all memory allocated by the Source - // (expect when the Source is stored in any other cache) - if (!cacheEntry.sizeOnlySource) { - cacheEntry.sizeOnlySource = new SizeOnlySource(size); + try { + if (!this._restoredUnsafeCacheEntries.has(identifier)) { + const data = unsafeCacheData.get(cachedModule); + if (data === undefined) { + processDependencyForResolving(dep); + if (--inProgressSorting === 0) onDependenciesSorted(); + return; + } + if (cachedModule !== unsafeCachedModule) { + unsafeCacheDependencies.set(dep, cachedModule); + } + cachedModule.restoreFromUnsafeCache( + data, + this.params.normalModuleFactory, + this.params + ); + this._restoredUnsafeCacheEntries.set( + identifier, + cachedModule + ); + this._restoredUnsafeCacheModuleEntries.add(cachedModule); + if (!this.modules.has(cachedModule)) { + inProgressTransitive++; + this._handleNewModuleFromUnsafeCache( + module, + dep, + cachedModule, + err => { + if (err) { + if (inProgressTransitive <= 0) return; + inProgressTransitive = -1; + onTransitiveTasksFinished(err); + } + if (--inProgressTransitive === 0) + return onTransitiveTasksFinished(); + } + ); + if (--inProgressSorting === 0) onDependenciesSorted(); + return; + } + } + if (unsafeCachedModule !== cachedModule) { + unsafeCacheDependencies.set(dep, cachedModule); + } + this._handleExistingModuleFromUnsafeCache( + module, + dep, + cachedModule + ); // a3 + } catch (err) { + if (inProgressSorting <= 0) return; + inProgressSorting = -1; + onDependenciesSorted(err); + return; } - compilation.updateAsset(file, cacheEntry.sizeOnlySource, { - size - }); - }; + if (--inProgressSorting === 0) onDependenciesSorted(); + }); + return; + } + } catch (e) { + console.error(e); + } + } + processDependencyForResolving(dep); + }; - const processExistingFile = stats => { - // skip emitting if it's already there and an immutable file - if (immutable) { - updateWithReplacementSource(stats.size); - return alreadyWritten(); + /** + * @param {Dependency} dep dependency + * @returns {void} + */ + const processDependencyForResolving = dep => { + const resourceIdent = dep.getResourceIdentifier(); + if (resourceIdent !== undefined && resourceIdent !== null) { + const category = dep.category; + const constructor = /** @type {DepConstructor} */ (dep.constructor); + if (factoryCacheKey === constructor) { + // Fast path 1: same constructor as prev item + if (listCacheKey1 === category && listCacheKey2 === resourceIdent) { + // Super fast path 1: also same resource + listCacheValue.push(dep); + return; + } + } else { + const factory = this.dependencyFactories.get(constructor); + if (factory === undefined) { + throw new Error( + `No module factory available for dependency type: ${constructor.name}` + ); + } + if (factoryCacheKey2 === factory) { + // Fast path 2: same factory as prev item + factoryCacheKey = constructor; + if (listCacheKey1 === category && listCacheKey2 === resourceIdent) { + // Super fast path 2: also same resource + listCacheValue.push(dep); + return; + } + } else { + // Slow path + if (factoryCacheKey2 !== undefined) { + // Archive last cache entry + if (dependencies === undefined) dependencies = new Map(); + dependencies.set(factoryCacheKey2, factoryCacheValue); + factoryCacheValue = dependencies.get(factory); + if (factoryCacheValue === undefined) { + factoryCacheValue = new Map(); } + } else { + factoryCacheValue = new Map(); + } + factoryCacheKey = constructor; + factoryCacheKey2 = factory; + } + } + // Here webpack is using heuristic that assumes + // mostly esm dependencies would be used + // so we don't allocate extra string for them + const cacheKey = + category === esmDependencyCategory + ? resourceIdent + : `${category}${resourceIdent}`; + let list = factoryCacheValue.get(cacheKey); + if (list === undefined) { + factoryCacheValue.set(cacheKey, (list = [])); + sortedDependencies.push({ + factory: factoryCacheKey2, + dependencies: list, + originModule: module + }); + } + list.push(dep); + listCacheKey1 = category; + listCacheKey2 = resourceIdent; + listCacheValue = list; + } + }; - const content = getContent(); + try { + /** @type {DependenciesBlock[]} */ + const queue = [module]; + do { + const block = queue.pop(); + if (block.dependencies) { + currentBlock = block; + let i = 0; + for (const dep of block.dependencies) processDependency(dep, i++); + } + if (block.blocks) { + for (const b of block.blocks) queue.push(b); + } + } while (queue.length !== 0); + } catch (e) { + return callback(e); + } - updateWithReplacementSource(content.length); + if (--inProgressSorting === 0) onDependenciesSorted(); + } - // if it exists and content on disk matches content - // skip writing the same content again - // (to keep mtime and don't trigger watchers) - // for a fast negative match file size is compared first - if (content.length === stats.size) { - compilation.comparedForEmitAssets.add(file); - return this.outputFileSystem.readFile( - targetPath, - (err, existingContent) => { - if ( - err || - !content.equals(/** @type {Buffer} */ (existingContent)) - ) { - return doWrite(content); - } else { - return alreadyWritten(); - } - } - ); - } + _handleNewModuleFromUnsafeCache(originModule, dependency, module, callback) { + const moduleGraph = this.moduleGraph; - return doWrite(content); - }; + moduleGraph.setResolvedModule(originModule, dependency, module); - const processMissingFile = () => { - const content = getContent(); + moduleGraph.setIssuerIfUnset( + module, + originModule !== undefined ? originModule : null + ); - updateWithReplacementSource(content.length); + this._modules.set(module.identifier(), module); + this.modules.add(module); + if (this._backCompat) + ModuleGraph.setModuleGraphForModule(module, this.moduleGraph); - return doWrite(content); - }; + this._handleModuleBuildAndDependencies( + originModule, + module, + true, + callback + ); + } - // if the target file has already been written - if (targetFileGeneration !== undefined) { - // check if the Source has been written to this target file - const writtenGeneration = cacheEntry.writtenTo.get(targetPath); - if (writtenGeneration === targetFileGeneration) { - // if yes, we may skip writing the file - // if it's already there - // (we assume one doesn't modify files while the Compiler is running, other then removing them) + _handleExistingModuleFromUnsafeCache(originModule, dependency, module) { + const moduleGraph = this.moduleGraph; - if (this._assetEmittingPreviousFiles.has(targetPath)) { - // We assume that assets from the last compilation say intact on disk (they are not removed) - compilation.updateAsset(file, cacheEntry.sizeOnlySource, { - size: cacheEntry.sizeOnlySource.size() - }); + moduleGraph.setResolvedModule(originModule, dependency, module); + } - return callback(); - } else { - // Settings immutable will make it accept file content without comparing when file exist - immutable = true; - } - } else if (!immutable) { - if (checkSimilarFile()) return; - // We wrote to this file before which has very likely a different content - // skip comparing and assume content is different for performance - // This case happens often during watch mode. - return processMissingFile(); - } - } + /** + * @typedef {Object} HandleModuleCreationOptions + * @property {ModuleFactory} factory + * @property {Dependency[]} dependencies + * @property {Module | null} originModule + * @property {Partial=} contextInfo + * @property {string=} context + * @property {boolean=} recursive recurse into dependencies of the created module + * @property {boolean=} connectOrigin connect the resolved module with the origin module + */ - if (checkSimilarFile()) return; - if (this.options.output.compareBeforeEmit) { - this.outputFileSystem.stat(targetPath, (err, stats) => { - const exists = !err && stats.isFile(); + /** + * @param {HandleModuleCreationOptions} options options object + * @param {ModuleCallback} callback callback + * @returns {void} + */ + handleModuleCreation( + { + factory, + dependencies, + originModule, + contextInfo, + context, + recursive = true, + connectOrigin = recursive + }, + callback + ) { + const moduleGraph = this.moduleGraph; - if (exists) { - processExistingFile(stats); - } else { - processMissingFile(); - } - }); - } else { - processMissingFile(); - } - }; + const currentProfile = this.profile ? new ModuleProfile() : undefined; - if (targetFile.match(/\/|\\/)) { - const fs = this.outputFileSystem; - const dir = dirname(fs, join(fs, outputPath, targetFile)); - mkdirp(fs, dir, writeOut); - } else { - writeOut(); + this.factorizeModule( + { + currentProfile, + factory, + dependencies, + factoryResult: true, + originModule, + contextInfo, + context + }, + (err, factoryResult) => { + const applyFactoryResultDependencies = () => { + const { fileDependencies, contextDependencies, missingDependencies } = + factoryResult; + if (fileDependencies) { + this.fileDependencies.addAll(fileDependencies); } - }, - err => { - // Clear map to free up memory - caseInsensitiveMap.clear(); - if (err) { - this._assetEmittingPreviousFiles.clear(); + if (contextDependencies) { + this.contextDependencies.addAll(contextDependencies); + } + if (missingDependencies) { + this.missingDependencies.addAll(missingDependencies); + } + }; + if (err) { + if (factoryResult) applyFactoryResultDependencies(); + if (dependencies.every(d => d.optional)) { + this.warnings.push(err); + return callback(); + } else { + this.errors.push(err); return callback(err); } + } - this._assetEmittingPreviousFiles = allTargetPaths; - - this.hooks.afterEmit.callAsync(compilation, err => { - if (err) return callback(err); + const newModule = factoryResult.module; - return callback(); - }); + if (!newModule) { + applyFactoryResultDependencies(); + return callback(); } - ); - }; - - this.hooks.emit.callAsync(compilation, err => { - if (err) return callback(err); - outputPath = compilation.getPath(this.outputPath, {}); - mkdirp(this.outputFileSystem, outputPath, emitFiles); - }); - } - /** - * @param {Callback} callback signals when the call finishes - * @returns {void} - */ - emitRecords(callback) { - if (!this.recordsOutputPath) return callback(); + if (currentProfile !== undefined) { + moduleGraph.setProfile(newModule, currentProfile); + } - const writeFile = () => { - this.outputFileSystem.writeFile( - this.recordsOutputPath, - JSON.stringify( - this.records, - (n, value) => { - if ( - typeof value === "object" && - value !== null && - !Array.isArray(value) - ) { - const keys = Object.keys(value); - if (!isSorted(keys)) { - return sortObject(value, keys); - } + this.addModule(newModule, (err, module) => { + if (err) { + applyFactoryResultDependencies(); + if (!err.module) { + err.module = module; } - return value; - }, - 2 - ), - callback - ); - }; + this.errors.push(err); - const recordsOutputPathDirectory = dirname( - this.outputFileSystem, - this.recordsOutputPath - ); - if (!recordsOutputPathDirectory) { - return writeFile(); - } - mkdirp(this.outputFileSystem, recordsOutputPathDirectory, err => { - if (err) return callback(err); - writeFile(); - }); - } + return callback(err); + } - /** - * @param {Callback} callback signals when the call finishes - * @returns {void} - */ - readRecords(callback) { - if (!this.recordsInputPath) { - this.records = {}; - return callback(); - } - this.inputFileSystem.stat(this.recordsInputPath, err => { - // It doesn't exist - // We can ignore this. - if (err) return callback(); + if ( + this._unsafeCache && + factoryResult.cacheable !== false && + /** @type {any} */ (module).restoreFromUnsafeCache && + this._unsafeCachePredicate(module) + ) { + const unsafeCacheableModule = + /** @type {Module & { restoreFromUnsafeCache: Function }} */ ( + module + ); + for (let i = 0; i < dependencies.length; i++) { + const dependency = dependencies[i]; + moduleGraph.setResolvedModule( + connectOrigin ? originModule : null, + dependency, + unsafeCacheableModule + ); + unsafeCacheDependencies.set(dependency, unsafeCacheableModule); + } + if (!unsafeCacheData.has(unsafeCacheableModule)) { + unsafeCacheData.set( + unsafeCacheableModule, + unsafeCacheableModule.getUnsafeCacheData() + ); + } + } else { + applyFactoryResultDependencies(); + for (let i = 0; i < dependencies.length; i++) { + const dependency = dependencies[i]; + moduleGraph.setResolvedModule( + connectOrigin ? originModule : null, + dependency, + module + ); + } + } - this.inputFileSystem.readFile(this.recordsInputPath, (err, content) => { - if (err) return callback(err); + moduleGraph.setIssuerIfUnset( + module, + originModule !== undefined ? originModule : null + ); + if (module !== newModule) { + if (currentProfile !== undefined) { + const otherProfile = moduleGraph.getProfile(module); + if (otherProfile !== undefined) { + currentProfile.mergeInto(otherProfile); + } else { + moduleGraph.setProfile(module, currentProfile); + } + } + } - try { - this.records = parseJson(content.toString("utf-8")); - } catch (e) { - e.message = "Cannot parse records: " + e.message; - return callback(e); + this._handleModuleBuildAndDependencies( + originModule, + module, + recursive, + callback + ); + }); + } + ); + } + + _handleModuleBuildAndDependencies(originModule, module, recursive, callback) { + // Check for cycles when build is trigger inside another build + let creatingModuleDuringBuildSet = undefined; + if (!recursive && this.buildQueue.isProcessing(originModule)) { + // Track build dependency + creatingModuleDuringBuildSet = + this.creatingModuleDuringBuild.get(originModule); + if (creatingModuleDuringBuildSet === undefined) { + creatingModuleDuringBuildSet = new Set(); + this.creatingModuleDuringBuild.set( + originModule, + creatingModuleDuringBuildSet + ); + } + creatingModuleDuringBuildSet.add(module); + + // When building is blocked by another module + // search for a cycle, cancel the cycle by throwing + // an error (otherwise this would deadlock) + const blockReasons = this.creatingModuleDuringBuild.get(module); + if (blockReasons !== undefined) { + const set = new Set(blockReasons); + for (const item of set) { + const blockReasons = this.creatingModuleDuringBuild.get(item); + if (blockReasons !== undefined) { + for (const m of blockReasons) { + if (m === module) { + return callback(new BuildCycleError(module)); + } + set.add(m); + } + } + } + } + } + + this.buildModule(module, err => { + if (creatingModuleDuringBuildSet !== undefined) { + creatingModuleDuringBuildSet.delete(module); + } + if (err) { + if (!err.module) { + err.module = module; } + this.errors.push(err); + + return callback(err); + } + + if (!recursive) { + this.processModuleDependenciesNonRecursive(module); + callback(null, module); + return; + } + // This avoids deadlocks for circular dependencies + if (this.processDependenciesQueue.isProcessing(module)) { return callback(); + } + + this.processModuleDependencies(module, err => { + if (err) { + return callback(err); + } + callback(null, module); }); }); } /** - * @param {Compilation} compilation the compilation - * @param {string} compilerName the compiler's name - * @param {number} compilerIndex the compiler's index - * @param {OutputOptions=} outputOptions the output options - * @param {WebpackPluginInstance[]=} plugins the plugins to apply - * @returns {Compiler} a child compiler + * @param {FactorizeModuleOptions} options options object + * @param {ModuleOrFactoryResultCallback} callback callback + * @returns {void} */ - createChildCompiler( - compilation, - compilerName, - compilerIndex, - outputOptions, - plugins + _factorizeModule( + { + currentProfile, + factory, + dependencies, + originModule, + factoryResult, + contextInfo, + context + }, + callback ) { - const childCompiler = new Compiler(this.context, { - ...this.options, - output: { - ...this.options.output, - ...outputOptions - } - }); - childCompiler.name = compilerName; - childCompiler.outputPath = this.outputPath; - childCompiler.inputFileSystem = this.inputFileSystem; - childCompiler.outputFileSystem = null; - childCompiler.resolverFactory = this.resolverFactory; - childCompiler.modifiedFiles = this.modifiedFiles; - childCompiler.removedFiles = this.removedFiles; - childCompiler.fileTimestamps = this.fileTimestamps; - childCompiler.contextTimestamps = this.contextTimestamps; - childCompiler.fsStartTime = this.fsStartTime; - childCompiler.cache = this.cache; - childCompiler.compilerPath = `${this.compilerPath}${compilerName}|${compilerIndex}|`; - childCompiler._backCompat = this._backCompat; + if (currentProfile !== undefined) { + currentProfile.markFactoryStart(); + } + factory.create( + { + contextInfo: { + issuer: originModule ? originModule.nameForCondition() : "", + issuerLayer: originModule ? originModule.layer : null, + compiler: this.compiler.name, + ...contextInfo + }, + resolveOptions: originModule ? originModule.resolveOptions : undefined, + context: context + ? context + : originModule + ? originModule.context + : this.compiler.context, + dependencies: dependencies + }, + (err, result) => { + if (result) { + // TODO webpack 6: remove + // For backward-compat + if (result.module === undefined && result instanceof Module) { + result = { + module: result + }; + } + if (!factoryResult) { + const { + fileDependencies, + contextDependencies, + missingDependencies + } = result; + if (fileDependencies) { + this.fileDependencies.addAll(fileDependencies); + } + if (contextDependencies) { + this.contextDependencies.addAll(contextDependencies); + } + if (missingDependencies) { + this.missingDependencies.addAll(missingDependencies); + } + } + } + if (err) { + const notFoundError = new ModuleNotFoundError( + originModule, + err, + dependencies.map(d => d.loc).filter(Boolean)[0] + ); + return callback(notFoundError, factoryResult ? result : undefined); + } + if (!result) { + return callback(); + } - const relativeCompilerName = makePathsRelative( - this.context, - compilerName, - this.root + if (currentProfile !== undefined) { + currentProfile.markFactoryEnd(); + } + + callback(null, factoryResult ? result : result.module); + } ); - if (!this.records[relativeCompilerName]) { - this.records[relativeCompilerName] = []; + } + + /** + * @param {string} context context string path + * @param {Dependency} dependency dependency used to create Module chain + * @param {ModuleCallback} callback callback for when module chain is complete + * @returns {void} will throw if dependency instance is not a valid Dependency + */ + addModuleChain(context, dependency, callback) { + return this.addModuleTree({ context, dependency }, callback); + } + + /** + * @param {Object} options options + * @param {string} options.context context string path + * @param {Dependency} options.dependency dependency used to create Module chain + * @param {Partial=} options.contextInfo additional context info for the root module + * @param {ModuleCallback} callback callback for when module chain is complete + * @returns {void} will throw if dependency instance is not a valid Dependency + */ + addModuleTree({ context, dependency, contextInfo }, callback) { + if ( + typeof dependency !== "object" || + dependency === null || + !dependency.constructor + ) { + return callback( + new WebpackError("Parameter 'dependency' must be a Dependency") + ); } - if (this.records[relativeCompilerName][compilerIndex]) { - childCompiler.records = this.records[relativeCompilerName][compilerIndex]; - } else { - this.records[relativeCompilerName].push((childCompiler.records = {})); + const Dep = /** @type {DepConstructor} */ (dependency.constructor); + const moduleFactory = this.dependencyFactories.get(Dep); + if (!moduleFactory) { + return callback( + new WebpackError( + `No dependency factory available for this dependency type: ${dependency.constructor.name}` + ) + ); } - childCompiler.parentCompilation = compilation; - childCompiler.root = this.root; - if (Array.isArray(plugins)) { - for (const plugin of plugins) { - plugin.apply(childCompiler); - } - } - for (const name in this.hooks) { - if ( - ![ - "make", - "compile", - "emit", - "afterEmit", - "invalid", - "done", - "thisCompilation" - ].includes(name) - ) { - if (childCompiler.hooks[name]) { - childCompiler.hooks[name].taps = this.hooks[name].taps.slice(); + this.handleModuleCreation( + { + factory: moduleFactory, + dependencies: [dependency], + originModule: null, + contextInfo, + context + }, + (err, result) => { + if (err && this.bail) { + callback(err); + this.buildQueue.stop(); + this.rebuildQueue.stop(); + this.processDependenciesQueue.stop(); + this.factorizeQueue.stop(); + } else if (!err && result) { + callback(null, result); + } else { + callback(); } } - } - - compilation.hooks.childCompiler.call( - childCompiler, - compilerName, - compilerIndex ); - - return childCompiler; } - isChild() { - return !!this.parentCompilation; - } + /** + * @param {string} context context path for entry + * @param {Dependency} entry entry dependency that should be followed + * @param {string | EntryOptions} optionsOrName options or deprecated name of entry + * @param {ModuleCallback} callback callback function + * @returns {void} returns + */ + addEntry(context, entry, optionsOrName, callback) { + // TODO webpack 6 remove + const options = + typeof optionsOrName === "object" + ? optionsOrName + : { name: optionsOrName }; - createCompilation(params) { - this._cleanupLastCompilation(); - return (this._lastCompilation = new Compilation(this, params)); + this._addEntryItem(context, entry, "dependencies", options, callback); } /** - * @param {CompilationParams} params the compilation parameters - * @returns {Compilation} the created compilation + * @param {string} context context path for entry + * @param {Dependency} dependency dependency that should be followed + * @param {EntryOptions} options options + * @param {ModuleCallback} callback callback function + * @returns {void} returns */ - newCompilation(params) { - const compilation = this.createCompilation(params); - compilation.name = this.name; - compilation.records = this.records; - this.hooks.thisCompilation.call(compilation, params); - this.hooks.compilation.call(compilation, params); - return compilation; + addInclude(context, dependency, options, callback) { + this._addEntryItem( + context, + dependency, + "includeDependencies", + options, + callback + ); } - createNormalModuleFactory() { - this._cleanupLastNormalModuleFactory(); - const normalModuleFactory = new NormalModuleFactory({ - context: this.options.context, - fs: this.inputFileSystem, - resolverFactory: this.resolverFactory, - options: this.options.module, - associatedObjectForCache: this.root, - layers: this.options.experiments.layers - }); - this._lastNormalModuleFactory = normalModuleFactory; - this.hooks.normalModuleFactory.call(normalModuleFactory); - return normalModuleFactory; - } + /** + * @param {string} context context path for entry + * @param {Dependency} entry entry dependency that should be followed + * @param {"dependencies" | "includeDependencies"} target type of entry + * @param {EntryOptions} options options + * @param {ModuleCallback} callback callback function + * @returns {void} returns + */ + _addEntryItem(context, entry, target, options, callback) { + const { name } = options; + let entryData = + name !== undefined ? this.entries.get(name) : this.globalEntry; + if (entryData === undefined) { + entryData = { + dependencies: [], + includeDependencies: [], + options: { + name: undefined, + ...options + } + }; + entryData[target].push(entry); + this.entries.set(name, entryData); + } else { + entryData[target].push(entry); + for (const key of Object.keys(options)) { + if (options[key] === undefined) continue; + if (entryData.options[key] === options[key]) continue; + if ( + Array.isArray(entryData.options[key]) && + Array.isArray(options[key]) && + arrayEquals(entryData.options[key], options[key]) + ) { + continue; + } + if (entryData.options[key] === undefined) { + entryData.options[key] = options[key]; + } else { + return callback( + new WebpackError( + `Conflicting entry option ${key} = ${entryData.options[key]} vs ${options[key]}` + ) + ); + } + } + } - createContextModuleFactory() { - const contextModuleFactory = new ContextModuleFactory(this.resolverFactory); - this.hooks.contextModuleFactory.call(contextModuleFactory); - return contextModuleFactory; - } + this.hooks.addEntry.call(entry, options); - newCompilationParams() { - const params = { - normalModuleFactory: this.createNormalModuleFactory(), - contextModuleFactory: this.createContextModuleFactory() - }; - return params; + this.addModuleTree( + { + context, + dependency: entry, + contextInfo: entryData.options.layer + ? { issuerLayer: entryData.options.layer } + : undefined + }, + (err, module) => { + if (err) { + this.hooks.failedEntry.call(entry, options, err); + return callback(err); + } + this.hooks.succeedEntry.call(entry, options, module); + return callback(null, module); + } + ); } /** - * @param {Callback} callback signals when the compilation finishes + * @param {Module} module module to be rebuilt + * @param {ModuleCallback} callback callback when module finishes rebuilding * @returns {void} */ - compile(callback) { - const params = this.newCompilationParams(); - this.hooks.beforeCompile.callAsync(params, err => { - if (err) return callback(err); - - this.hooks.compile.call(params); - - const compilation = this.newCompilation(params); + rebuildModule(module, callback) { + this.rebuildQueue.add(module, callback); + } - const logger = compilation.getLogger("webpack.Compiler"); + /** + * @param {Module} module module to be rebuilt + * @param {ModuleCallback} callback callback when module finishes rebuilding + * @returns {void} + */ + _rebuildModule(module, callback) { + this.hooks.rebuildModule.call(module); + const oldDependencies = module.dependencies.slice(); + const oldBlocks = module.blocks.slice(); + module.invalidateBuild(); + this.buildQueue.invalidate(module); + this.buildModule(module, err => { + if (err) { + return this.hooks.finishRebuildingModule.callAsync(module, err2 => { + if (err2) { + callback( + makeWebpackError(err2, "Compilation.hooks.finishRebuildingModule") + ); + return; + } + callback(err); + }); + } - logger.time("make hook"); - this.hooks.make.callAsync(compilation, err => { - logger.timeEnd("make hook"); + this.processDependenciesQueue.invalidate(module); + this.moduleGraph.unfreeze(); + this.processModuleDependencies(module, err => { if (err) return callback(err); - - logger.time("finish make hook"); - this.hooks.finishMake.callAsync(compilation, err => { - logger.timeEnd("finish make hook"); - if (err) return callback(err); - - process.nextTick(() => { - logger.time("finish compilation"); - compilation.finish(err => { - logger.timeEnd("finish compilation"); - if (err) return callback(err); - - logger.time("seal compilation"); - compilation.seal(err => { - logger.timeEnd("seal compilation"); - if (err) return callback(err); - - logger.time("afterCompile hook"); - this.hooks.afterCompile.callAsync(compilation, err => { - logger.timeEnd("afterCompile hook"); - if (err) return callback(err); - - return callback(null, compilation); - }); - }); - }); - }); + this.removeReasonsOfDependencyBlock(module, { + dependencies: oldDependencies, + blocks: oldBlocks + }); + this.hooks.finishRebuildingModule.callAsync(module, err2 => { + if (err2) { + callback( + makeWebpackError(err2, "Compilation.hooks.finishRebuildingModule") + ); + return; + } + callback(null, module); }); }); }); } - /** - * @param {Callback} callback signals when the compiler closes - * @returns {void} - */ - close(callback) { - if (this.watching) { - // When there is still an active watching, close this first - this.watching.close(err => { - this.close(callback); - }); - return; + _computeAffectedModules(modules) { + const moduleMemCacheCache = this.compiler.moduleMemCaches; + if (!moduleMemCacheCache) return; + if (!this.moduleMemCaches) { + this.moduleMemCaches = new Map(); + this.moduleGraph.setModuleMemCaches(this.moduleMemCaches); } - this.hooks.shutdown.callAsync(err => { - if (err) return callback(err); - // Get rid of reference to last compilation to avoid leaking memory - // We can't run this._cleanupLastCompilation() as the Stats to this compilation - // might be still in use. We try to get rid of the reference to the cache instead. - this._lastCompilation = undefined; - this._lastNormalModuleFactory = undefined; - this.cache.shutdown(callback); - }); - } -} - -module.exports = Compiler; - - -/***/ }), - -/***/ 14067: -/***/ (function(module) { - -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ - - - -/** @typedef {import("./Module")} Module */ - -const MODULE_REFERENCE_REGEXP = - /^__WEBPACK_MODULE_REFERENCE__(\d+)_([\da-f]+|ns)(_call)?(_directImport)?(?:_asiSafe(\d))?__$/; - -const DEFAULT_EXPORT = "__WEBPACK_DEFAULT_EXPORT__"; -const NAMESPACE_OBJECT_EXPORT = "__WEBPACK_NAMESPACE_OBJECT__"; - -/** - * @typedef {Object} ExternalModuleInfo - * @property {number} index - * @property {Module} module - */ - -/** - * @typedef {Object} ConcatenatedModuleInfo - * @property {number} index - * @property {Module} module - * @property {Map} exportMap mapping from export name to symbol - * @property {Map} rawExportMap mapping from export name to symbol - * @property {string=} namespaceExportSymbol - */ + const { moduleGraph, moduleMemCaches } = this; + const affectedModules = new Set(); + const infectedModules = new Set(); + let statNew = 0; + let statChanged = 0; + let statUnchanged = 0; + let statReferencesChanged = 0; + let statWithoutBuild = 0; -/** @typedef {ConcatenatedModuleInfo | ExternalModuleInfo} ModuleInfo */ + const computeReferences = module => { + /** @type {WeakMap} */ + let references = undefined; + for (const connection of moduleGraph.getOutgoingConnections(module)) { + const d = connection.dependency; + const m = connection.module; + if (!d || !m || unsafeCacheDependencies.has(d)) continue; + if (references === undefined) references = new WeakMap(); + references.set(d, m); + } + return references; + }; -/** - * @typedef {Object} ModuleReferenceOptions - * @property {string[]} ids the properties/exports of the module - * @property {boolean} call true, when this referenced export is called - * @property {boolean} directImport true, when this referenced export is directly imported (not via property access) - * @property {boolean | undefined} asiSafe if the position is ASI safe or unknown - */ + /** + * @param {Module} module the module + * @param {WeakMap} references references + * @returns {boolean} true, when the references differ + */ + const compareReferences = (module, references) => { + if (references === undefined) return true; + for (const connection of moduleGraph.getOutgoingConnections(module)) { + const d = connection.dependency; + if (!d) continue; + const entry = references.get(d); + if (entry === undefined) continue; + if (entry !== connection.module) return false; + } + return true; + }; -class ConcatenationScope { - /** - * @param {ModuleInfo[] | Map} modulesMap all module info by module - * @param {ConcatenatedModuleInfo} currentModule the current module info - */ - constructor(modulesMap, currentModule) { - this._currentModule = currentModule; - if (Array.isArray(modulesMap)) { - const map = new Map(); - for (const info of modulesMap) { - map.set(info.module, info); + const modulesWithoutCache = new Set(modules); + for (const [module, cachedMemCache] of moduleMemCacheCache) { + if (modulesWithoutCache.has(module)) { + const buildInfo = module.buildInfo; + if (buildInfo) { + if (cachedMemCache.buildInfo !== buildInfo) { + // use a new one + const memCache = new WeakTupleMap(); + moduleMemCaches.set(module, memCache); + affectedModules.add(module); + cachedMemCache.buildInfo = buildInfo; + cachedMemCache.references = computeReferences(module); + cachedMemCache.memCache = memCache; + statChanged++; + } else if (!compareReferences(module, cachedMemCache.references)) { + // use a new one + const memCache = new WeakTupleMap(); + moduleMemCaches.set(module, memCache); + affectedModules.add(module); + cachedMemCache.references = computeReferences(module); + cachedMemCache.memCache = memCache; + statReferencesChanged++; + } else { + // keep the old mem cache + moduleMemCaches.set(module, cachedMemCache.memCache); + statUnchanged++; + } + } else { + infectedModules.add(module); + moduleMemCacheCache.delete(module); + statWithoutBuild++; + } + modulesWithoutCache.delete(module); + } else { + moduleMemCacheCache.delete(module); } - modulesMap = map; } - this._modulesMap = modulesMap; - } - - /** - * @param {Module} module the referenced module - * @returns {boolean} true, when it's in the scope - */ - isModuleInScope(module) { - return this._modulesMap.has(module); - } - /** - * - * @param {string} exportName name of the export - * @param {string} symbol identifier of the export in source code - */ - registerExport(exportName, symbol) { - if (!this._currentModule.exportMap) { - this._currentModule.exportMap = new Map(); - } - if (!this._currentModule.exportMap.has(exportName)) { - this._currentModule.exportMap.set(exportName, symbol); + for (const module of modulesWithoutCache) { + const buildInfo = module.buildInfo; + if (buildInfo) { + // create a new entry + const memCache = new WeakTupleMap(); + moduleMemCacheCache.set(module, { + buildInfo, + references: computeReferences(module), + memCache + }); + moduleMemCaches.set(module, memCache); + affectedModules.add(module); + statNew++; + } else { + infectedModules.add(module); + statWithoutBuild++; + } } - } - /** - * - * @param {string} exportName name of the export - * @param {string} expression expression to be used - */ - registerRawExport(exportName, expression) { - if (!this._currentModule.rawExportMap) { - this._currentModule.rawExportMap = new Map(); + const reduceAffectType = connections => { + let affected = false; + for (const { dependency } of connections) { + if (!dependency) continue; + const type = dependency.couldAffectReferencingModule(); + if (type === Dependency.TRANSITIVE) return Dependency.TRANSITIVE; + if (type === false) continue; + affected = true; + } + return affected; + }; + const directOnlyInfectedModules = new Set(); + for (const module of infectedModules) { + for (const [ + referencingModule, + connections + ] of moduleGraph.getIncomingConnectionsByOriginModule(module)) { + if (!referencingModule) continue; + if (infectedModules.has(referencingModule)) continue; + const type = reduceAffectType(connections); + if (!type) continue; + if (type === true) { + directOnlyInfectedModules.add(referencingModule); + } else { + infectedModules.add(referencingModule); + } + } } - if (!this._currentModule.rawExportMap.has(exportName)) { - this._currentModule.rawExportMap.set(exportName, expression); + for (const module of directOnlyInfectedModules) infectedModules.add(module); + const directOnlyAffectModules = new Set(); + for (const module of affectedModules) { + for (const [ + referencingModule, + connections + ] of moduleGraph.getIncomingConnectionsByOriginModule(module)) { + if (!referencingModule) continue; + if (infectedModules.has(referencingModule)) continue; + if (affectedModules.has(referencingModule)) continue; + const type = reduceAffectType(connections); + if (!type) continue; + if (type === true) { + directOnlyAffectModules.add(referencingModule); + } else { + affectedModules.add(referencingModule); + } + const memCache = new WeakTupleMap(); + const cache = moduleMemCacheCache.get(referencingModule); + cache.memCache = memCache; + moduleMemCaches.set(referencingModule, memCache); + } } + for (const module of directOnlyAffectModules) affectedModules.add(module); + this.logger.log( + `${Math.round( + (100 * (affectedModules.size + infectedModules.size)) / + this.modules.size + )}% (${affectedModules.size} affected + ${ + infectedModules.size + } infected of ${ + this.modules.size + }) modules flagged as affected (${statNew} new modules, ${statChanged} changed, ${statReferencesChanged} references changed, ${statUnchanged} unchanged, ${statWithoutBuild} were not built)` + ); } - /** - * @param {string} symbol identifier of the export in source code - */ - registerNamespaceExport(symbol) { - this._currentModule.namespaceExportSymbol = symbol; - } - - /** - * - * @param {Module} module the referenced module - * @param {Partial} options options - * @returns {string} the reference as identifier - */ - createModuleReference( - module, - { ids = undefined, call = false, directImport = false, asiSafe = false } - ) { - const info = this._modulesMap.get(module); - const callFlag = call ? "_call" : ""; - const directImportFlag = directImport ? "_directImport" : ""; - const asiSafeFlag = asiSafe - ? "_asiSafe1" - : asiSafe === false - ? "_asiSafe0" - : ""; - const exportData = ids - ? Buffer.from(JSON.stringify(ids), "utf-8").toString("hex") - : "ns"; - // a "._" is appended to allow "delete ...", which would cause a SyntaxError in strict mode - return `__WEBPACK_MODULE_REFERENCE__${info.index}_${exportData}${callFlag}${directImportFlag}${asiSafeFlag}__._`; - } - - /** - * @param {string} name the identifier - * @returns {boolean} true, when it's an module reference - */ - static isModuleReference(name) { - return MODULE_REFERENCE_REGEXP.test(name); - } - - /** - * @param {string} name the identifier - * @returns {ModuleReferenceOptions & { index: number }} parsed options and index - */ - static matchModuleReference(name) { - const match = MODULE_REFERENCE_REGEXP.exec(name); - if (!match) return null; - const index = +match[1]; - const asiSafe = match[5]; - return { - index, - ids: - match[2] === "ns" - ? [] - : JSON.parse(Buffer.from(match[2], "hex").toString("utf-8")), - call: !!match[3], - directImport: !!match[4], - asiSafe: asiSafe ? asiSafe === "1" : undefined + _computeAffectedModulesWithChunkGraph() { + const { moduleMemCaches } = this; + if (!moduleMemCaches) return; + const moduleMemCaches2 = (this.moduleMemCaches2 = new Map()); + const { moduleGraph, chunkGraph } = this; + const key = "memCache2"; + let statUnchanged = 0; + let statChanged = 0; + let statNew = 0; + /** + * @param {Module} module module + * @returns {{ id: string | number, modules?: Map, blocks?: (string | number)[] }} references + */ + const computeReferences = module => { + const id = chunkGraph.getModuleId(module); + /** @type {Map} */ + let modules = undefined; + /** @type {(string | number)[] | undefined} */ + let blocks = undefined; + const outgoing = moduleGraph.getOutgoingConnectionsByModule(module); + if (outgoing !== undefined) { + for (const m of outgoing.keys()) { + if (!m) continue; + if (modules === undefined) modules = new Map(); + modules.set(m, chunkGraph.getModuleId(m)); + } + } + if (module.blocks.length > 0) { + blocks = []; + const queue = Array.from(module.blocks); + for (const block of queue) { + const chunkGroup = chunkGraph.getBlockChunkGroup(block); + if (chunkGroup) { + for (const chunk of chunkGroup.chunks) { + blocks.push(chunk.id); + } + } else { + blocks.push(null); + } + queue.push.apply(queue, block.blocks); + } + } + return { id, modules, blocks }; + }; + /** + * @param {Module} module module + * @param {Object} references references + * @param {string | number} references.id id + * @param {Map=} references.modules modules + * @param {(string | number)[]=} references.blocks blocks + * @returns {boolean} ok? + */ + const compareReferences = (module, { id, modules, blocks }) => { + if (id !== chunkGraph.getModuleId(module)) return false; + if (modules !== undefined) { + for (const [module, id] of modules) { + if (chunkGraph.getModuleId(module) !== id) return false; + } + } + if (blocks !== undefined) { + const queue = Array.from(module.blocks); + let i = 0; + for (const block of queue) { + const chunkGroup = chunkGraph.getBlockChunkGroup(block); + if (chunkGroup) { + for (const chunk of chunkGroup.chunks) { + if (i >= blocks.length || blocks[i++] !== chunk.id) return false; + } + } else { + if (i >= blocks.length || blocks[i++] !== null) return false; + } + queue.push.apply(queue, block.blocks); + } + if (i !== blocks.length) return false; + } + return true; }; - } -} - -ConcatenationScope.DEFAULT_EXPORT = DEFAULT_EXPORT; -ConcatenationScope.NAMESPACE_OBJECT_EXPORT = NAMESPACE_OBJECT_EXPORT; - -module.exports = ConcatenationScope; - - -/***/ }), - -/***/ 51684: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Maksim Nazarjev @acupofspirt -*/ - - - -const WebpackError = __webpack_require__(68422); -module.exports = class ConcurrentCompilationError extends WebpackError { - constructor() { - super(); + for (const [module, memCache] of moduleMemCaches) { + /** @type {{ references: { id: string | number, modules?: Map, blocks?: (string | number)[]}, memCache: WeakTupleMap }} */ + const cache = memCache.get(key); + if (cache === undefined) { + const memCache2 = new WeakTupleMap(); + memCache.set(key, { + references: computeReferences(module), + memCache: memCache2 + }); + moduleMemCaches2.set(module, memCache2); + statNew++; + } else if (!compareReferences(module, cache.references)) { + const memCache = new WeakTupleMap(); + cache.references = computeReferences(module); + cache.memCache = memCache; + moduleMemCaches2.set(module, memCache); + statChanged++; + } else { + moduleMemCaches2.set(module, cache.memCache); + statUnchanged++; + } + } - this.name = "ConcurrentCompilationError"; - this.message = - "You ran Webpack twice. Each instance only supports a single concurrent compilation at a time."; + this.logger.log( + `${Math.round( + (100 * statChanged) / (statNew + statChanged + statUnchanged) + )}% modules flagged as affected by chunk graph (${statNew} new modules, ${statChanged} changed, ${statUnchanged} unchanged)` + ); } -}; + finish(callback) { + this.factorizeQueue.clear(); + if (this.profile) { + this.logger.time("finish module profiles"); + const ParallelismFactorCalculator = __webpack_require__(67491); + const p = new ParallelismFactorCalculator(); + const moduleGraph = this.moduleGraph; + const modulesWithProfiles = new Map(); + for (const module of this.modules) { + const profile = moduleGraph.getProfile(module); + if (!profile) continue; + modulesWithProfiles.set(module, profile); + p.range( + profile.buildingStartTime, + profile.buildingEndTime, + f => (profile.buildingParallelismFactor = f) + ); + p.range( + profile.factoryStartTime, + profile.factoryEndTime, + f => (profile.factoryParallelismFactor = f) + ); + p.range( + profile.integrationStartTime, + profile.integrationEndTime, + f => (profile.integrationParallelismFactor = f) + ); + p.range( + profile.storingStartTime, + profile.storingEndTime, + f => (profile.storingParallelismFactor = f) + ); + p.range( + profile.restoringStartTime, + profile.restoringEndTime, + f => (profile.restoringParallelismFactor = f) + ); + if (profile.additionalFactoryTimes) { + for (const { start, end } of profile.additionalFactoryTimes) { + const influence = (end - start) / profile.additionalFactories; + p.range( + start, + end, + f => + (profile.additionalFactoriesParallelismFactor += f * influence) + ); + } + } + } + p.calculate(); -/***/ }), - -/***/ 90921: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ - - - -const { ConcatSource, PrefixSource } = __webpack_require__(96192); -const InitFragment = __webpack_require__(51739); -const Template = __webpack_require__(92066); -const { mergeRuntime } = __webpack_require__(19655); - -/** @typedef {import("webpack-sources").Source} Source */ -/** @typedef {import("./Generator").GenerateContext} GenerateContext */ -/** @typedef {import("./util/runtime").RuntimeSpec} RuntimeSpec */ + const logger = this.getLogger("webpack.Compilation.ModuleProfile"); + const logByValue = (value, msg) => { + if (value > 1000) { + logger.error(msg); + } else if (value > 500) { + logger.warn(msg); + } else if (value > 200) { + logger.info(msg); + } else if (value > 30) { + logger.log(msg); + } else { + logger.debug(msg); + } + }; + const logNormalSummary = (category, getDuration, getParallelism) => { + let sum = 0; + let max = 0; + for (const [module, profile] of modulesWithProfiles) { + const p = getParallelism(profile); + const d = getDuration(profile); + if (d === 0 || p === 0) continue; + const t = d / p; + sum += t; + if (t <= 10) continue; + logByValue( + t, + ` | ${Math.round(t)} ms${ + p >= 1.1 ? ` (parallelism ${Math.round(p * 10) / 10})` : "" + } ${category} > ${module.readableIdentifier(this.requestShortener)}` + ); + max = Math.max(max, t); + } + if (sum <= 10) return; + logByValue( + Math.max(sum / 10, max), + `${Math.round(sum)} ms ${category}` + ); + }; + const logByLoadersSummary = (category, getDuration, getParallelism) => { + const map = new Map(); + for (const [module, profile] of modulesWithProfiles) { + const list = provide( + map, + module.type + "!" + module.identifier().replace(/(!|^)[^!]*$/, ""), + () => [] + ); + list.push({ module, profile }); + } -const wrapInCondition = (condition, source) => { - if (typeof source === "string") { - return Template.asString([ - `if (${condition}) {`, - Template.indent(source), - "}", - "" - ]); - } else { - return new ConcatSource( - `if (${condition}) {\n`, - new PrefixSource("\t", source), - "}\n" - ); - } -}; + let sum = 0; + let max = 0; + for (const [key, modules] of map) { + let innerSum = 0; + let innerMax = 0; + for (const { module, profile } of modules) { + const p = getParallelism(profile); + const d = getDuration(profile); + if (d === 0 || p === 0) continue; + const t = d / p; + innerSum += t; + if (t <= 10) continue; + logByValue( + t, + ` | | ${Math.round(t)} ms${ + p >= 1.1 ? ` (parallelism ${Math.round(p * 10) / 10})` : "" + } ${category} > ${module.readableIdentifier( + this.requestShortener + )}` + ); + innerMax = Math.max(innerMax, t); + } + sum += innerSum; + if (innerSum <= 10) continue; + const idx = key.indexOf("!"); + const loaders = key.slice(idx + 1); + const moduleType = key.slice(0, idx); + const t = Math.max(innerSum / 10, innerMax); + logByValue( + t, + ` | ${Math.round(innerSum)} ms ${category} > ${ + loaders + ? `${ + modules.length + } x ${moduleType} with ${this.requestShortener.shorten( + loaders + )}` + : `${modules.length} x ${moduleType}` + }` + ); + max = Math.max(max, t); + } + if (sum <= 10) return; + logByValue( + Math.max(sum / 10, max), + `${Math.round(sum)} ms ${category}` + ); + }; + logNormalSummary( + "resolve to new modules", + p => p.factory, + p => p.factoryParallelismFactor + ); + logNormalSummary( + "resolve to existing modules", + p => p.additionalFactories, + p => p.additionalFactoriesParallelismFactor + ); + logNormalSummary( + "integrate modules", + p => p.restoring, + p => p.restoringParallelismFactor + ); + logByLoadersSummary( + "build modules", + p => p.building, + p => p.buildingParallelismFactor + ); + logNormalSummary( + "store modules", + p => p.storing, + p => p.storingParallelismFactor + ); + logNormalSummary( + "restore modules", + p => p.restoring, + p => p.restoringParallelismFactor + ); + this.logger.timeEnd("finish module profiles"); + } + this.logger.time("compute affected modules"); + this._computeAffectedModules(this.modules); + this.logger.timeEnd("compute affected modules"); + this.logger.time("finish modules"); + const { modules, moduleMemCaches } = this; + this.hooks.finishModules.callAsync(modules, err => { + this.logger.timeEnd("finish modules"); + if (err) return callback(err); -/** - * @typedef {GenerateContext} Context - */ -class ConditionalInitFragment extends InitFragment { - /** - * @param {string|Source} content the source code that will be included as initialization code - * @param {number} stage category of initialization code (contribute to order) - * @param {number} position position in the category (contribute to order) - * @param {string} key unique key to avoid emitting the same initialization code twice - * @param {RuntimeSpec | boolean} runtimeCondition in which runtime this fragment should be executed - * @param {string|Source=} endContent the source code that will be included at the end of the module - */ - constructor( - content, - stage, - position, - key, - runtimeCondition = true, - endContent - ) { - super(content, stage, position, key, endContent); - this.runtimeCondition = runtimeCondition; - } + // extract warnings and errors from modules + this.moduleGraph.freeze("dependency errors"); + // TODO keep a cacheToken (= {}) for each module in the graph + // create a new one per compilation and flag all updated files + // and parents with it + this.logger.time("report dependency errors and warnings"); + for (const module of modules) { + // TODO only run for modules with changed cacheToken + // global WeakMap> to keep modules without errors/warnings + const memCache = moduleMemCaches && moduleMemCaches.get(module); + if (memCache && memCache.get("noWarningsOrErrors")) continue; + let hasProblems = this.reportDependencyErrorsAndWarnings(module, [ + module + ]); + const errors = module.getErrors(); + if (errors !== undefined) { + for (const error of errors) { + if (!error.module) { + error.module = module; + } + this.errors.push(error); + hasProblems = true; + } + } + const warnings = module.getWarnings(); + if (warnings !== undefined) { + for (const warning of warnings) { + if (!warning.module) { + warning.module = module; + } + this.warnings.push(warning); + hasProblems = true; + } + } + if (!hasProblems && memCache) memCache.set("noWarningsOrErrors", true); + } + this.moduleGraph.unfreeze(); + this.logger.timeEnd("report dependency errors and warnings"); - /** - * @param {Context} context context - * @returns {string|Source} the source code that will be included as initialization code - */ - getContent(context) { - if (this.runtimeCondition === false || !this.content) return ""; - if (this.runtimeCondition === true) return this.content; - const expr = context.runtimeTemplate.runtimeConditionExpression({ - chunkGraph: context.chunkGraph, - runtimeRequirements: context.runtimeRequirements, - runtime: context.runtime, - runtimeCondition: this.runtimeCondition + callback(); }); - if (expr === "true") return this.content; - return wrapInCondition(expr, this.content); } - /** - * @param {Context} context context - * @returns {string|Source=} the source code that will be included at the end of the module - */ - getEndContent(context) { - if (this.runtimeCondition === false || !this.endContent) return ""; - if (this.runtimeCondition === true) return this.endContent; - const expr = context.runtimeTemplate.runtimeConditionExpression({ - chunkGraph: context.chunkGraph, - runtimeRequirements: context.runtimeRequirements, - runtime: context.runtime, - runtimeCondition: this.runtimeCondition - }); - if (expr === "true") return this.endContent; - return wrapInCondition(expr, this.endContent); + unseal() { + this.hooks.unseal.call(); + this.chunks.clear(); + this.chunkGroups.length = 0; + this.namedChunks.clear(); + this.namedChunkGroups.clear(); + this.entrypoints.clear(); + this.additionalChunkAssets.length = 0; + this.assets = {}; + this.assetsInfo.clear(); + this.moduleGraph.removeAllModuleAttributes(); + this.moduleGraph.unfreeze(); + this.moduleMemCaches2 = undefined; } - merge(other) { - if (this.runtimeCondition === true) return this; - if (other.runtimeCondition === true) return other; - if (this.runtimeCondition === false) return other; - if (other.runtimeCondition === false) return this; - const runtimeCondition = mergeRuntime( - this.runtimeCondition, - other.runtimeCondition - ); - return new ConditionalInitFragment( - this.content, - this.stage, - this.position, - this.key, - runtimeCondition, - this.endContent + /** + * @param {Callback} callback signals when the call finishes + * @returns {void} + */ + seal(callback) { + const finalCallback = err => { + this.factorizeQueue.clear(); + this.buildQueue.clear(); + this.rebuildQueue.clear(); + this.processDependenciesQueue.clear(); + this.addModuleQueue.clear(); + return callback(err); + }; + const chunkGraph = new ChunkGraph( + this.moduleGraph, + this.outputOptions.hashFunction ); - } -} - -module.exports = ConditionalInitFragment; + this.chunkGraph = chunkGraph; + if (this._backCompat) { + for (const module of this.modules) { + ChunkGraph.setChunkGraphForModule(module, chunkGraph); + } + } -/***/ }), + this.hooks.seal.call(); -/***/ 53042: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + this.logger.time("optimize dependencies"); + while (this.hooks.optimizeDependencies.call(this.modules)) { + /* empty */ + } + this.hooks.afterOptimizeDependencies.call(this.modules); + this.logger.timeEnd("optimize dependencies"); -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ + this.logger.time("create chunks"); + this.hooks.beforeChunks.call(); + this.moduleGraph.freeze("seal"); + /** @type {Map} */ + const chunkGraphInit = new Map(); + for (const [name, { dependencies, includeDependencies, options }] of this + .entries) { + const chunk = this.addChunk(name); + if (options.filename) { + chunk.filenameTemplate = options.filename; + } + const entrypoint = new Entrypoint(options); + if (!options.dependOn && !options.runtime) { + entrypoint.setRuntimeChunk(chunk); + } + entrypoint.setEntrypointChunk(chunk); + this.namedChunkGroups.set(name, entrypoint); + this.entrypoints.set(name, entrypoint); + this.chunkGroups.push(entrypoint); + connectChunkGroupAndChunk(entrypoint, chunk); + const entryModules = new Set(); + for (const dep of [...this.globalEntry.dependencies, ...dependencies]) { + entrypoint.addOrigin(null, { name }, /** @type {any} */ (dep).request); + const module = this.moduleGraph.getModule(dep); + if (module) { + chunkGraph.connectChunkAndEntryModule(chunk, module, entrypoint); + entryModules.add(module); + const modulesList = chunkGraphInit.get(entrypoint); + if (modulesList === undefined) { + chunkGraphInit.set(entrypoint, [module]); + } else { + modulesList.push(module); + } + } + } -const CachedConstDependency = __webpack_require__(64177); -const ConstDependency = __webpack_require__(60864); -const { evaluateToString } = __webpack_require__(28723); -const { parseResource } = __webpack_require__(96236); + this.assignDepths(entryModules); -/** @typedef {import("estree").Expression} ExpressionNode */ -/** @typedef {import("estree").Super} SuperNode */ -/** @typedef {import("./Compiler")} Compiler */ + const mapAndSort = deps => + deps + .map(dep => this.moduleGraph.getModule(dep)) + .filter(Boolean) + .sort(compareModulesByIdentifier); + const includedModules = [ + ...mapAndSort(this.globalEntry.includeDependencies), + ...mapAndSort(includeDependencies) + ]; -const collectDeclaration = (declarations, pattern) => { - const stack = [pattern]; - while (stack.length > 0) { - const node = stack.pop(); - switch (node.type) { - case "Identifier": - declarations.add(node.name); - break; - case "ArrayPattern": - for (const element of node.elements) { - if (element) { - stack.push(element); + let modulesList = chunkGraphInit.get(entrypoint); + if (modulesList === undefined) { + chunkGraphInit.set(entrypoint, (modulesList = [])); + } + for (const module of includedModules) { + this.assignDepth(module); + modulesList.push(module); + } + } + const runtimeChunks = new Set(); + outer: for (const [ + name, + { + options: { dependOn, runtime } + } + ] of this.entries) { + if (dependOn && runtime) { + const err = + new WebpackError(`Entrypoint '${name}' has 'dependOn' and 'runtime' specified. This is not valid. +Entrypoints that depend on other entrypoints do not have their own runtime. +They will use the runtime(s) from referenced entrypoints instead. +Remove the 'runtime' option from the entrypoint.`); + const entry = this.entrypoints.get(name); + err.chunk = entry.getEntrypointChunk(); + this.errors.push(err); + } + if (dependOn) { + const entry = this.entrypoints.get(name); + const referencedChunks = entry + .getEntrypointChunk() + .getAllReferencedChunks(); + const dependOnEntries = []; + for (const dep of dependOn) { + const dependency = this.entrypoints.get(dep); + if (!dependency) { + throw new Error( + `Entry ${name} depends on ${dep}, but this entry was not found` + ); } + if (referencedChunks.has(dependency.getEntrypointChunk())) { + const err = new WebpackError( + `Entrypoints '${name}' and '${dep}' use 'dependOn' to depend on each other in a circular way.` + ); + const entryChunk = entry.getEntrypointChunk(); + err.chunk = entryChunk; + this.errors.push(err); + entry.setRuntimeChunk(entryChunk); + continue outer; + } + dependOnEntries.push(dependency); } - break; - case "AssignmentPattern": - stack.push(node.left); - break; - case "ObjectPattern": - for (const property of node.properties) { - stack.push(property.value); - } - break; - case "RestElement": - stack.push(node.argument); - break; - } - } -}; - -const getHoistedDeclarations = (branch, includeFunctionDeclarations) => { - const declarations = new Set(); - const stack = [branch]; - while (stack.length > 0) { - const node = stack.pop(); - // Some node could be `null` or `undefined`. - if (!node) continue; - switch (node.type) { - // Walk through control statements to look for hoisted declarations. - // Some branches are skipped since they do not allow declarations. - case "BlockStatement": - for (const stmt of node.body) { - stack.push(stmt); + for (const dependency of dependOnEntries) { + connectChunkGroupParentAndChild(dependency, entry); } - break; - case "IfStatement": - stack.push(node.consequent); - stack.push(node.alternate); - break; - case "ForStatement": - stack.push(node.init); - stack.push(node.body); - break; - case "ForInStatement": - case "ForOfStatement": - stack.push(node.left); - stack.push(node.body); - break; - case "DoWhileStatement": - case "WhileStatement": - case "LabeledStatement": - stack.push(node.body); - break; - case "SwitchStatement": - for (const cs of node.cases) { - for (const consequent of cs.consequent) { - stack.push(consequent); - } - } - break; - case "TryStatement": - stack.push(node.block); - if (node.handler) { - stack.push(node.handler.body); - } - stack.push(node.finalizer); - break; - case "FunctionDeclaration": - if (includeFunctionDeclarations) { - collectDeclaration(declarations, node.id); - } - break; - case "VariableDeclaration": - if (node.kind === "var") { - for (const decl of node.declarations) { - collectDeclaration(declarations, decl.id); + } else if (runtime) { + const entry = this.entrypoints.get(name); + let chunk = this.namedChunks.get(runtime); + if (chunk) { + if (!runtimeChunks.has(chunk)) { + const err = + new WebpackError(`Entrypoint '${name}' has a 'runtime' option which points to another entrypoint named '${runtime}'. +It's not valid to use other entrypoints as runtime chunk. +Did you mean to use 'dependOn: ${JSON.stringify( + runtime + )}' instead to allow using entrypoint '${name}' within the runtime of entrypoint '${runtime}'? For this '${runtime}' must always be loaded when '${name}' is used. +Or do you want to use the entrypoints '${name}' and '${runtime}' independently on the same page with a shared runtime? In this case give them both the same value for the 'runtime' option. It must be a name not already used by an entrypoint.`); + const entryChunk = entry.getEntrypointChunk(); + err.chunk = entryChunk; + this.errors.push(err); + entry.setRuntimeChunk(entryChunk); + continue; } + } else { + chunk = this.addChunk(runtime); + chunk.preventIntegration = true; + runtimeChunks.add(chunk); } - break; + entry.unshiftChunk(chunk); + chunk.addGroup(entry); + entry.setRuntimeChunk(chunk); + } } - } - return Array.from(declarations); -}; + buildChunkGraph(this, chunkGraphInit); + this.hooks.afterChunks.call(this.chunks); + this.logger.timeEnd("create chunks"); -class ConstPlugin { - /** - * Apply the plugin - * @param {Compiler} compiler the compiler instance - * @returns {void} - */ - apply(compiler) { - const cachedParseResource = parseResource.bindCache(compiler.root); - compiler.hooks.compilation.tap( - "ConstPlugin", - (compilation, { normalModuleFactory }) => { - compilation.dependencyTemplates.set( - ConstDependency, - new ConstDependency.Template() - ); + this.logger.time("optimize"); + this.hooks.optimize.call(); - compilation.dependencyTemplates.set( - CachedConstDependency, - new CachedConstDependency.Template() - ); + while (this.hooks.optimizeModules.call(this.modules)) { + /* empty */ + } + this.hooks.afterOptimizeModules.call(this.modules); - const handler = parser => { - parser.hooks.statementIf.tap("ConstPlugin", statement => { - if (parser.scope.isAsmJs) return; - const param = parser.evaluateExpression(statement.test); - const bool = param.asBool(); - if (typeof bool === "boolean") { - if (!param.couldHaveSideEffects()) { - const dep = new ConstDependency(`${bool}`, param.range); - dep.loc = statement.loc; - parser.state.module.addPresentationalDependency(dep); - } else { - parser.walkExpression(statement.test); - } - const branchToRemove = bool - ? statement.alternate - : statement.consequent; - if (branchToRemove) { - // Before removing the dead branch, the hoisted declarations - // must be collected. - // - // Given the following code: - // - // if (true) f() else g() - // if (false) { - // function f() {} - // const g = function g() {} - // if (someTest) { - // let a = 1 - // var x, {y, z} = obj - // } - // } else { - // … - // } - // - // the generated code is: - // - // if (true) f() else {} - // if (false) { - // var f, x, y, z; (in loose mode) - // var x, y, z; (in strict mode) - // } else { - // … - // } - // - // NOTE: When code runs in strict mode, `var` declarations - // are hoisted but `function` declarations don't. - // - let declarations; - if (parser.scope.isStrict) { - // If the code runs in strict mode, variable declarations - // using `var` must be hoisted. - declarations = getHoistedDeclarations(branchToRemove, false); - } else { - // Otherwise, collect all hoisted declaration. - declarations = getHoistedDeclarations(branchToRemove, true); - } - let replacement; - if (declarations.length > 0) { - replacement = `{ var ${declarations.join(", ")}; }`; - } else { - replacement = "{}"; - } - const dep = new ConstDependency( - replacement, - branchToRemove.range - ); - dep.loc = branchToRemove.loc; - parser.state.module.addPresentationalDependency(dep); - } - return bool; - } - }); - parser.hooks.expressionConditionalOperator.tap( - "ConstPlugin", - expression => { - if (parser.scope.isAsmJs) return; - const param = parser.evaluateExpression(expression.test); - const bool = param.asBool(); - if (typeof bool === "boolean") { - if (!param.couldHaveSideEffects()) { - const dep = new ConstDependency(` ${bool}`, param.range); - dep.loc = expression.loc; - parser.state.module.addPresentationalDependency(dep); - } else { - parser.walkExpression(expression.test); - } - // Expressions do not hoist. - // It is safe to remove the dead branch. - // - // Given the following code: - // - // false ? someExpression() : otherExpression(); - // - // the generated code is: - // - // false ? 0 : otherExpression(); - // - const branchToRemove = bool - ? expression.alternate - : expression.consequent; - const dep = new ConstDependency("0", branchToRemove.range); - dep.loc = branchToRemove.loc; - parser.state.module.addPresentationalDependency(dep); - return bool; - } - } - ); - parser.hooks.expressionLogicalOperator.tap( - "ConstPlugin", - expression => { - if (parser.scope.isAsmJs) return; - if ( - expression.operator === "&&" || - expression.operator === "||" - ) { - const param = parser.evaluateExpression(expression.left); - const bool = param.asBool(); - if (typeof bool === "boolean") { - // Expressions do not hoist. - // It is safe to remove the dead branch. - // - // ------------------------------------------ - // - // Given the following code: - // - // falsyExpression() && someExpression(); - // - // the generated code is: - // - // falsyExpression() && false; - // - // ------------------------------------------ - // - // Given the following code: - // - // truthyExpression() && someExpression(); - // - // the generated code is: - // - // true && someExpression(); - // - // ------------------------------------------ - // - // Given the following code: - // - // truthyExpression() || someExpression(); - // - // the generated code is: - // - // truthyExpression() || false; - // - // ------------------------------------------ - // - // Given the following code: - // - // falsyExpression() || someExpression(); - // - // the generated code is: - // - // false && someExpression(); - // - const keepRight = - (expression.operator === "&&" && bool) || - (expression.operator === "||" && !bool); + while (this.hooks.optimizeChunks.call(this.chunks, this.chunkGroups)) { + /* empty */ + } + this.hooks.afterOptimizeChunks.call(this.chunks, this.chunkGroups); - if ( - !param.couldHaveSideEffects() && - (param.isBoolean() || keepRight) - ) { - // for case like - // - // return'development'===process.env.NODE_ENV&&'foo' - // - // we need a space before the bool to prevent result like - // - // returnfalse&&'foo' - // - const dep = new ConstDependency(` ${bool}`, param.range); - dep.loc = expression.loc; - parser.state.module.addPresentationalDependency(dep); - } else { - parser.walkExpression(expression.left); - } - if (!keepRight) { - const dep = new ConstDependency( - "0", - expression.right.range - ); - dep.loc = expression.loc; - parser.state.module.addPresentationalDependency(dep); - } - return keepRight; - } - } else if (expression.operator === "??") { - const param = parser.evaluateExpression(expression.left); - const keepRight = param && param.asNullish(); - if (typeof keepRight === "boolean") { - // ------------------------------------------ - // - // Given the following code: - // - // nonNullish ?? someExpression(); - // - // the generated code is: - // - // nonNullish ?? 0; - // - // ------------------------------------------ - // - // Given the following code: - // - // nullish ?? someExpression(); - // - // the generated code is: - // - // null ?? someExpression(); - // - if (!param.couldHaveSideEffects() && keepRight) { - // cspell:word returnnull - // for case like - // - // return('development'===process.env.NODE_ENV&&null)??'foo' - // - // we need a space before the bool to prevent result like - // - // returnnull??'foo' - // - const dep = new ConstDependency(" null", param.range); - dep.loc = expression.loc; - parser.state.module.addPresentationalDependency(dep); - } else { - const dep = new ConstDependency( - "0", - expression.right.range - ); - dep.loc = expression.loc; - parser.state.module.addPresentationalDependency(dep); - parser.walkExpression(expression.left); - } + this.hooks.optimizeTree.callAsync(this.chunks, this.modules, err => { + if (err) { + return finalCallback( + makeWebpackError(err, "Compilation.hooks.optimizeTree") + ); + } - return keepRight; - } - } - } - ); - parser.hooks.optionalChaining.tap("ConstPlugin", expr => { - /** @type {ExpressionNode[]} */ - const optionalExpressionsStack = []; - /** @type {ExpressionNode|SuperNode} */ - let next = expr.expression; + this.hooks.afterOptimizeTree.call(this.chunks, this.modules); - while ( - next.type === "MemberExpression" || - next.type === "CallExpression" - ) { - if (next.type === "MemberExpression") { - if (next.optional) { - // SuperNode can not be optional - optionalExpressionsStack.push( - /** @type {ExpressionNode} */ (next.object) - ); - } - next = next.object; - } else { - if (next.optional) { - // SuperNode can not be optional - optionalExpressionsStack.push( - /** @type {ExpressionNode} */ (next.callee) - ); - } - next = next.callee; - } - } + this.hooks.optimizeChunkModules.callAsync( + this.chunks, + this.modules, + err => { + if (err) { + return finalCallback( + makeWebpackError(err, "Compilation.hooks.optimizeChunkModules") + ); + } - while (optionalExpressionsStack.length) { - const expression = optionalExpressionsStack.pop(); - const evaluated = parser.evaluateExpression(expression); + this.hooks.afterOptimizeChunkModules.call(this.chunks, this.modules); - if (evaluated && evaluated.asNullish()) { - // ------------------------------------------ - // - // Given the following code: - // - // nullishMemberChain?.a.b(); - // - // the generated code is: - // - // undefined; - // - // ------------------------------------------ - // - const dep = new ConstDependency(" undefined", expr.range); - dep.loc = expr.loc; - parser.state.module.addPresentationalDependency(dep); - return true; - } - } - }); - parser.hooks.evaluateIdentifier - .for("__resourceQuery") - .tap("ConstPlugin", expr => { - if (parser.scope.isAsmJs) return; - if (!parser.state.module) return; - return evaluateToString( - cachedParseResource(parser.state.module.resource).query - )(expr); - }); - parser.hooks.expression - .for("__resourceQuery") - .tap("ConstPlugin", expr => { - if (parser.scope.isAsmJs) return; - if (!parser.state.module) return; - const dep = new CachedConstDependency( - JSON.stringify( - cachedParseResource(parser.state.module.resource).query - ), - expr.range, - "__resourceQuery" - ); - dep.loc = expr.loc; - parser.state.module.addPresentationalDependency(dep); - return true; - }); + const shouldRecord = this.hooks.shouldRecord.call() !== false; - parser.hooks.evaluateIdentifier - .for("__resourceFragment") - .tap("ConstPlugin", expr => { - if (parser.scope.isAsmJs) return; - if (!parser.state.module) return; - return evaluateToString( - cachedParseResource(parser.state.module.resource).fragment - )(expr); - }); - parser.hooks.expression - .for("__resourceFragment") - .tap("ConstPlugin", expr => { - if (parser.scope.isAsmJs) return; - if (!parser.state.module) return; - const dep = new CachedConstDependency( - JSON.stringify( - cachedParseResource(parser.state.module.resource).fragment - ), - expr.range, - "__resourceFragment" - ); - dep.loc = expr.loc; - parser.state.module.addPresentationalDependency(dep); - return true; - }); - }; + this.hooks.reviveModules.call(this.modules, this.records); + this.hooks.beforeModuleIds.call(this.modules); + this.hooks.moduleIds.call(this.modules); + this.hooks.optimizeModuleIds.call(this.modules); + this.hooks.afterOptimizeModuleIds.call(this.modules); - normalModuleFactory.hooks.parser - .for("javascript/auto") - .tap("ConstPlugin", handler); - normalModuleFactory.hooks.parser - .for("javascript/dynamic") - .tap("ConstPlugin", handler); - normalModuleFactory.hooks.parser - .for("javascript/esm") - .tap("ConstPlugin", handler); - } - ); - } -} + this.hooks.reviveChunks.call(this.chunks, this.records); + this.hooks.beforeChunkIds.call(this.chunks); + this.hooks.chunkIds.call(this.chunks); + this.hooks.optimizeChunkIds.call(this.chunks); + this.hooks.afterOptimizeChunkIds.call(this.chunks); -module.exports = ConstPlugin; + this.assignRuntimeIds(); + this.logger.time("compute affected modules with chunk graph"); + this._computeAffectedModulesWithChunkGraph(); + this.logger.timeEnd("compute affected modules with chunk graph"); -/***/ }), + this.sortItemsWithChunkIds(); -/***/ 30480: -/***/ (function(module) { + if (shouldRecord) { + this.hooks.recordModules.call(this.modules, this.records); + this.hooks.recordChunks.call(this.chunks, this.records); + } -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php -*/ + this.hooks.optimizeCodeGeneration.call(this.modules); + this.logger.timeEnd("optimize"); + this.logger.time("module hashing"); + this.hooks.beforeModuleHash.call(); + this.createModuleHashes(); + this.hooks.afterModuleHash.call(); + this.logger.timeEnd("module hashing"); + this.logger.time("code generation"); + this.hooks.beforeCodeGeneration.call(); + this.codeGeneration(err => { + if (err) { + return finalCallback(err); + } + this.hooks.afterCodeGeneration.call(); + this.logger.timeEnd("code generation"); -/** @typedef {import("./Compiler")} Compiler */ -/** @typedef {import("./ContextModuleFactory")} ContextModuleFactory */ - -class ContextExclusionPlugin { - /** - * @param {RegExp} negativeMatcher Matcher regular expression - */ - constructor(negativeMatcher) { - this.negativeMatcher = negativeMatcher; - } - - /** - * Apply the plugin - * @param {Compiler} compiler the compiler instance - * @returns {void} - */ - apply(compiler) { - compiler.hooks.contextModuleFactory.tap("ContextExclusionPlugin", cmf => { - cmf.hooks.contextModuleFiles.tap("ContextExclusionPlugin", files => { - return files.filter(filePath => !this.negativeMatcher.test(filePath)); - }); - }); - } -} - -module.exports = ContextExclusionPlugin; - - -/***/ }), - -/***/ 80207: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ + this.logger.time("runtime requirements"); + this.hooks.beforeRuntimeRequirements.call(); + this.processRuntimeRequirements(); + this.hooks.afterRuntimeRequirements.call(); + this.logger.timeEnd("runtime requirements"); + this.logger.time("hashing"); + this.hooks.beforeHash.call(); + const codeGenerationJobs = this.createHash(); + this.hooks.afterHash.call(); + this.logger.timeEnd("hashing"); + this._runCodeGenerationJobs(codeGenerationJobs, err => { + if (err) { + return finalCallback(err); + } -const { OriginalSource, RawSource } = __webpack_require__(96192); -const AsyncDependenciesBlock = __webpack_require__(11315); -const { makeWebpackError } = __webpack_require__(89935); -const Module = __webpack_require__(85887); -const RuntimeGlobals = __webpack_require__(49404); -const Template = __webpack_require__(92066); -const WebpackError = __webpack_require__(68422); -const { - compareLocations, - concatComparators, - compareSelect, - keepOriginalOrder, - compareModulesById -} = __webpack_require__(26296); -const { contextify, parseResource } = __webpack_require__(96236); -const makeSerializable = __webpack_require__(26522); + if (shouldRecord) { + this.logger.time("record hash"); + this.hooks.recordHash.call(this.records); + this.logger.timeEnd("record hash"); + } -/** @typedef {import("webpack-sources").Source} Source */ -/** @typedef {import("../declarations/WebpackOptions").WebpackOptionsNormalized} WebpackOptions */ -/** @typedef {import("./ChunkGraph")} ChunkGraph */ -/** @typedef {import("./ChunkGroup").RawChunkGroupOptions} RawChunkGroupOptions */ -/** @typedef {import("./Compilation")} Compilation */ -/** @typedef {import("./DependencyTemplates")} DependencyTemplates */ -/** @typedef {import("./Module").BuildMeta} BuildMeta */ -/** @typedef {import("./Module").CodeGenerationContext} CodeGenerationContext */ -/** @typedef {import("./Module").CodeGenerationResult} CodeGenerationResult */ -/** @typedef {import("./Module").LibIdentOptions} LibIdentOptions */ -/** @typedef {import("./Module").NeedBuildContext} NeedBuildContext */ -/** @typedef {import("./ModuleGraph")} ModuleGraph */ -/** @typedef {import("./RequestShortener")} RequestShortener */ -/** @typedef {import("./ResolverFactory").ResolverWithOptions} ResolverWithOptions */ -/** @typedef {import("./RuntimeTemplate")} RuntimeTemplate */ -/** @typedef {import("./dependencies/ContextElementDependency")} ContextElementDependency */ -/** @template T @typedef {import("./util/LazySet")} LazySet */ -/** @typedef {import("./util/fs").InputFileSystem} InputFileSystem */ + this.logger.time("module assets"); + this.clearAssets(); -/** @typedef {"sync" | "eager" | "weak" | "async-weak" | "lazy" | "lazy-once"} ContextMode Context mode */ + this.hooks.beforeModuleAssets.call(); + this.createModuleAssets(); + this.logger.timeEnd("module assets"); -/** - * @typedef {Object} ContextOptions - * @property {ContextMode} mode - * @property {boolean} recursive - * @property {RegExp} regExp - * @property {"strict"|boolean=} namespaceObject - * @property {string=} addon - * @property {string=} chunkName - * @property {RegExp=} include - * @property {RegExp=} exclude - * @property {RawChunkGroupOptions=} groupOptions - * @property {string=} typePrefix - * @property {string=} category - * @property {string[][]=} referencedExports exports referenced from modules (won't be mangled) - */ + const cont = () => { + this.logger.time("process assets"); + this.hooks.processAssets.callAsync(this.assets, err => { + if (err) { + return finalCallback( + makeWebpackError(err, "Compilation.hooks.processAssets") + ); + } + this.hooks.afterProcessAssets.call(this.assets); + this.logger.timeEnd("process assets"); + this.assets = this._backCompat + ? soonFrozenObjectDeprecation( + this.assets, + "Compilation.assets", + "DEP_WEBPACK_COMPILATION_ASSETS", + `BREAKING CHANGE: No more changes should happen to Compilation.assets after sealing the Compilation. + Do changes to assets earlier, e. g. in Compilation.hooks.processAssets. + Make sure to select an appropriate stage from Compilation.PROCESS_ASSETS_STAGE_*.` + ) + : Object.freeze(this.assets); -/** - * @typedef {Object} ContextModuleOptionsExtras - * @property {string} resource - * @property {string=} resourceQuery - * @property {string=} resourceFragment - * @property {TODO} resolveOptions - */ + this.summarizeDependencies(); + if (shouldRecord) { + this.hooks.record.call(this, this.records); + } -/** @typedef {ContextOptions & ContextModuleOptionsExtras} ContextModuleOptions */ + if (this.hooks.needAdditionalSeal.call()) { + this.unseal(); + return this.seal(callback); + } + return this.hooks.afterSeal.callAsync(err => { + if (err) { + return finalCallback( + makeWebpackError(err, "Compilation.hooks.afterSeal") + ); + } + this.fileSystemInfo.logStatistics(); + finalCallback(); + }); + }); + }; -/** - * @callback ResolveDependenciesCallback - * @param {Error=} err - * @param {ContextElementDependency[]=} dependencies - */ + this.logger.time("create chunk assets"); + if (this.hooks.shouldGenerateChunkAssets.call() !== false) { + this.hooks.beforeChunkAssets.call(); + this.createChunkAssets(err => { + this.logger.timeEnd("create chunk assets"); + if (err) { + return finalCallback(err); + } + cont(); + }); + } else { + this.logger.timeEnd("create chunk assets"); + cont(); + } + }); + }); + } + ); + }); + } -/** - * @callback ResolveDependencies - * @param {InputFileSystem} fs - * @param {ContextModuleOptions} options - * @param {ResolveDependenciesCallback} callback - */ + /** + * @param {Module} module module to report from + * @param {DependenciesBlock[]} blocks blocks to report from + * @returns {boolean} true, when it has warnings or errors + */ + reportDependencyErrorsAndWarnings(module, blocks) { + let hasProblems = false; + for (let indexBlock = 0; indexBlock < blocks.length; indexBlock++) { + const block = blocks[indexBlock]; + const dependencies = block.dependencies; -const SNAPSHOT_OPTIONS = { timestamp: true }; + for (let indexDep = 0; indexDep < dependencies.length; indexDep++) { + const d = dependencies[indexDep]; -const TYPES = new Set(["javascript"]); + const warnings = d.getWarnings(this.moduleGraph); + if (warnings) { + for (let indexWar = 0; indexWar < warnings.length; indexWar++) { + const w = warnings[indexWar]; -class ContextModule extends Module { - /** - * @param {ResolveDependencies} resolveDependencies function to get dependencies in this context - * @param {ContextModuleOptions} options options object - */ - constructor(resolveDependencies, options) { - const parsed = parseResource(options ? options.resource : ""); - const resource = parsed.path; - const resourceQuery = (options && options.resourceQuery) || parsed.query; - const resourceFragment = - (options && options.resourceFragment) || parsed.fragment; + const warning = new ModuleDependencyWarning(module, w, d.loc); + this.warnings.push(warning); + hasProblems = true; + } + } + const errors = d.getErrors(this.moduleGraph); + if (errors) { + for (let indexErr = 0; indexErr < errors.length; indexErr++) { + const e = errors[indexErr]; - super("javascript/dynamic", resource); + const error = new ModuleDependencyError(module, e, d.loc); + this.errors.push(error); + hasProblems = true; + } + } + } - // Info from Factory - this.resolveDependencies = resolveDependencies; - /** @type {ContextModuleOptions} */ - this.options = { - ...options, - resource, - resourceQuery, - resourceFragment - }; - if (options && options.resolveOptions !== undefined) { - this.resolveOptions = options.resolveOptions; + if (this.reportDependencyErrorsAndWarnings(module, block.blocks)) + hasProblems = true; } + return hasProblems; + } - if (options && typeof options.mode !== "string") { - throw new Error("options.mode is a required option"); + codeGeneration(callback) { + const { chunkGraph } = this; + this.codeGenerationResults = new CodeGenerationResults( + this.outputOptions.hashFunction + ); + /** @type {{module: Module, hash: string, runtime: RuntimeSpec, runtimes: RuntimeSpec[]}[]} */ + const jobs = []; + for (const module of this.modules) { + const runtimes = chunkGraph.getModuleRuntimes(module); + if (runtimes.size === 1) { + for (const runtime of runtimes) { + const hash = chunkGraph.getModuleHash(module, runtime); + jobs.push({ module, hash, runtime, runtimes: [runtime] }); + } + } else if (runtimes.size > 1) { + /** @type {Map} */ + const map = new Map(); + for (const runtime of runtimes) { + const hash = chunkGraph.getModuleHash(module, runtime); + const job = map.get(hash); + if (job === undefined) { + const newJob = { module, hash, runtime, runtimes: [runtime] }; + jobs.push(newJob); + map.set(hash, newJob); + } else { + job.runtimes.push(runtime); + } + } + } } - this._identifier = this._createIdentifier(); - this._forceBuild = true; - } - - /** - * @returns {Set} types available (do not mutate) - */ - getSourceTypes() { - return TYPES; + this._runCodeGenerationJobs(jobs, callback); } - /** - * Assuming this module is in the cache. Update the (cached) module with - * the fresh module from the factory. Usually updates internal references - * and properties. - * @param {Module} module fresh module - * @returns {void} - */ - updateCacheModule(module) { - const m = /** @type {ContextModule} */ (module); - this.resolveDependencies = m.resolveDependencies; - this.options = m.options; + _runCodeGenerationJobs(jobs, callback) { + let statModulesFromCache = 0; + let statModulesGenerated = 0; + const { chunkGraph, moduleGraph, dependencyTemplates, runtimeTemplate } = + this; + const results = this.codeGenerationResults; + const errors = []; + asyncLib.eachLimit( + jobs, + this.options.parallelism, + ({ module, hash, runtime, runtimes }, callback) => { + this._codeGenerationModule( + module, + runtime, + runtimes, + hash, + dependencyTemplates, + chunkGraph, + moduleGraph, + runtimeTemplate, + errors, + results, + (err, codeGenerated) => { + if (codeGenerated) statModulesGenerated++; + else statModulesFromCache++; + callback(err); + } + ); + }, + err => { + if (err) return callback(err); + if (errors.length > 0) { + errors.sort( + compareSelect(err => err.module, compareModulesByIdentifier) + ); + for (const error of errors) { + this.errors.push(error); + } + } + this.logger.log( + `${Math.round( + (100 * statModulesGenerated) / + (statModulesGenerated + statModulesFromCache) + )}% code generated (${statModulesGenerated} generated, ${statModulesFromCache} from cache)` + ); + callback(); + } + ); } /** - * Assuming this module is in the cache. Remove internal references to allow freeing some memory. + * @param {Module} module module + * @param {RuntimeSpec} runtime runtime + * @param {RuntimeSpec[]} runtimes runtimes + * @param {string} hash hash + * @param {DependencyTemplates} dependencyTemplates dependencyTemplates + * @param {ChunkGraph} chunkGraph chunkGraph + * @param {ModuleGraph} moduleGraph moduleGraph + * @param {RuntimeTemplate} runtimeTemplate runtimeTemplate + * @param {WebpackError[]} errors errors + * @param {CodeGenerationResults} results results + * @param {function(WebpackError=, boolean=): void} callback callback */ - cleanupForCache() { - super.cleanupForCache(); - this.resolveDependencies = undefined; - } - - prettyRegExp(regexString) { - // remove the "/" at the front and the beginning - // "/foo/" -> "foo" - return regexString - .substring(1, regexString.length - 1) - .replace(/!/g, "%21"); + _codeGenerationModule( + module, + runtime, + runtimes, + hash, + dependencyTemplates, + chunkGraph, + moduleGraph, + runtimeTemplate, + errors, + results, + callback + ) { + let codeGenerated = false; + const cache = new MultiItemCache( + runtimes.map(runtime => + this._codeGenerationCache.getItemCache( + `${module.identifier()}|${getRuntimeKey(runtime)}`, + `${hash}|${dependencyTemplates.getHash()}` + ) + ) + ); + cache.get((err, cachedResult) => { + if (err) return callback(err); + let result; + if (!cachedResult) { + try { + codeGenerated = true; + this.codeGeneratedModules.add(module); + result = module.codeGeneration({ + chunkGraph, + moduleGraph, + dependencyTemplates, + runtimeTemplate, + runtime + }); + } catch (err) { + errors.push(new CodeGenerationError(module, err)); + result = cachedResult = { + sources: new Map(), + runtimeRequirements: null + }; + } + } else { + result = cachedResult; + } + for (const runtime of runtimes) { + results.add(module, runtime, result); + } + if (!cachedResult) { + cache.store(result, err => callback(err, codeGenerated)); + } else { + callback(null, codeGenerated); + } + }); } - _createIdentifier() { - let identifier = this.context; - if (this.options.resourceQuery) { - identifier += `|${this.options.resourceQuery}`; - } - if (this.options.resourceFragment) { - identifier += `|${this.options.resourceFragment}`; - } - if (this.options.mode) { - identifier += `|${this.options.mode}`; - } - if (!this.options.recursive) { - identifier += "|nonrecursive"; - } - if (this.options.addon) { - identifier += `|${this.options.addon}`; - } - if (this.options.regExp) { - identifier += `|${this.options.regExp}`; - } - if (this.options.include) { - identifier += `|include: ${this.options.include}`; - } - if (this.options.exclude) { - identifier += `|exclude: ${this.options.exclude}`; - } - if (this.options.referencedExports) { - identifier += `|referencedExports: ${JSON.stringify( - this.options.referencedExports - )}`; - } - if (this.options.chunkName) { - identifier += `|chunkName: ${this.options.chunkName}`; - } - if (this.options.groupOptions) { - identifier += `|groupOptions: ${JSON.stringify( - this.options.groupOptions - )}`; + _getChunkGraphEntries() { + /** @type {Set} */ + const treeEntries = new Set(); + for (const ep of this.entrypoints.values()) { + const chunk = ep.getRuntimeChunk(); + if (chunk) treeEntries.add(chunk); } - if (this.options.namespaceObject === "strict") { - identifier += "|strict namespace object"; - } else if (this.options.namespaceObject) { - identifier += "|namespace object"; + for (const ep of this.asyncEntrypoints) { + const chunk = ep.getRuntimeChunk(); + if (chunk) treeEntries.add(chunk); } - - return identifier; - } - - /** - * @returns {string} a unique identifier of the module - */ - identifier() { - return this._identifier; + return treeEntries; } /** - * @param {RequestShortener} requestShortener the request shortener - * @returns {string} a user readable identifier of the module + * @param {Object} options options + * @param {ChunkGraph=} options.chunkGraph the chunk graph + * @param {Iterable=} options.modules modules + * @param {Iterable=} options.chunks chunks + * @param {CodeGenerationResults=} options.codeGenerationResults codeGenerationResults + * @param {Iterable=} options.chunkGraphEntries chunkGraphEntries + * @returns {void} */ - readableIdentifier(requestShortener) { - let identifier = requestShortener.shorten(this.context) + "/"; - if (this.options.resourceQuery) { - identifier += ` ${this.options.resourceQuery}`; - } - if (this.options.mode) { - identifier += ` ${this.options.mode}`; - } - if (!this.options.recursive) { - identifier += " nonrecursive"; - } - if (this.options.addon) { - identifier += ` ${requestShortener.shorten(this.options.addon)}`; - } - if (this.options.regExp) { - identifier += ` ${this.prettyRegExp(this.options.regExp + "")}`; - } - if (this.options.include) { - identifier += ` include: ${this.prettyRegExp(this.options.include + "")}`; + processRuntimeRequirements({ + chunkGraph = this.chunkGraph, + modules = this.modules, + chunks = this.chunks, + codeGenerationResults = this.codeGenerationResults, + chunkGraphEntries = this._getChunkGraphEntries() + } = {}) { + const context = { chunkGraph, codeGenerationResults }; + const { moduleMemCaches2 } = this; + this.logger.time("runtime requirements.modules"); + const additionalModuleRuntimeRequirements = + this.hooks.additionalModuleRuntimeRequirements; + const runtimeRequirementInModule = this.hooks.runtimeRequirementInModule; + for (const module of modules) { + if (chunkGraph.getNumberOfModuleChunks(module) > 0) { + const memCache = moduleMemCaches2 && moduleMemCaches2.get(module); + for (const runtime of chunkGraph.getModuleRuntimes(module)) { + if (memCache) { + const cached = memCache.get( + `moduleRuntimeRequirements-${getRuntimeKey(runtime)}` + ); + if (cached !== undefined) { + if (cached !== null) { + chunkGraph.addModuleRuntimeRequirements( + module, + runtime, + cached, + false + ); + } + continue; + } + } + let set; + const runtimeRequirements = + codeGenerationResults.getRuntimeRequirements(module, runtime); + if (runtimeRequirements && runtimeRequirements.size > 0) { + set = new Set(runtimeRequirements); + } else if (additionalModuleRuntimeRequirements.isUsed()) { + set = new Set(); + } else { + if (memCache) { + memCache.set( + `moduleRuntimeRequirements-${getRuntimeKey(runtime)}`, + null + ); + } + continue; + } + additionalModuleRuntimeRequirements.call(module, set, context); + + for (const r of set) { + const hook = runtimeRequirementInModule.get(r); + if (hook !== undefined) hook.call(module, set, context); + } + if (set.size === 0) { + if (memCache) { + memCache.set( + `moduleRuntimeRequirements-${getRuntimeKey(runtime)}`, + null + ); + } + } else { + if (memCache) { + memCache.set( + `moduleRuntimeRequirements-${getRuntimeKey(runtime)}`, + set + ); + chunkGraph.addModuleRuntimeRequirements( + module, + runtime, + set, + false + ); + } else { + chunkGraph.addModuleRuntimeRequirements(module, runtime, set); + } + } + } + } } - if (this.options.exclude) { - identifier += ` exclude: ${this.prettyRegExp(this.options.exclude + "")}`; + this.logger.timeEnd("runtime requirements.modules"); + + this.logger.time("runtime requirements.chunks"); + for (const chunk of chunks) { + const set = new Set(); + for (const module of chunkGraph.getChunkModulesIterable(chunk)) { + const runtimeRequirements = chunkGraph.getModuleRuntimeRequirements( + module, + chunk.runtime + ); + for (const r of runtimeRequirements) set.add(r); + } + this.hooks.additionalChunkRuntimeRequirements.call(chunk, set, context); + + for (const r of set) { + this.hooks.runtimeRequirementInChunk.for(r).call(chunk, set, context); + } + + chunkGraph.addChunkRuntimeRequirements(chunk, set); } - if (this.options.referencedExports) { - identifier += ` referencedExports: ${this.options.referencedExports - .map(e => e.join(".")) - .join(", ")}`; + this.logger.timeEnd("runtime requirements.chunks"); + + this.logger.time("runtime requirements.entries"); + for (const treeEntry of chunkGraphEntries) { + const set = new Set(); + for (const chunk of treeEntry.getAllReferencedChunks()) { + const runtimeRequirements = + chunkGraph.getChunkRuntimeRequirements(chunk); + for (const r of runtimeRequirements) set.add(r); + } + + this.hooks.additionalTreeRuntimeRequirements.call( + treeEntry, + set, + context + ); + + for (const r of set) { + this.hooks.runtimeRequirementInTree + .for(r) + .call(treeEntry, set, context); + } + + chunkGraph.addTreeRuntimeRequirements(treeEntry, set); } - if (this.options.chunkName) { - identifier += ` chunkName: ${this.options.chunkName}`; + this.logger.timeEnd("runtime requirements.entries"); + } + + // TODO webpack 6 make chunkGraph argument non-optional + /** + * @param {Chunk} chunk target chunk + * @param {RuntimeModule} module runtime module + * @param {ChunkGraph} chunkGraph the chunk graph + * @returns {void} + */ + addRuntimeModule(chunk, module, chunkGraph = this.chunkGraph) { + // Deprecated ModuleGraph association + if (this._backCompat) + ModuleGraph.setModuleGraphForModule(module, this.moduleGraph); + + // add it to the list + this.modules.add(module); + this._modules.set(module.identifier(), module); + + // connect to the chunk graph + chunkGraph.connectChunkAndModule(chunk, module); + chunkGraph.connectChunkAndRuntimeModule(chunk, module); + if (module.fullHash) { + chunkGraph.addFullHashModuleToChunk(chunk, module); + } else if (module.dependentHash) { + chunkGraph.addDependentHashModuleToChunk(chunk, module); } - if (this.options.groupOptions) { - const groupOptions = this.options.groupOptions; - for (const key of Object.keys(groupOptions)) { - identifier += ` ${key}: ${groupOptions[key]}`; + + // attach runtime module + module.attach(this, chunk, chunkGraph); + + // Setup internals + const exportsInfo = this.moduleGraph.getExportsInfo(module); + exportsInfo.setHasProvideInfo(); + if (typeof chunk.runtime === "string") { + exportsInfo.setUsedForSideEffectsOnly(chunk.runtime); + } else if (chunk.runtime === undefined) { + exportsInfo.setUsedForSideEffectsOnly(undefined); + } else { + for (const runtime of chunk.runtime) { + exportsInfo.setUsedForSideEffectsOnly(runtime); } } - if (this.options.namespaceObject === "strict") { - identifier += " strict namespace object"; - } else if (this.options.namespaceObject) { - identifier += " namespace object"; - } + chunkGraph.addModuleRuntimeRequirements( + module, + chunk.runtime, + new Set([RuntimeGlobals.requireScope]) + ); - return identifier; + // runtime modules don't need ids + chunkGraph.setModuleId(module, ""); + + // Call hook + this.hooks.runtimeModule.call(module, chunk); } /** - * @param {LibIdentOptions} options options - * @returns {string | null} an identifier for library inclusion + * @param {string | ChunkGroupOptions} groupOptions options for the chunk group + * @param {Module} module the module the references the chunk group + * @param {DependencyLocation} loc the location from with the chunk group is referenced (inside of module) + * @param {string} request the request from which the the chunk group is referenced + * @returns {ChunkGroup} the new or existing chunk group */ - libIdent(options) { - let identifier = contextify( - options.context, - this.context, - options.associatedObjectForCache - ); - if (this.options.mode) { - identifier += ` ${this.options.mode}`; + addChunkInGroup(groupOptions, module, loc, request) { + if (typeof groupOptions === "string") { + groupOptions = { name: groupOptions }; } - if (this.options.recursive) { - identifier += " recursive"; + const name = groupOptions.name; + + if (name) { + const chunkGroup = this.namedChunkGroups.get(name); + if (chunkGroup !== undefined) { + chunkGroup.addOptions(groupOptions); + if (module) { + chunkGroup.addOrigin(module, loc, request); + } + return chunkGroup; + } } - if (this.options.addon) { - identifier += ` ${contextify( - options.context, - this.options.addon, - options.associatedObjectForCache - )}`; + const chunkGroup = new ChunkGroup(groupOptions); + if (module) chunkGroup.addOrigin(module, loc, request); + const chunk = this.addChunk(name); + + connectChunkGroupAndChunk(chunkGroup, chunk); + + this.chunkGroups.push(chunkGroup); + if (name) { + this.namedChunkGroups.set(name, chunkGroup); } - if (this.options.regExp) { - identifier += ` ${this.prettyRegExp(this.options.regExp + "")}`; + return chunkGroup; + } + + /** + * @param {EntryOptions} options options for the entrypoint + * @param {Module} module the module the references the chunk group + * @param {DependencyLocation} loc the location from with the chunk group is referenced (inside of module) + * @param {string} request the request from which the the chunk group is referenced + * @returns {Entrypoint} the new or existing entrypoint + */ + addAsyncEntrypoint(options, module, loc, request) { + const name = options.name; + if (name) { + const entrypoint = this.namedChunkGroups.get(name); + if (entrypoint instanceof Entrypoint) { + if (entrypoint !== undefined) { + if (module) { + entrypoint.addOrigin(module, loc, request); + } + return entrypoint; + } + } else if (entrypoint) { + throw new Error( + `Cannot add an async entrypoint with the name '${name}', because there is already an chunk group with this name` + ); + } } - if (this.options.include) { - identifier += ` include: ${this.prettyRegExp(this.options.include + "")}`; + const chunk = this.addChunk(name); + if (options.filename) { + chunk.filenameTemplate = options.filename; } - if (this.options.exclude) { - identifier += ` exclude: ${this.prettyRegExp(this.options.exclude + "")}`; + const entrypoint = new Entrypoint(options, false); + entrypoint.setRuntimeChunk(chunk); + entrypoint.setEntrypointChunk(chunk); + if (name) { + this.namedChunkGroups.set(name, entrypoint); } - if (this.options.referencedExports) { - identifier += ` referencedExports: ${this.options.referencedExports - .map(e => e.join(".")) - .join(", ")}`; + this.chunkGroups.push(entrypoint); + this.asyncEntrypoints.push(entrypoint); + connectChunkGroupAndChunk(entrypoint, chunk); + if (module) { + entrypoint.addOrigin(module, loc, request); } - - return identifier; + return entrypoint; } /** - * @returns {void} + * This method first looks to see if a name is provided for a new chunk, + * and first looks to see if any named chunks already exist and reuse that chunk instead. + * + * @param {string=} name optional chunk name to be provided + * @returns {Chunk} create a chunk (invoked during seal event) */ - invalidateBuild() { - this._forceBuild = true; + addChunk(name) { + if (name) { + const chunk = this.namedChunks.get(name); + if (chunk !== undefined) { + return chunk; + } + } + const chunk = new Chunk(name, this._backCompat); + this.chunks.add(chunk); + if (this._backCompat) + ChunkGraph.setChunkGraphForChunk(chunk, this.chunkGraph); + if (name) { + this.namedChunks.set(name, chunk); + } + return chunk; } /** - * @param {NeedBuildContext} context context info - * @param {function(WebpackError=, boolean=): void} callback callback function, returns true, if the module needs a rebuild + * @deprecated + * @param {Module} module module to assign depth * @returns {void} */ - needBuild({ fileSystemInfo }, callback) { - // build if enforced - if (this._forceBuild) return callback(null, true); + assignDepth(module) { + const moduleGraph = this.moduleGraph; - // always build when we have no snapshot - if (!this.buildInfo.snapshot) return callback(null, true); + const queue = new Set([module]); + let depth; - fileSystemInfo.checkSnapshotValid(this.buildInfo.snapshot, (err, valid) => { - callback(err, !valid); - }); + moduleGraph.setDepth(module, 0); + + /** + * @param {Module} module module for processing + * @returns {void} + */ + const processModule = module => { + if (!moduleGraph.setDepthIfLower(module, depth)) return; + queue.add(module); + }; + + for (module of queue) { + queue.delete(module); + depth = moduleGraph.getDepth(module) + 1; + + for (const connection of moduleGraph.getOutgoingConnections(module)) { + const refModule = connection.module; + if (refModule) { + processModule(refModule); + } + } + } } /** - * @param {WebpackOptions} options webpack options - * @param {Compilation} compilation the compilation - * @param {ResolverWithOptions} resolver the resolver - * @param {InputFileSystem} fs the file system - * @param {function(WebpackError=): void} callback callback function + * @param {Set} modules module to assign depth * @returns {void} */ - build(options, compilation, resolver, fs, callback) { - this._forceBuild = false; - /** @type {BuildMeta} */ - this.buildMeta = { - exportsType: "default", - defaultObject: "redirect-warn" - }; - this.buildInfo = { - snapshot: undefined - }; - this.dependencies.length = 0; - this.blocks.length = 0; - const startTime = Date.now(); - this.resolveDependencies(fs, this.options, (err, dependencies) => { - if (err) { - return callback( - makeWebpackError(err, "ContextModule.resolveDependencies") - ); - } - - // abort if something failed - // this will create an empty context - if (!dependencies) { - callback(); - return; - } + assignDepths(modules) { + const moduleGraph = this.moduleGraph; - // enhance dependencies with meta info - for (const dep of dependencies) { - dep.loc = { - name: dep.userRequest - }; - dep.request = this.options.addon + dep.request; - } - dependencies.sort( - concatComparators( - compareSelect(a => a.loc, compareLocations), - keepOriginalOrder(this.dependencies) - ) - ); + /** @type {Set} */ + const queue = new Set(modules); + queue.add(1); + let depth = 0; - if (this.options.mode === "sync" || this.options.mode === "eager") { - // if we have an sync or eager context - // just add all dependencies and continue - this.dependencies = dependencies; - } else if (this.options.mode === "lazy-once") { - // for the lazy-once mode create a new async dependency block - // and add that block to this context - if (dependencies.length > 0) { - const block = new AsyncDependenciesBlock({ - ...this.options.groupOptions, - name: this.options.chunkName - }); - for (const dep of dependencies) { - block.addDependency(dep); - } - this.addBlock(block); - } - } else if ( - this.options.mode === "weak" || - this.options.mode === "async-weak" - ) { - // we mark all dependencies as weak - for (const dep of dependencies) { - dep.weak = true; - } - this.dependencies = dependencies; - } else if (this.options.mode === "lazy") { - // if we are lazy create a new async dependency block per dependency - // and add all blocks to this context - let index = 0; - for (const dep of dependencies) { - let chunkName = this.options.chunkName; - if (chunkName) { - if (!/\[(index|request)\]/.test(chunkName)) { - chunkName += "[index]"; - } - chunkName = chunkName.replace(/\[index\]/g, `${index++}`); - chunkName = chunkName.replace( - /\[request\]/g, - Template.toPath(dep.userRequest) - ); + let i = 0; + for (const module of queue) { + i++; + if (typeof module === "number") { + depth = module; + if (queue.size === i) return; + queue.add(depth + 1); + } else { + moduleGraph.setDepth(module, depth); + for (const { module: refModule } of moduleGraph.getOutgoingConnections( + module + )) { + if (refModule) { + queue.add(refModule); } - const block = new AsyncDependenciesBlock( - { - ...this.options.groupOptions, - name: chunkName - }, - dep.loc, - dep.userRequest - ); - block.addDependency(dep); - this.addBlock(block); } - } else { - callback( - new WebpackError(`Unsupported mode "${this.options.mode}" in context`) - ); - return; } - compilation.fileSystemInfo.createSnapshot( - startTime, - null, - [this.context], - null, - SNAPSHOT_OPTIONS, - (err, snapshot) => { - if (err) return callback(err); - this.buildInfo.snapshot = snapshot; - callback(); - } - ); - }); + } } /** - * @param {LazySet} fileDependencies set where file dependencies are added to - * @param {LazySet} contextDependencies set where context dependencies are added to - * @param {LazySet} missingDependencies set where missing dependencies are added to - * @param {LazySet} buildDependencies set where build dependencies are added to + * @param {Dependency} dependency the dependency + * @param {RuntimeSpec} runtime the runtime + * @returns {(string[] | ReferencedExport)[]} referenced exports */ - addCacheDependencies( - fileDependencies, - contextDependencies, - missingDependencies, - buildDependencies - ) { - contextDependencies.add(this.context); + getDependencyReferencedExports(dependency, runtime) { + const referencedExports = dependency.getReferencedExports( + this.moduleGraph, + runtime + ); + return this.hooks.dependencyReferencedExports.call( + referencedExports, + dependency, + runtime + ); } /** - * @param {ContextElementDependency[]} dependencies all dependencies - * @param {ChunkGraph} chunkGraph chunk graph - * @returns {TODO} TODO + * + * @param {Module} module module relationship for removal + * @param {DependenciesBlockLike} block //TODO: good description + * @returns {void} */ - getUserRequestMap(dependencies, chunkGraph) { - const moduleGraph = chunkGraph.moduleGraph; - // if we filter first we get a new array - // therefore we don't need to create a clone of dependencies explicitly - // therefore the order of this is !important! - const sortedDependencies = dependencies - .filter(dependency => moduleGraph.getModule(dependency)) - .sort((a, b) => { - if (a.userRequest === b.userRequest) { - return 0; + removeReasonsOfDependencyBlock(module, block) { + if (block.blocks) { + for (const b of block.blocks) { + this.removeReasonsOfDependencyBlock(module, b); + } + } + + if (block.dependencies) { + for (const dep of block.dependencies) { + const originalModule = this.moduleGraph.getModule(dep); + if (originalModule) { + this.moduleGraph.removeConnection(dep); + + if (this.chunkGraph) { + for (const chunk of this.chunkGraph.getModuleChunks( + originalModule + )) { + this.patchChunksAfterReasonRemoval(originalModule, chunk); + } + } } - return a.userRequest < b.userRequest ? -1 : 1; - }); - const map = Object.create(null); - for (const dep of sortedDependencies) { - const module = moduleGraph.getModule(dep); - map[dep.userRequest] = chunkGraph.getModuleId(module); + } } - return map; } /** - * @param {ContextElementDependency[]} dependencies all dependencies - * @param {ChunkGraph} chunkGraph chunk graph - * @returns {TODO} TODO + * @param {Module} module module to patch tie + * @param {Chunk} chunk chunk to patch tie + * @returns {void} */ - getFakeMap(dependencies, chunkGraph) { - if (!this.options.namespaceObject) { - return 9; + patchChunksAfterReasonRemoval(module, chunk) { + if (!module.hasReasons(this.moduleGraph, chunk.runtime)) { + this.removeReasonsOfDependencyBlock(module, module); } - const moduleGraph = chunkGraph.moduleGraph; - // bitfield - let hasType = 0; - const comparator = compareModulesById(chunkGraph); - // if we filter first we get a new array - // therefore we don't need to create a clone of dependencies explicitly - // therefore the order of this is !important! - const sortedModules = dependencies - .map(dependency => moduleGraph.getModule(dependency)) - .filter(Boolean) - .sort(comparator); - const fakeMap = Object.create(null); - for (const module of sortedModules) { - const exportsType = module.getExportsType( - moduleGraph, - this.options.namespaceObject === "strict" - ); - const id = chunkGraph.getModuleId(module); - switch (exportsType) { - case "namespace": - fakeMap[id] = 9; - hasType |= 1; - break; - case "dynamic": - fakeMap[id] = 7; - hasType |= 2; - break; - case "default-only": - fakeMap[id] = 1; - hasType |= 4; - break; - case "default-with-named": - fakeMap[id] = 3; - hasType |= 8; - break; - default: - throw new Error(`Unexpected exports type ${exportsType}`); + if (!module.hasReasonForChunk(chunk, this.moduleGraph, this.chunkGraph)) { + if (this.chunkGraph.isModuleInChunk(module, chunk)) { + this.chunkGraph.disconnectChunkAndModule(chunk, module); + this.removeChunkFromDependencies(module, chunk); } } - if (hasType === 1) { - return 9; - } - if (hasType === 2) { - return 7; - } - if (hasType === 4) { - return 1; - } - if (hasType === 8) { - return 3; - } - if (hasType === 0) { - return 9; - } - return fakeMap; } - getFakeMapInitStatement(fakeMap) { - return typeof fakeMap === "object" - ? `var fakeMap = ${JSON.stringify(fakeMap, null, "\t")};` - : ""; - } + /** + * + * @param {DependenciesBlock} block block tie for Chunk + * @param {Chunk} chunk chunk to remove from dep + * @returns {void} + */ + removeChunkFromDependencies(block, chunk) { + /** + * @param {Dependency} d dependency to (maybe) patch up + */ + const iteratorDependency = d => { + const depModule = this.moduleGraph.getModule(d); + if (!depModule) { + return; + } + this.patchChunksAfterReasonRemoval(depModule, chunk); + }; - getReturn(type, asyncModule) { - if (type === 9) { - return "__webpack_require__(id)"; + const blocks = block.blocks; + for (let indexBlock = 0; indexBlock < blocks.length; indexBlock++) { + const asyncBlock = blocks[indexBlock]; + const chunkGroup = this.chunkGraph.getBlockChunkGroup(asyncBlock); + // Grab all chunks from the first Block's AsyncDepBlock + const chunks = chunkGroup.chunks; + // For each chunk in chunkGroup + for (let indexChunk = 0; indexChunk < chunks.length; indexChunk++) { + const iteratedChunk = chunks[indexChunk]; + chunkGroup.removeChunk(iteratedChunk); + // Recurse + this.removeChunkFromDependencies(block, iteratedChunk); + } } - return `${RuntimeGlobals.createFakeNamespaceObject}(id, ${type}${ - asyncModule ? " | 16" : "" - })`; - } - getReturnModuleObjectSource( - fakeMap, - asyncModule, - fakeMapDataExpression = "fakeMap[id]" - ) { - if (typeof fakeMap === "number") { - return `return ${this.getReturn(fakeMap, asyncModule)};`; + if (block.dependencies) { + for (const dep of block.dependencies) iteratorDependency(dep); } - return `return ${ - RuntimeGlobals.createFakeNamespaceObject - }(id, ${fakeMapDataExpression}${asyncModule ? " | 16" : ""})`; } - /** - * @param {TODO} dependencies TODO - * @param {TODO} id TODO - * @param {ChunkGraph} chunkGraph the chunk graph - * @returns {string} source code - */ - getSyncSource(dependencies, id, chunkGraph) { - const map = this.getUserRequestMap(dependencies, chunkGraph); - const fakeMap = this.getFakeMap(dependencies, chunkGraph); - const returnModuleObject = this.getReturnModuleObjectSource(fakeMap); - - return `var map = ${JSON.stringify(map, null, "\t")}; -${this.getFakeMapInitStatement(fakeMap)} - -function webpackContext(req) { - var id = webpackContextResolve(req); - ${returnModuleObject} -} -function webpackContextResolve(req) { - if(!${RuntimeGlobals.hasOwnProperty}(map, req)) { - var e = new Error("Cannot find module '" + req + "'"); - e.code = 'MODULE_NOT_FOUND'; - throw e; - } - return map[req]; -} -webpackContext.keys = function webpackContextKeys() { - return Object.keys(map); -}; -webpackContext.resolve = webpackContextResolve; -module.exports = webpackContext; -webpackContext.id = ${JSON.stringify(id)};`; + assignRuntimeIds() { + const { chunkGraph } = this; + const processEntrypoint = ep => { + const runtime = ep.options.runtime || ep.name; + const chunk = ep.getRuntimeChunk(); + chunkGraph.setRuntimeId(runtime, chunk.id); + }; + for (const ep of this.entrypoints.values()) { + processEntrypoint(ep); + } + for (const ep of this.asyncEntrypoints) { + processEntrypoint(ep); + } } - /** - * @param {TODO} dependencies TODO - * @param {TODO} id TODO - * @param {ChunkGraph} chunkGraph the chunk graph - * @returns {string} source code - */ - getWeakSyncSource(dependencies, id, chunkGraph) { - const map = this.getUserRequestMap(dependencies, chunkGraph); - const fakeMap = this.getFakeMap(dependencies, chunkGraph); - const returnModuleObject = this.getReturnModuleObjectSource(fakeMap); - - return `var map = ${JSON.stringify(map, null, "\t")}; -${this.getFakeMapInitStatement(fakeMap)} + sortItemsWithChunkIds() { + for (const chunkGroup of this.chunkGroups) { + chunkGroup.sortItems(); + } -function webpackContext(req) { - var id = webpackContextResolve(req); - if(!${RuntimeGlobals.moduleFactories}[id]) { - var e = new Error("Module '" + req + "' ('" + id + "') is not available (weak dependency)"); - e.code = 'MODULE_NOT_FOUND'; - throw e; - } - ${returnModuleObject} -} -function webpackContextResolve(req) { - if(!${RuntimeGlobals.hasOwnProperty}(map, req)) { - var e = new Error("Cannot find module '" + req + "'"); - e.code = 'MODULE_NOT_FOUND'; - throw e; - } - return map[req]; -} -webpackContext.keys = function webpackContextKeys() { - return Object.keys(map); -}; -webpackContext.resolve = webpackContextResolve; -webpackContext.id = ${JSON.stringify(id)}; -module.exports = webpackContext;`; + this.errors.sort(compareErrors); + this.warnings.sort(compareErrors); + this.children.sort(byNameOrHash); } - /** - * @param {TODO} dependencies TODO - * @param {TODO} id TODO - * @param {Object} context context - * @param {ChunkGraph} context.chunkGraph the chunk graph - * @param {RuntimeTemplate} context.runtimeTemplate the chunk graph - * @returns {string} source code - */ - getAsyncWeakSource(dependencies, id, { chunkGraph, runtimeTemplate }) { - const arrow = runtimeTemplate.supportsArrowFunction(); - const map = this.getUserRequestMap(dependencies, chunkGraph); - const fakeMap = this.getFakeMap(dependencies, chunkGraph); - const returnModuleObject = this.getReturnModuleObjectSource(fakeMap, true); - - return `var map = ${JSON.stringify(map, null, "\t")}; -${this.getFakeMapInitStatement(fakeMap)} + summarizeDependencies() { + for ( + let indexChildren = 0; + indexChildren < this.children.length; + indexChildren++ + ) { + const child = this.children[indexChildren]; -function webpackAsyncContext(req) { - return webpackAsyncContextResolve(req).then(${ - arrow ? "id =>" : "function(id)" - } { - if(!${RuntimeGlobals.moduleFactories}[id]) { - var e = new Error("Module '" + req + "' ('" + id + "') is not available (weak dependency)"); - e.code = 'MODULE_NOT_FOUND'; - throw e; + this.fileDependencies.addAll(child.fileDependencies); + this.contextDependencies.addAll(child.contextDependencies); + this.missingDependencies.addAll(child.missingDependencies); + this.buildDependencies.addAll(child.buildDependencies); } - ${returnModuleObject} - }); -} -function webpackAsyncContextResolve(req) { - // Here Promise.resolve().then() is used instead of new Promise() to prevent - // uncaught exception popping up in devtools - return Promise.resolve().then(${arrow ? "() =>" : "function()"} { - if(!${RuntimeGlobals.hasOwnProperty}(map, req)) { - var e = new Error("Cannot find module '" + req + "'"); - e.code = 'MODULE_NOT_FOUND'; - throw e; + + for (const module of this.modules) { + module.addCacheDependencies( + this.fileDependencies, + this.contextDependencies, + this.missingDependencies, + this.buildDependencies + ); } - return map[req]; - }); -} -webpackAsyncContext.keys = ${runtimeTemplate.returningFunction( - "Object.keys(map)" - )}; -webpackAsyncContext.resolve = webpackAsyncContextResolve; -webpackAsyncContext.id = ${JSON.stringify(id)}; -module.exports = webpackAsyncContext;`; } - /** - * @param {TODO} dependencies TODO - * @param {TODO} id TODO - * @param {Object} context context - * @param {ChunkGraph} context.chunkGraph the chunk graph - * @param {RuntimeTemplate} context.runtimeTemplate the chunk graph - * @returns {string} source code - */ - getEagerSource(dependencies, id, { chunkGraph, runtimeTemplate }) { - const arrow = runtimeTemplate.supportsArrowFunction(); - const map = this.getUserRequestMap(dependencies, chunkGraph); - const fakeMap = this.getFakeMap(dependencies, chunkGraph); - const thenFunction = - fakeMap !== 9 - ? `${arrow ? "id =>" : "function(id)"} { - ${this.getReturnModuleObjectSource(fakeMap)} - }` - : "__webpack_require__"; - return `var map = ${JSON.stringify(map, null, "\t")}; -${this.getFakeMapInitStatement(fakeMap)} - -function webpackAsyncContext(req) { - return webpackAsyncContextResolve(req).then(${thenFunction}); -} -function webpackAsyncContextResolve(req) { - // Here Promise.resolve().then() is used instead of new Promise() to prevent - // uncaught exception popping up in devtools - return Promise.resolve().then(${arrow ? "() =>" : "function()"} { - if(!${RuntimeGlobals.hasOwnProperty}(map, req)) { - var e = new Error("Cannot find module '" + req + "'"); - e.code = 'MODULE_NOT_FOUND'; - throw e; + createModuleHashes() { + let statModulesHashed = 0; + let statModulesFromCache = 0; + const { chunkGraph, runtimeTemplate, moduleMemCaches2 } = this; + const { hashFunction, hashDigest, hashDigestLength } = this.outputOptions; + for (const module of this.modules) { + const memCache = moduleMemCaches2 && moduleMemCaches2.get(module); + for (const runtime of chunkGraph.getModuleRuntimes(module)) { + if (memCache) { + const digest = memCache.get(`moduleHash-${getRuntimeKey(runtime)}`); + if (digest !== undefined) { + chunkGraph.setModuleHashes( + module, + runtime, + digest, + digest.substr(0, hashDigestLength) + ); + statModulesFromCache++; + continue; + } + } + statModulesHashed++; + const digest = this._createModuleHash( + module, + chunkGraph, + runtime, + hashFunction, + runtimeTemplate, + hashDigest, + hashDigestLength + ); + if (memCache) { + memCache.set(`moduleHash-${getRuntimeKey(runtime)}`, digest); + } + } } - return map[req]; - }); -} -webpackAsyncContext.keys = ${runtimeTemplate.returningFunction( - "Object.keys(map)" - )}; -webpackAsyncContext.resolve = webpackAsyncContextResolve; -webpackAsyncContext.id = ${JSON.stringify(id)}; -module.exports = webpackAsyncContext;`; + this.logger.log( + `${statModulesHashed} modules hashed, ${statModulesFromCache} from cache (${ + Math.round( + (100 * (statModulesHashed + statModulesFromCache)) / this.modules.size + ) / 100 + } variants per module in average)` + ); } - /** - * @param {TODO} block TODO - * @param {TODO} dependencies TODO - * @param {TODO} id TODO - * @param {Object} options options object - * @param {RuntimeTemplate} options.runtimeTemplate the runtime template - * @param {ChunkGraph} options.chunkGraph the chunk graph - * @returns {string} source code - */ - getLazyOnceSource(block, dependencies, id, { runtimeTemplate, chunkGraph }) { - const promise = runtimeTemplate.blockPromise({ + _createModuleHash( + module, + chunkGraph, + runtime, + hashFunction, + runtimeTemplate, + hashDigest, + hashDigestLength + ) { + const moduleHash = createHash(hashFunction); + module.updateHash(moduleHash, { chunkGraph, - block, - message: "lazy-once context", - runtimeRequirements: new Set() + runtime, + runtimeTemplate }); - const arrow = runtimeTemplate.supportsArrowFunction(); - const map = this.getUserRequestMap(dependencies, chunkGraph); - const fakeMap = this.getFakeMap(dependencies, chunkGraph); - const thenFunction = - fakeMap !== 9 - ? `${arrow ? "id =>" : "function(id)"} { - ${this.getReturnModuleObjectSource(fakeMap, true)}; - }` - : "__webpack_require__"; - - return `var map = ${JSON.stringify(map, null, "\t")}; -${this.getFakeMapInitStatement(fakeMap)} - -function webpackAsyncContext(req) { - return webpackAsyncContextResolve(req).then(${thenFunction}); -} -function webpackAsyncContextResolve(req) { - return ${promise}.then(${arrow ? "() =>" : "function()"} { - if(!${RuntimeGlobals.hasOwnProperty}(map, req)) { - var e = new Error("Cannot find module '" + req + "'"); - e.code = 'MODULE_NOT_FOUND'; - throw e; - } - return map[req]; - }); -} -webpackAsyncContext.keys = ${runtimeTemplate.returningFunction( - "Object.keys(map)" - )}; -webpackAsyncContext.resolve = webpackAsyncContextResolve; -webpackAsyncContext.id = ${JSON.stringify(id)}; -module.exports = webpackAsyncContext;`; + const moduleHashDigest = /** @type {string} */ ( + moduleHash.digest(hashDigest) + ); + chunkGraph.setModuleHashes( + module, + runtime, + moduleHashDigest, + moduleHashDigest.substr(0, hashDigestLength) + ); + return moduleHashDigest; } - /** - * @param {TODO} blocks TODO - * @param {TODO} id TODO - * @param {Object} context context - * @param {ChunkGraph} context.chunkGraph the chunk graph - * @param {RuntimeTemplate} context.runtimeTemplate the chunk graph - * @returns {string} source code - */ - getLazySource(blocks, id, { chunkGraph, runtimeTemplate }) { - const moduleGraph = chunkGraph.moduleGraph; - const arrow = runtimeTemplate.supportsArrowFunction(); - let hasMultipleOrNoChunks = false; - let hasNoChunk = true; - const fakeMap = this.getFakeMap( - blocks.map(b => b.dependencies[0]), - chunkGraph - ); - const hasFakeMap = typeof fakeMap === "object"; - const items = blocks - .map(block => { - const dependency = block.dependencies[0]; - return { - dependency: dependency, - module: moduleGraph.getModule(dependency), - block: block, - userRequest: dependency.userRequest, - chunks: undefined - }; - }) - .filter(item => item.module); - for (const item of items) { - const chunkGroup = chunkGraph.getBlockChunkGroup(item.block); - const chunks = (chunkGroup && chunkGroup.chunks) || []; - item.chunks = chunks; - if (chunks.length > 0) { - hasNoChunk = false; + createHash() { + this.logger.time("hashing: initialize hash"); + const chunkGraph = this.chunkGraph; + const runtimeTemplate = this.runtimeTemplate; + const outputOptions = this.outputOptions; + const hashFunction = outputOptions.hashFunction; + const hashDigest = outputOptions.hashDigest; + const hashDigestLength = outputOptions.hashDigestLength; + const hash = createHash(hashFunction); + if (outputOptions.hashSalt) { + hash.update(outputOptions.hashSalt); + } + this.logger.timeEnd("hashing: initialize hash"); + if (this.children.length > 0) { + this.logger.time("hashing: hash child compilations"); + for (const child of this.children) { + hash.update(child.hash); } - if (chunks.length !== 1) { - hasMultipleOrNoChunks = true; + this.logger.timeEnd("hashing: hash child compilations"); + } + if (this.warnings.length > 0) { + this.logger.time("hashing: hash warnings"); + for (const warning of this.warnings) { + hash.update(`${warning.message}`); } + this.logger.timeEnd("hashing: hash warnings"); } - const shortMode = hasNoChunk && !hasFakeMap; - const sortedItems = items.sort((a, b) => { - if (a.userRequest === b.userRequest) return 0; - return a.userRequest < b.userRequest ? -1 : 1; - }); - const map = Object.create(null); - for (const item of sortedItems) { - const moduleId = chunkGraph.getModuleId(item.module); - if (shortMode) { - map[item.userRequest] = moduleId; - } else { - const arrayStart = [moduleId]; - if (hasFakeMap) { - arrayStart.push(fakeMap[moduleId]); - } - map[item.userRequest] = arrayStart.concat( - item.chunks.map(chunk => chunk.id) - ); + if (this.errors.length > 0) { + this.logger.time("hashing: hash errors"); + for (const error of this.errors) { + hash.update(`${error.message}`); } + this.logger.timeEnd("hashing: hash errors"); } - const chunksStartPosition = hasFakeMap ? 2 : 1; - const requestPrefix = hasNoChunk - ? "Promise.resolve()" - : hasMultipleOrNoChunks - ? `Promise.all(ids.slice(${chunksStartPosition}).map(${RuntimeGlobals.ensureChunk}))` - : `${RuntimeGlobals.ensureChunk}(ids[${chunksStartPosition}])`; - const returnModuleObject = this.getReturnModuleObjectSource( - fakeMap, - true, - shortMode ? "invalid" : "ids[1]" - ); - - const webpackAsyncContext = - requestPrefix === "Promise.resolve()" - ? ` -function webpackAsyncContext(req) { - return Promise.resolve().then(${arrow ? "() =>" : "function()"} { - if(!${RuntimeGlobals.hasOwnProperty}(map, req)) { - var e = new Error("Cannot find module '" + req + "'"); - e.code = 'MODULE_NOT_FOUND'; - throw e; + this.logger.time("hashing: sort chunks"); + /* + * all non-runtime chunks need to be hashes first, + * since runtime chunk might use their hashes. + * runtime chunks need to be hashed in the correct order + * since they may depend on each other (for async entrypoints). + * So we put all non-runtime chunks first and hash them in any order. + * And order runtime chunks according to referenced between each other. + * Chunks need to be in deterministic order since we add hashes to full chunk + * during these hashing. + */ + /** @type {Chunk[]} */ + const unorderedRuntimeChunks = []; + /** @type {Chunk[]} */ + const otherChunks = []; + for (const c of this.chunks) { + if (c.hasRuntime()) { + unorderedRuntimeChunks.push(c); + } else { + otherChunks.push(c); + } } + unorderedRuntimeChunks.sort(byId); + otherChunks.sort(byId); - ${shortMode ? "var id = map[req];" : "var ids = map[req], id = ids[0];"} - ${returnModuleObject} - }); -}` - : `function webpackAsyncContext(req) { - if(!${RuntimeGlobals.hasOwnProperty}(map, req)) { - return Promise.resolve().then(${arrow ? "() =>" : "function()"} { - var e = new Error("Cannot find module '" + req + "'"); - e.code = 'MODULE_NOT_FOUND'; - throw e; - }); - } - - var ids = map[req], id = ids[0]; - return ${requestPrefix}.then(${arrow ? "() =>" : "function()"} { - ${returnModuleObject} - }); -}`; - - return `var map = ${JSON.stringify(map, null, "\t")}; -${webpackAsyncContext} -webpackAsyncContext.keys = ${runtimeTemplate.returningFunction( - "Object.keys(map)" - )}; -webpackAsyncContext.id = ${JSON.stringify(id)}; -module.exports = webpackAsyncContext;`; - } - - getSourceForEmptyContext(id, runtimeTemplate) { - return `function webpackEmptyContext(req) { - var e = new Error("Cannot find module '" + req + "'"); - e.code = 'MODULE_NOT_FOUND'; - throw e; -} -webpackEmptyContext.keys = ${runtimeTemplate.returningFunction("[]")}; -webpackEmptyContext.resolve = webpackEmptyContext; -webpackEmptyContext.id = ${JSON.stringify(id)}; -module.exports = webpackEmptyContext;`; - } - - getSourceForEmptyAsyncContext(id, runtimeTemplate) { - const arrow = runtimeTemplate.supportsArrowFunction(); - return `function webpackEmptyAsyncContext(req) { - // Here Promise.resolve().then() is used instead of new Promise() to prevent - // uncaught exception popping up in devtools - return Promise.resolve().then(${arrow ? "() =>" : "function()"} { - var e = new Error("Cannot find module '" + req + "'"); - e.code = 'MODULE_NOT_FOUND'; - throw e; - }); -} -webpackEmptyAsyncContext.keys = ${runtimeTemplate.returningFunction("[]")}; -webpackEmptyAsyncContext.resolve = webpackEmptyAsyncContext; -webpackEmptyAsyncContext.id = ${JSON.stringify(id)}; -module.exports = webpackEmptyAsyncContext;`; - } - - /** - * @param {string} asyncMode module mode - * @param {CodeGenerationContext} context context info - * @returns {string} the source code - */ - getSourceString(asyncMode, { runtimeTemplate, chunkGraph }) { - const id = chunkGraph.getModuleId(this); - if (asyncMode === "lazy") { - if (this.blocks && this.blocks.length > 0) { - return this.getLazySource(this.blocks, id, { - runtimeTemplate, - chunkGraph - }); + /** @typedef {{ chunk: Chunk, referencedBy: RuntimeChunkInfo[], remaining: number }} RuntimeChunkInfo */ + /** @type {Map} */ + const runtimeChunksMap = new Map(); + for (const chunk of unorderedRuntimeChunks) { + runtimeChunksMap.set(chunk, { + chunk, + referencedBy: [], + remaining: 0 + }); + } + let remaining = 0; + for (const info of runtimeChunksMap.values()) { + for (const other of new Set( + Array.from(info.chunk.getAllReferencedAsyncEntrypoints()).map( + e => e.chunks[e.chunks.length - 1] + ) + )) { + const otherInfo = runtimeChunksMap.get(other); + otherInfo.referencedBy.push(info); + info.remaining++; + remaining++; } - return this.getSourceForEmptyAsyncContext(id, runtimeTemplate); } - if (asyncMode === "eager") { - if (this.dependencies && this.dependencies.length > 0) { - return this.getEagerSource(this.dependencies, id, { - chunkGraph, - runtimeTemplate - }); + /** @type {Chunk[]} */ + const runtimeChunks = []; + for (const info of runtimeChunksMap.values()) { + if (info.remaining === 0) { + runtimeChunks.push(info.chunk); } - return this.getSourceForEmptyAsyncContext(id, runtimeTemplate); } - if (asyncMode === "lazy-once") { - const block = this.blocks[0]; - if (block) { - return this.getLazyOnceSource(block, block.dependencies, id, { - runtimeTemplate, - chunkGraph - }); + // If there are any references between chunks + // make sure to follow these chains + if (remaining > 0) { + const readyChunks = []; + for (const chunk of runtimeChunks) { + const hasFullHashModules = + chunkGraph.getNumberOfChunkFullHashModules(chunk) !== 0; + const info = runtimeChunksMap.get(chunk); + for (const otherInfo of info.referencedBy) { + if (hasFullHashModules) { + chunkGraph.upgradeDependentToFullHashModules(otherInfo.chunk); + } + remaining--; + if (--otherInfo.remaining === 0) { + readyChunks.push(otherInfo.chunk); + } + } + if (readyChunks.length > 0) { + // This ensures deterministic ordering, since referencedBy is non-deterministic + readyChunks.sort(byId); + for (const c of readyChunks) runtimeChunks.push(c); + readyChunks.length = 0; + } } - return this.getSourceForEmptyAsyncContext(id, runtimeTemplate); } - if (asyncMode === "async-weak") { - if (this.dependencies && this.dependencies.length > 0) { - return this.getAsyncWeakSource(this.dependencies, id, { + // If there are still remaining references we have cycles and want to create a warning + if (remaining > 0) { + let circularRuntimeChunkInfo = []; + for (const info of runtimeChunksMap.values()) { + if (info.remaining !== 0) { + circularRuntimeChunkInfo.push(info); + } + } + circularRuntimeChunkInfo.sort(compareSelect(i => i.chunk, byId)); + const err = + new WebpackError(`Circular dependency between chunks with runtime (${Array.from( + circularRuntimeChunkInfo, + c => c.chunk.name || c.chunk.id + ).join(", ")}) +This prevents using hashes of each other and should be avoided.`); + err.chunk = circularRuntimeChunkInfo[0].chunk; + this.warnings.push(err); + for (const i of circularRuntimeChunkInfo) runtimeChunks.push(i.chunk); + } + this.logger.timeEnd("hashing: sort chunks"); + + const fullHashChunks = new Set(); + /** @type {{module: Module, hash: string, runtime: RuntimeSpec, runtimes: RuntimeSpec[]}[]} */ + const codeGenerationJobs = []; + /** @type {Map>} */ + const codeGenerationJobsMap = new Map(); + + const processChunk = chunk => { + // Last minute module hash generation for modules that depend on chunk hashes + this.logger.time("hashing: hash runtime modules"); + const runtime = chunk.runtime; + for (const module of chunkGraph.getChunkModulesIterable(chunk)) { + if (!chunkGraph.hasModuleHashes(module, runtime)) { + const hash = this._createModuleHash( + module, + chunkGraph, + runtime, + hashFunction, + runtimeTemplate, + hashDigest, + hashDigestLength + ); + let hashMap = codeGenerationJobsMap.get(hash); + if (hashMap) { + const moduleJob = hashMap.get(module); + if (moduleJob) { + moduleJob.runtimes.push(runtime); + continue; + } + } else { + hashMap = new Map(); + codeGenerationJobsMap.set(hash, hashMap); + } + const job = { + module, + hash, + runtime, + runtimes: [runtime] + }; + hashMap.set(module, job); + codeGenerationJobs.push(job); + } + } + this.logger.timeAggregate("hashing: hash runtime modules"); + this.logger.time("hashing: hash chunks"); + const chunkHash = createHash(hashFunction); + try { + if (outputOptions.hashSalt) { + chunkHash.update(outputOptions.hashSalt); + } + chunk.updateHash(chunkHash, chunkGraph); + this.hooks.chunkHash.call(chunk, chunkHash, { chunkGraph, - runtimeTemplate + moduleGraph: this.moduleGraph, + runtimeTemplate: this.runtimeTemplate }); + const chunkHashDigest = /** @type {string} */ ( + chunkHash.digest(hashDigest) + ); + hash.update(chunkHashDigest); + chunk.hash = chunkHashDigest; + chunk.renderedHash = chunk.hash.substr(0, hashDigestLength); + const fullHashModules = + chunkGraph.getChunkFullHashModulesIterable(chunk); + if (fullHashModules) { + fullHashChunks.add(chunk); + } else { + this.hooks.contentHash.call(chunk); + } + } catch (err) { + this.errors.push(new ChunkRenderError(chunk, "", err)); } - return this.getSourceForEmptyAsyncContext(id, runtimeTemplate); - } - if (asyncMode === "weak") { - if (this.dependencies && this.dependencies.length > 0) { - return this.getWeakSyncSource(this.dependencies, id, chunkGraph); + this.logger.timeAggregate("hashing: hash chunks"); + }; + otherChunks.forEach(processChunk); + for (const chunk of runtimeChunks) processChunk(chunk); + + this.logger.timeAggregateEnd("hashing: hash runtime modules"); + this.logger.timeAggregateEnd("hashing: hash chunks"); + this.logger.time("hashing: hash digest"); + this.hooks.fullHash.call(hash); + this.fullHash = /** @type {string} */ (hash.digest(hashDigest)); + this.hash = this.fullHash.substr(0, hashDigestLength); + this.logger.timeEnd("hashing: hash digest"); + + this.logger.time("hashing: process full hash modules"); + for (const chunk of fullHashChunks) { + for (const module of chunkGraph.getChunkFullHashModulesIterable(chunk)) { + const moduleHash = createHash(hashFunction); + module.updateHash(moduleHash, { + chunkGraph, + runtime: chunk.runtime, + runtimeTemplate + }); + const moduleHashDigest = /** @type {string} */ ( + moduleHash.digest(hashDigest) + ); + const oldHash = chunkGraph.getModuleHash(module, chunk.runtime); + chunkGraph.setModuleHashes( + module, + chunk.runtime, + moduleHashDigest, + moduleHashDigest.substr(0, hashDigestLength) + ); + codeGenerationJobsMap.get(oldHash).get(module).hash = moduleHashDigest; } + const chunkHash = createHash(hashFunction); + chunkHash.update(chunk.hash); + chunkHash.update(this.hash); + const chunkHashDigest = /** @type {string} */ ( + chunkHash.digest(hashDigest) + ); + chunk.hash = chunkHashDigest; + chunk.renderedHash = chunk.hash.substr(0, hashDigestLength); + this.hooks.contentHash.call(chunk); } - if (this.dependencies && this.dependencies.length > 0) { - return this.getSyncSource(this.dependencies, id, chunkGraph); - } - return this.getSourceForEmptyContext(id, runtimeTemplate); + this.logger.timeEnd("hashing: process full hash modules"); + return codeGenerationJobs; } - getSource(sourceString) { - if (this.useSourceMap || this.useSimpleSourceMap) { - return new OriginalSource(sourceString, this.identifier()); + /** + * @param {string} file file name + * @param {Source} source asset source + * @param {AssetInfo} assetInfo extra asset information + * @returns {void} + */ + emitAsset(file, source, assetInfo = {}) { + if (this.assets[file]) { + if (!isSourceEqual(this.assets[file], source)) { + this.errors.push( + new WebpackError( + `Conflict: Multiple assets emit different content to the same filename ${file}` + ) + ); + this.assets[file] = source; + this._setAssetInfo(file, assetInfo); + return; + } + const oldInfo = this.assetsInfo.get(file); + const newInfo = Object.assign({}, oldInfo, assetInfo); + this._setAssetInfo(file, newInfo, oldInfo); + return; } - return new RawSource(sourceString); + this.assets[file] = source; + this._setAssetInfo(file, assetInfo, undefined); } - /** - * @param {CodeGenerationContext} context context for code generation - * @returns {CodeGenerationResult} result - */ - codeGeneration(context) { - const { chunkGraph } = context; - const sources = new Map(); - sources.set( - "javascript", - this.getSource(this.getSourceString(this.options.mode, context)) - ); - const set = new Set(); - const allDeps = /** @type {ContextElementDependency[]} */ ( - this.dependencies.concat(this.blocks.map(b => b.dependencies[0])) - ); - set.add(RuntimeGlobals.module); - set.add(RuntimeGlobals.hasOwnProperty); - if (allDeps.length > 0) { - const asyncMode = this.options.mode; - set.add(RuntimeGlobals.require); - if (asyncMode === "weak") { - set.add(RuntimeGlobals.moduleFactories); - } else if (asyncMode === "async-weak") { - set.add(RuntimeGlobals.moduleFactories); - set.add(RuntimeGlobals.ensureChunk); - } else if (asyncMode === "lazy" || asyncMode === "lazy-once") { - set.add(RuntimeGlobals.ensureChunk); + _setAssetInfo(file, newInfo, oldInfo = this.assetsInfo.get(file)) { + if (newInfo === undefined) { + this.assetsInfo.delete(file); + } else { + this.assetsInfo.set(file, newInfo); + } + const oldRelated = oldInfo && oldInfo.related; + const newRelated = newInfo && newInfo.related; + if (oldRelated) { + for (const key of Object.keys(oldRelated)) { + const remove = name => { + const relatedIn = this._assetsRelatedIn.get(name); + if (relatedIn === undefined) return; + const entry = relatedIn.get(key); + if (entry === undefined) return; + entry.delete(file); + if (entry.size !== 0) return; + relatedIn.delete(key); + if (relatedIn.size === 0) this._assetsRelatedIn.delete(name); + }; + const entry = oldRelated[key]; + if (Array.isArray(entry)) { + entry.forEach(remove); + } else if (entry) { + remove(entry); + } } - if (this.getFakeMap(allDeps, chunkGraph) !== 9) { - set.add(RuntimeGlobals.createFakeNamespaceObject); + } + if (newRelated) { + for (const key of Object.keys(newRelated)) { + const add = name => { + let relatedIn = this._assetsRelatedIn.get(name); + if (relatedIn === undefined) { + this._assetsRelatedIn.set(name, (relatedIn = new Map())); + } + let entry = relatedIn.get(key); + if (entry === undefined) { + relatedIn.set(key, (entry = new Set())); + } + entry.add(file); + }; + const entry = newRelated[key]; + if (Array.isArray(entry)) { + entry.forEach(add); + } else if (entry) { + add(entry); + } } } - return { - sources, - runtimeRequirements: set - }; } /** - * @param {string=} type the source type for which the size should be estimated - * @returns {number} the estimated size of the module (must be non-zero) + * @param {string} file file name + * @param {Source | function(Source): Source} newSourceOrFunction new asset source or function converting old to new + * @param {AssetInfo | function(AssetInfo | undefined): AssetInfo} assetInfoUpdateOrFunction new asset info or function converting old to new */ - size(type) { - // base penalty - let size = 160; - - // if we don't have dependencies we stop here. - for (const dependency of this.dependencies) { - const element = /** @type {ContextElementDependency} */ (dependency); - size += 5 + element.userRequest.length; + updateAsset( + file, + newSourceOrFunction, + assetInfoUpdateOrFunction = undefined + ) { + if (!this.assets[file]) { + throw new Error( + `Called Compilation.updateAsset for not existing filename ${file}` + ); + } + if (typeof newSourceOrFunction === "function") { + this.assets[file] = newSourceOrFunction(this.assets[file]); + } else { + this.assets[file] = newSourceOrFunction; + } + if (assetInfoUpdateOrFunction !== undefined) { + const oldInfo = this.assetsInfo.get(file) || EMPTY_ASSET_INFO; + if (typeof assetInfoUpdateOrFunction === "function") { + this._setAssetInfo(file, assetInfoUpdateOrFunction(oldInfo), oldInfo); + } else { + this._setAssetInfo( + file, + cachedCleverMerge(oldInfo, assetInfoUpdateOrFunction), + oldInfo + ); + } } - return size; - } - - serialize(context) { - const { write } = context; - write(this._identifier); - write(this._forceBuild); - super.serialize(context); } - deserialize(context) { - const { read } = context; - this._identifier = read(); - this._forceBuild = read(); - super.deserialize(context); + renameAsset(file, newFile) { + const source = this.assets[file]; + if (!source) { + throw new Error( + `Called Compilation.renameAsset for not existing filename ${file}` + ); + } + if (this.assets[newFile]) { + if (!isSourceEqual(this.assets[file], source)) { + this.errors.push( + new WebpackError( + `Conflict: Called Compilation.renameAsset for already existing filename ${newFile} with different content` + ) + ); + } + } + const assetInfo = this.assetsInfo.get(file); + // Update related in all other assets + const relatedInInfo = this._assetsRelatedIn.get(file); + if (relatedInInfo) { + for (const [key, assets] of relatedInInfo) { + for (const name of assets) { + const info = this.assetsInfo.get(name); + if (!info) continue; + const related = info.related; + if (!related) continue; + const entry = related[key]; + let newEntry; + if (Array.isArray(entry)) { + newEntry = entry.map(x => (x === file ? newFile : x)); + } else if (entry === file) { + newEntry = newFile; + } else continue; + this.assetsInfo.set(name, { + ...info, + related: { + ...related, + [key]: newEntry + } + }); + } + } + } + this._setAssetInfo(file, undefined, assetInfo); + this._setAssetInfo(newFile, assetInfo); + delete this.assets[file]; + this.assets[newFile] = source; + for (const chunk of this.chunks) { + { + const size = chunk.files.size; + chunk.files.delete(file); + if (size !== chunk.files.size) { + chunk.files.add(newFile); + } + } + { + const size = chunk.auxiliaryFiles.size; + chunk.auxiliaryFiles.delete(file); + if (size !== chunk.auxiliaryFiles.size) { + chunk.auxiliaryFiles.add(newFile); + } + } + } } -} - -makeSerializable(ContextModule, "webpack/lib/ContextModule"); - -module.exports = ContextModule; - - -/***/ }), - -/***/ 26268: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ + /** + * @param {string} file file name + */ + deleteAsset(file) { + if (!this.assets[file]) { + return; + } + delete this.assets[file]; + const assetInfo = this.assetsInfo.get(file); + this._setAssetInfo(file, undefined, assetInfo); + const related = assetInfo && assetInfo.related; + if (related) { + for (const key of Object.keys(related)) { + const checkUsedAndDelete = file => { + if (!this._assetsRelatedIn.has(file)) { + this.deleteAsset(file); + } + }; + const items = related[key]; + if (Array.isArray(items)) { + items.forEach(checkUsedAndDelete); + } else if (items) { + checkUsedAndDelete(items); + } + } + } + // TODO If this becomes a performance problem + // store a reverse mapping from asset to chunk + for (const chunk of this.chunks) { + chunk.files.delete(file); + chunk.auxiliaryFiles.delete(file); + } + } + getAssets() { + /** @type {Readonly[]} */ + const array = []; + for (const assetName of Object.keys(this.assets)) { + if (Object.prototype.hasOwnProperty.call(this.assets, assetName)) { + array.push({ + name: assetName, + source: this.assets[assetName], + info: this.assetsInfo.get(assetName) || EMPTY_ASSET_INFO + }); + } + } + return array; + } -const asyncLib = __webpack_require__(36386); -const { AsyncSeriesWaterfallHook, SyncWaterfallHook } = __webpack_require__(34718); -const ContextModule = __webpack_require__(80207); -const ModuleFactory = __webpack_require__(61574); -const ContextElementDependency = __webpack_require__(83853); -const LazySet = __webpack_require__(59534); -const { cachedSetProperty } = __webpack_require__(11217); -const { createFakeHook } = __webpack_require__(2594); -const { join } = __webpack_require__(93204); + /** + * @param {string} name the name of the asset + * @returns {Readonly | undefined} the asset or undefined when not found + */ + getAsset(name) { + if (!Object.prototype.hasOwnProperty.call(this.assets, name)) + return undefined; + return { + name, + source: this.assets[name], + info: this.assetsInfo.get(name) || EMPTY_ASSET_INFO + }; + } -/** @typedef {import("./ContextModule").ContextModuleOptions} ContextModuleOptions */ -/** @typedef {import("./ContextModule").ResolveDependenciesCallback} ResolveDependenciesCallback */ -/** @typedef {import("./Module")} Module */ -/** @typedef {import("./ModuleFactory").ModuleFactoryCreateData} ModuleFactoryCreateData */ -/** @typedef {import("./ModuleFactory").ModuleFactoryResult} ModuleFactoryResult */ -/** @typedef {import("./ResolverFactory")} ResolverFactory */ -/** @typedef {import("./dependencies/ContextDependency")} ContextDependency */ -/** @template T @typedef {import("./util/deprecation").FakeHook} FakeHook */ -/** @typedef {import("./util/fs").InputFileSystem} InputFileSystem */ + clearAssets() { + for (const chunk of this.chunks) { + chunk.files.clear(); + chunk.auxiliaryFiles.clear(); + } + } -const EMPTY_RESOLVE_OPTIONS = {}; + createModuleAssets() { + const { chunkGraph } = this; + for (const module of this.modules) { + if (module.buildInfo.assets) { + const assetsInfo = module.buildInfo.assetsInfo; + for (const assetName of Object.keys(module.buildInfo.assets)) { + const fileName = this.getPath(assetName, { + chunkGraph: this.chunkGraph, + module + }); + for (const chunk of chunkGraph.getModuleChunksIterable(module)) { + chunk.auxiliaryFiles.add(fileName); + } + this.emitAsset( + fileName, + module.buildInfo.assets[assetName], + assetsInfo ? assetsInfo.get(assetName) : undefined + ); + this.hooks.moduleAsset.call(module, fileName); + } + } + } + } -module.exports = class ContextModuleFactory extends ModuleFactory { /** - * @param {ResolverFactory} resolverFactory resolverFactory + * @param {RenderManifestOptions} options options object + * @returns {RenderManifestEntry[]} manifest entries */ - constructor(resolverFactory) { - super(); - /** @type {AsyncSeriesWaterfallHook<[TODO[], ContextModuleOptions]>} */ - const alternativeRequests = new AsyncSeriesWaterfallHook([ - "modules", - "options" - ]); - this.hooks = Object.freeze({ - /** @type {AsyncSeriesWaterfallHook<[TODO]>} */ - beforeResolve: new AsyncSeriesWaterfallHook(["data"]), - /** @type {AsyncSeriesWaterfallHook<[TODO]>} */ - afterResolve: new AsyncSeriesWaterfallHook(["data"]), - /** @type {SyncWaterfallHook<[string[]]>} */ - contextModuleFiles: new SyncWaterfallHook(["files"]), - /** @type {FakeHook, "tap" | "tapAsync" | "tapPromise" | "name">>} */ - alternatives: createFakeHook( - { - name: "alternatives", - /** @type {AsyncSeriesWaterfallHook<[TODO[]]>["intercept"]} */ - intercept: interceptor => { - throw new Error( - "Intercepting fake hook ContextModuleFactory.hooks.alternatives is not possible, use ContextModuleFactory.hooks.alternativeRequests instead" - ); - }, - /** @type {AsyncSeriesWaterfallHook<[TODO[]]>["tap"]} */ - tap: (options, fn) => { - alternativeRequests.tap(options, fn); - }, - /** @type {AsyncSeriesWaterfallHook<[TODO[]]>["tapAsync"]} */ - tapAsync: (options, fn) => { - alternativeRequests.tapAsync(options, (items, _options, callback) => - fn(items, callback) - ); - }, - /** @type {AsyncSeriesWaterfallHook<[TODO[]]>["tapPromise"]} */ - tapPromise: (options, fn) => { - alternativeRequests.tapPromise(options, fn); - } - }, - "ContextModuleFactory.hooks.alternatives has deprecated in favor of ContextModuleFactory.hooks.alternativeRequests with an additional options argument.", - "DEP_WEBPACK_CONTEXT_MODULE_FACTORY_ALTERNATIVES" - ), - alternativeRequests - }); - this.resolverFactory = resolverFactory; + getRenderManifest(options) { + return this.hooks.renderManifest.call([], options); } /** - * @param {ModuleFactoryCreateData} data data object - * @param {function(Error=, ModuleFactoryResult=): void} callback callback + * @param {Callback} callback signals when the call finishes * @returns {void} */ - create(data, callback) { - const context = data.context; - const dependencies = data.dependencies; - const resolveOptions = data.resolveOptions; - const dependency = /** @type {ContextDependency} */ (dependencies[0]); - const fileDependencies = new LazySet(); - const missingDependencies = new LazySet(); - const contextDependencies = new LazySet(); - this.hooks.beforeResolve.callAsync( - { - context: context, - dependencies: dependencies, - resolveOptions, - fileDependencies, - missingDependencies, - contextDependencies, - ...dependency.options - }, - (err, beforeResolveResult) => { - if (err) { - return callback(err, { - fileDependencies, - missingDependencies, - contextDependencies - }); - } + createChunkAssets(callback) { + const outputOptions = this.outputOptions; + const cachedSourceMap = new WeakMap(); + /** @type {Map} */ + const alreadyWrittenFiles = new Map(); - // Ignored - if (!beforeResolveResult) { - return callback(null, { - fileDependencies, - missingDependencies, - contextDependencies + asyncLib.forEachLimit( + this.chunks, + 15, + (chunk, callback) => { + /** @type {RenderManifestEntry[]} */ + let manifest; + try { + manifest = this.getRenderManifest({ + chunk, + hash: this.hash, + fullHash: this.fullHash, + outputOptions, + codeGenerationResults: this.codeGenerationResults, + moduleTemplates: this.moduleTemplates, + dependencyTemplates: this.dependencyTemplates, + chunkGraph: this.chunkGraph, + moduleGraph: this.moduleGraph, + runtimeTemplate: this.runtimeTemplate }); + } catch (err) { + this.errors.push(new ChunkRenderError(chunk, "", err)); + return callback(); } + asyncLib.forEach( + manifest, + (fileManifest, callback) => { + const ident = fileManifest.identifier; + const usedHash = fileManifest.hash; - const context = beforeResolveResult.context; - const request = beforeResolveResult.request; - const resolveOptions = beforeResolveResult.resolveOptions; + const assetCacheItem = this._assetsCache.getItemCache( + ident, + usedHash + ); - let loaders, - resource, - loadersPrefix = ""; - const idx = request.lastIndexOf("!"); - if (idx >= 0) { - let loadersRequest = request.substr(0, idx + 1); - let i; - for ( - i = 0; - i < loadersRequest.length && loadersRequest[i] === "!"; - i++ - ) { - loadersPrefix += "!"; - } - loadersRequest = loadersRequest - .substr(i) - .replace(/!+$/, "") - .replace(/!!+/g, "!"); - if (loadersRequest === "") { - loaders = []; - } else { - loaders = loadersRequest.split("!"); - } - resource = request.substr(idx + 1); - } else { - loaders = []; - resource = request; - } + assetCacheItem.get((err, sourceFromCache) => { + /** @type {string | function(PathData, AssetInfo=): string} */ + let filenameTemplate; + /** @type {string} */ + let file; + /** @type {AssetInfo} */ + let assetInfo; - const contextResolver = this.resolverFactory.get( - "context", - dependencies.length > 0 - ? cachedSetProperty( - resolveOptions || EMPTY_RESOLVE_OPTIONS, - "dependencyType", - dependencies[0].category - ) - : resolveOptions - ); - const loaderResolver = this.resolverFactory.get("loader"); + let inTry = true; + const errorAndCallback = err => { + const filename = + file || + (typeof file === "string" + ? file + : typeof filenameTemplate === "string" + ? filenameTemplate + : ""); - asyncLib.parallel( - [ - callback => { - contextResolver.resolve( - {}, - context, - resource, - { - fileDependencies, - missingDependencies, - contextDependencies - }, - (err, result) => { - if (err) return callback(err); - callback(null, result); - } - ); - }, - callback => { - asyncLib.map( - loaders, - (loader, callback) => { - loaderResolver.resolve( - {}, - context, - loader, - { - fileDependencies, - missingDependencies, - contextDependencies - }, - (err, result) => { - if (err) return callback(err); - callback(null, result); - } - ); - }, - callback - ); - } - ], - (err, result) => { - if (err) { - return callback(err, { - fileDependencies, - missingDependencies, - contextDependencies - }); - } + this.errors.push(new ChunkRenderError(chunk, filename, err)); + inTry = false; + return callback(); + }; - this.hooks.afterResolve.callAsync( - { - addon: - loadersPrefix + - result[1].join("!") + - (result[1].length > 0 ? "!" : ""), - resource: result[0], - resolveDependencies: this.resolveDependencies.bind(this), - ...beforeResolveResult - }, - (err, result) => { - if (err) { - return callback(err, { - fileDependencies, - missingDependencies, - contextDependencies - }); + try { + if ("filename" in fileManifest) { + file = fileManifest.filename; + assetInfo = fileManifest.info; + } else { + filenameTemplate = fileManifest.filenameTemplate; + const pathAndInfo = this.getPathWithInfo( + filenameTemplate, + fileManifest.pathOptions + ); + file = pathAndInfo.path; + assetInfo = fileManifest.info + ? { + ...pathAndInfo.info, + ...fileManifest.info + } + : pathAndInfo.info; } - // Ignored - if (!result) { - return callback(null, { - fileDependencies, - missingDependencies, - contextDependencies - }); + if (err) { + return errorAndCallback(err); } - return callback(null, { - module: new ContextModule(result.resolveDependencies, result), - fileDependencies, - missingDependencies, - contextDependencies - }); - } - ); - } - ); - } - ); - } + let source = sourceFromCache; - /** - * @param {InputFileSystem} fs file system - * @param {ContextModuleOptions} options options - * @param {ResolveDependenciesCallback} callback callback function - * @returns {void} - */ - resolveDependencies(fs, options, callback) { - const cmf = this; - const { - resource, - resourceQuery, - resourceFragment, - recursive, - regExp, - include, - exclude, - referencedExports, - category, - typePrefix - } = options; - if (!regExp || !resource) return callback(null, []); - - const addDirectoryChecked = (directory, visited, callback) => { - fs.realpath(directory, (err, realPath) => { - if (err) return callback(err); - if (visited.has(realPath)) return callback(null, []); - let recursionStack; - addDirectory( - directory, - (dir, callback) => { - if (recursionStack === undefined) { - recursionStack = new Set(visited); - recursionStack.add(realPath); - } - addDirectoryChecked(dir, recursionStack, callback); - }, - callback - ); - }); - }; - - const addDirectory = (directory, addSubDirectory, callback) => { - fs.readdir(directory, (err, files) => { - if (err) return callback(err); - const processedFiles = cmf.hooks.contextModuleFiles.call( - /** @type {string[]} */ (files).map(file => file.normalize("NFC")) - ); - if (!processedFiles || processedFiles.length === 0) - return callback(null, []); - asyncLib.map( - processedFiles.filter(p => p.indexOf(".") !== 0), - (segment, callback) => { - const subResource = join(fs, directory, segment); - - if (!exclude || !subResource.match(exclude)) { - fs.stat(subResource, (err, stat) => { - if (err) { - if (err.code === "ENOENT") { - // ENOENT is ok here because the file may have been deleted between - // the readdir and stat calls. - return callback(); + // check if the same filename was already written by another chunk + const alreadyWritten = alreadyWrittenFiles.get(file); + if (alreadyWritten !== undefined) { + if (alreadyWritten.hash !== usedHash) { + inTry = false; + return callback( + new WebpackError( + `Conflict: Multiple chunks emit assets to the same filename ${file}` + + ` (chunks ${alreadyWritten.chunk.id} and ${chunk.id})` + ) + ); } else { - return callback(err); + source = alreadyWritten.source; } - } - - if (stat.isDirectory()) { - if (!recursive) return callback(); - addSubDirectory(subResource, callback); - } else if ( - stat.isFile() && - (!include || subResource.match(include)) - ) { - const obj = { - context: resource, - request: - "." + - subResource.substr(resource.length).replace(/\\/g, "/") - }; + } else if (!source) { + // render the asset + source = fileManifest.render(); - this.hooks.alternativeRequests.callAsync( - [obj], - options, - (err, alternatives) => { - if (err) return callback(err); - alternatives = alternatives - .filter(obj => regExp.test(obj.request)) - .map(obj => { - const dep = new ContextElementDependency( - obj.request + resourceQuery + resourceFragment, - obj.request, - typePrefix, - category, - referencedExports - ); - dep.optional = true; - return dep; - }); - callback(null, alternatives); + // Ensure that source is a cached source to avoid additional cost because of repeated access + if (!(source instanceof CachedSource)) { + const cacheEntry = cachedSourceMap.get(source); + if (cacheEntry) { + source = cacheEntry; + } else { + const cachedSource = new CachedSource(source); + cachedSourceMap.set(source, cachedSource); + source = cachedSource; } - ); + } + } + this.emitAsset(file, source, assetInfo); + if (fileManifest.auxiliary) { + chunk.auxiliaryFiles.add(file); + } else { + chunk.files.add(file); + } + this.hooks.chunkAsset.call(chunk, file); + alreadyWrittenFiles.set(file, { + hash: usedHash, + source, + chunk + }); + if (source !== sourceFromCache) { + assetCacheItem.store(source, err => { + if (err) return errorAndCallback(err); + inTry = false; + return callback(); + }); } else { + inTry = false; callback(); } - }); - } else { - callback(); - } + } catch (err) { + if (!inTry) throw err; + errorAndCallback(err); + } + }); }, - (err, result) => { - if (err) return callback(err); - - if (!result) return callback(null, []); - - const flattenedResult = []; - - for (const item of result) { - if (item) flattenedResult.push(...item); - } - - callback(null, flattenedResult); - } + callback ); - }); - }; - - if (typeof fs.realpath === "function") { - addDirectoryChecked(resource, new Set(), callback); - } else { - const addSubDirectory = (dir, callback) => - addDirectory(dir, addSubDirectory, callback); - addDirectory(resource, addSubDirectory, callback); - } + }, + callback + ); } -}; - - -/***/ }), - -/***/ 21542: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ - - - -const ContextElementDependency = __webpack_require__(83853); -const { join } = __webpack_require__(93204); - -class ContextReplacementPlugin { - constructor( - resourceRegExp, - newContentResource, - newContentRecursive, - newContentRegExp - ) { - this.resourceRegExp = resourceRegExp; - if (typeof newContentResource === "function") { - this.newContentCallback = newContentResource; - } else if ( - typeof newContentResource === "string" && - typeof newContentRecursive === "object" - ) { - this.newContentResource = newContentResource; - this.newContentCreateContextMap = (fs, callback) => { - callback(null, newContentRecursive); + /** + * @param {string | function(PathData, AssetInfo=): string} filename used to get asset path with hash + * @param {PathData} data context data + * @returns {string} interpolated path + */ + getPath(filename, data = {}) { + if (!data.hash) { + data = { + hash: this.hash, + ...data }; - } else if ( - typeof newContentResource === "string" && - typeof newContentRecursive === "function" - ) { - this.newContentResource = newContentResource; - this.newContentCreateContextMap = newContentRecursive; - } else { - if (typeof newContentResource !== "string") { - newContentRegExp = newContentRecursive; - newContentRecursive = newContentResource; - newContentResource = undefined; - } - if (typeof newContentRecursive !== "boolean") { - newContentRegExp = newContentRecursive; - newContentRecursive = undefined; - } - this.newContentResource = newContentResource; - this.newContentRecursive = newContentRecursive; - this.newContentRegExp = newContentRegExp; } + return this.getAssetPath(filename, data); } - apply(compiler) { - const resourceRegExp = this.resourceRegExp; - const newContentCallback = this.newContentCallback; - const newContentResource = this.newContentResource; - const newContentRecursive = this.newContentRecursive; - const newContentRegExp = this.newContentRegExp; - const newContentCreateContextMap = this.newContentCreateContextMap; - - compiler.hooks.contextModuleFactory.tap("ContextReplacementPlugin", cmf => { - cmf.hooks.beforeResolve.tap("ContextReplacementPlugin", result => { - if (!result) return; - if (resourceRegExp.test(result.request)) { - if (newContentResource !== undefined) { - result.request = newContentResource; - } - if (newContentRecursive !== undefined) { - result.recursive = newContentRecursive; - } - if (newContentRegExp !== undefined) { - result.regExp = newContentRegExp; - } - if (typeof newContentCallback === "function") { - newContentCallback(result); - } else { - for (const d of result.dependencies) { - if (d.critical) d.critical = false; - } - } - } - return result; - }); - cmf.hooks.afterResolve.tap("ContextReplacementPlugin", result => { - if (!result) return; - if (resourceRegExp.test(result.resource)) { - if (newContentResource !== undefined) { - if ( - newContentResource.startsWith("/") || - (newContentResource.length > 1 && newContentResource[1] === ":") - ) { - result.resource = newContentResource; - } else { - result.resource = join( - compiler.inputFileSystem, - result.resource, - newContentResource - ); - } - } - if (newContentRecursive !== undefined) { - result.recursive = newContentRecursive; - } - if (newContentRegExp !== undefined) { - result.regExp = newContentRegExp; - } - if (typeof newContentCreateContextMap === "function") { - result.resolveDependencies = - createResolveDependenciesFromContextMap( - newContentCreateContextMap - ); - } - if (typeof newContentCallback === "function") { - const origResource = result.resource; - newContentCallback(result); - if ( - result.resource !== origResource && - !result.resource.startsWith("/") && - (result.resource.length <= 1 || result.resource[1] !== ":") - ) { - // When the function changed it to an relative path - result.resource = join( - compiler.inputFileSystem, - origResource, - result.resource - ); - } - } else { - for (const d of result.dependencies) { - if (d.critical) d.critical = false; - } - } - } - return result; - }); - }); - } -} - -const createResolveDependenciesFromContextMap = createContextMap => { - const resolveDependenciesFromContextMap = (fs, options, callback) => { - createContextMap(fs, (err, map) => { - if (err) return callback(err); - const dependencies = Object.keys(map).map(key => { - return new ContextElementDependency( - map[key] + options.resourceQuery + options.resourceFragment, - key, - options.category, - options.referencedExports - ); - }); - callback(null, dependencies); - }); - }; - return resolveDependenciesFromContextMap; -}; - -module.exports = ContextReplacementPlugin; - - -/***/ }), - -/***/ 46754: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ - - - -const RuntimeGlobals = __webpack_require__(49404); -const WebpackError = __webpack_require__(68422); -const ConstDependency = __webpack_require__(60864); -const BasicEvaluatedExpression = __webpack_require__(2412); -const { - evaluateToString, - toConstantDependency -} = __webpack_require__(28723); -const createHash = __webpack_require__(24123); - -/** @typedef {import("estree").Expression} Expression */ -/** @typedef {import("./Compiler")} Compiler */ -/** @typedef {import("./NormalModule")} NormalModule */ -/** @typedef {import("./RuntimeTemplate")} RuntimeTemplate */ -/** @typedef {import("./javascript/JavascriptParser")} JavascriptParser */ - -/** @typedef {null|undefined|RegExp|Function|string|number|boolean|bigint|undefined} CodeValuePrimitive */ -/** @typedef {RecursiveArrayOrRecord} CodeValue */ - -/** - * @typedef {Object} RuntimeValueOptions - * @property {string[]=} fileDependencies - * @property {string[]=} contextDependencies - * @property {string[]=} missingDependencies - * @property {string[]=} buildDependencies - * @property {string|function(): string=} version - */ - -class RuntimeValue { /** - * @param {function({ module: NormalModule, key: string, readonly version: string | undefined }): CodeValuePrimitive} fn generator function - * @param {true | string[] | RuntimeValueOptions=} options options + * @param {string | function(PathData, AssetInfo=): string} filename used to get asset path with hash + * @param {PathData} data context data + * @returns {{ path: string, info: AssetInfo }} interpolated path and asset info */ - constructor(fn, options) { - this.fn = fn; - if (Array.isArray(options)) { - options = { - fileDependencies: options + getPathWithInfo(filename, data = {}) { + if (!data.hash) { + data = { + hash: this.hash, + ...data }; } - this.options = options || {}; + return this.getAssetPathWithInfo(filename, data); } - get fileDependencies() { - return this.options === true ? true : this.options.fileDependencies; + /** + * @param {string | function(PathData, AssetInfo=): string} filename used to get asset path with hash + * @param {PathData} data context data + * @returns {string} interpolated path + */ + getAssetPath(filename, data) { + return this.hooks.assetPath.call( + typeof filename === "function" ? filename(data) : filename, + data, + undefined + ); } /** - * @param {JavascriptParser} parser the parser - * @param {Map>} valueCacheVersions valueCacheVersions - * @param {string} key the defined key - * @returns {CodeValuePrimitive} code + * @param {string | function(PathData, AssetInfo=): string} filename used to get asset path with hash + * @param {PathData} data context data + * @returns {{ path: string, info: AssetInfo }} interpolated path and asset info */ - exec(parser, valueCacheVersions, key) { - const buildInfo = parser.state.module.buildInfo; - if (this.options === true) { - buildInfo.cacheable = false; - } else { - if (this.options.fileDependencies) { - for (const dep of this.options.fileDependencies) { - buildInfo.fileDependencies.add(dep); - } - } - if (this.options.contextDependencies) { - for (const dep of this.options.contextDependencies) { - buildInfo.contextDependencies.add(dep); - } - } - if (this.options.missingDependencies) { - for (const dep of this.options.missingDependencies) { - buildInfo.missingDependencies.add(dep); - } - } - if (this.options.buildDependencies) { - for (const dep of this.options.buildDependencies) { - buildInfo.buildDependencies.add(dep); - } - } - } + getAssetPathWithInfo(filename, data) { + const assetInfo = {}; + // TODO webpack 5: refactor assetPath hook to receive { path, info } object + const newPath = this.hooks.assetPath.call( + typeof filename === "function" ? filename(data, assetInfo) : filename, + data, + assetInfo + ); + return { path: newPath, info: assetInfo }; + } - return this.fn({ - module: parser.state.module, - key, - get version() { - return /** @type {string} */ ( - valueCacheVersions.get(VALUE_DEP_PREFIX + key) - ); - } - }); + getWarnings() { + return this.hooks.processWarnings.call(this.warnings); } - getCacheVersion() { - return this.options === true - ? undefined - : (typeof this.options.version === "function" - ? this.options.version() - : this.options.version) || "unset"; + getErrors() { + return this.hooks.processErrors.call(this.errors); } -} -/** - * @param {any[]|{[k: string]: any}} obj obj - * @param {JavascriptParser} parser Parser - * @param {Map>} valueCacheVersions valueCacheVersions - * @param {string} key the defined key - * @param {RuntimeTemplate} runtimeTemplate the runtime template - * @param {boolean|undefined|null=} asiSafe asi safe (undefined: unknown, null: unneeded) - * @returns {string} code converted to string that evaluates - */ -const stringifyObj = ( - obj, - parser, - valueCacheVersions, - key, - runtimeTemplate, - asiSafe -) => { - let code; - let arr = Array.isArray(obj); - if (arr) { - code = `[${obj - .map(code => - toCode(code, parser, valueCacheVersions, key, runtimeTemplate, null) - ) - .join(",")}]`; - } else { - code = `{${Object.keys(obj) - .map(key => { - const code = obj[key]; - return ( - JSON.stringify(key) + - ":" + - toCode(code, parser, valueCacheVersions, key, runtimeTemplate, null) - ); - }) - .join(",")}}`; - } - - switch (asiSafe) { - case null: - return code; - case true: - return arr ? code : `(${code})`; - case false: - return arr ? `;${code}` : `;(${code})`; - default: - return `/*#__PURE__*/Object(${code})`; - } -}; - -/** - * Convert code to a string that evaluates - * @param {CodeValue} code Code to evaluate - * @param {JavascriptParser} parser Parser - * @param {Map>} valueCacheVersions valueCacheVersions - * @param {string} key the defined key - * @param {RuntimeTemplate} runtimeTemplate the runtime template - * @param {boolean|undefined|null=} asiSafe asi safe (undefined: unknown, null: unneeded) - * @returns {string} code converted to string that evaluates - */ -const toCode = ( - code, - parser, - valueCacheVersions, - key, - runtimeTemplate, - asiSafe -) => { - if (code === null) { - return "null"; - } - if (code === undefined) { - return "undefined"; - } - if (Object.is(code, -0)) { - return "-0"; - } - if (code instanceof RuntimeValue) { - return toCode( - code.exec(parser, valueCacheVersions, key), - parser, - valueCacheVersions, - key, - runtimeTemplate, - asiSafe - ); - } - if (code instanceof RegExp && code.toString) { - return code.toString(); - } - if (typeof code === "function" && code.toString) { - return "(" + code.toString() + ")"; - } - if (typeof code === "object") { - return stringifyObj( - code, - parser, - valueCacheVersions, - key, - runtimeTemplate, - asiSafe - ); - } - if (typeof code === "bigint") { - return runtimeTemplate.supportsBigIntLiteral() - ? `${code}n` - : `BigInt("${code}")`; - } - return code + ""; -}; - -const toCacheVersion = code => { - if (code === null) { - return "null"; - } - if (code === undefined) { - return "undefined"; - } - if (Object.is(code, -0)) { - return "-0"; - } - if (code instanceof RuntimeValue) { - return code.getCacheVersion(); - } - if (code instanceof RegExp && code.toString) { - return code.toString(); - } - if (typeof code === "function" && code.toString) { - return "(" + code.toString() + ")"; - } - if (typeof code === "object") { - const items = Object.keys(code).map(key => ({ - key, - value: toCacheVersion(code[key]) - })); - if (items.some(({ value }) => value === undefined)) return undefined; - return `{${items.map(({ key, value }) => `${key}: ${value}`).join(", ")}}`; - } - if (typeof code === "bigint") { - return `${code}n`; - } - return code + ""; -}; - -const VALUE_DEP_PREFIX = "webpack/DefinePlugin "; -const VALUE_DEP_MAIN = "webpack/DefinePlugin_hash"; - -class DefinePlugin { /** - * Create a new define plugin - * @param {Record} definitions A map of global object definitions + * This function allows you to run another instance of webpack inside of webpack however as + * a child with different settings and configurations (if desired) applied. It copies all hooks, plugins + * from parent (or top level compiler) and creates a child Compilation + * + * @param {string} name name of the child compiler + * @param {OutputOptions=} outputOptions // Need to convert config schema to types for this + * @param {Array=} plugins webpack plugins that will be applied + * @returns {Compiler} creates a child Compiler instance */ - constructor(definitions) { - this.definitions = definitions; + createChildCompiler(name, outputOptions, plugins) { + const idx = this.childrenCounters[name] || 0; + this.childrenCounters[name] = idx + 1; + return this.compiler.createChildCompiler( + this, + name, + idx, + outputOptions, + plugins + ); } /** - * @param {function({ module: NormalModule, key: string, readonly version: string | undefined }): CodeValuePrimitive} fn generator function - * @param {true | string[] | RuntimeValueOptions=} options options - * @returns {RuntimeValue} runtime value + * @param {Module} module the module + * @param {ExecuteModuleOptions} options options + * @param {ExecuteModuleCallback} callback callback */ - static runtimeValue(fn, options) { - return new RuntimeValue(fn, options); - } + executeModule(module, options, callback) { + // Aggregate all referenced modules and ensure they are ready + const modules = new Set([module]); + processAsyncTree( + modules, + 10, + /** + * @param {Module} module the module + * @param {function(Module): void} push push more jobs + * @param {Callback} callback callback + * @returns {void} + */ + (module, push, callback) => { + this.buildQueue.waitFor(module, err => { + if (err) return callback(err); + this.processDependenciesQueue.waitFor(module, err => { + if (err) return callback(err); + for (const { module: m } of this.moduleGraph.getOutgoingConnections( + module + )) { + const size = modules.size; + modules.add(m); + if (modules.size !== size) push(m); + } + callback(); + }); + }); + }, + err => { + if (err) return callback(err); - /** - * Apply the plugin - * @param {Compiler} compiler the compiler instance - * @returns {void} - */ - apply(compiler) { - const definitions = this.definitions; - compiler.hooks.compilation.tap( - "DefinePlugin", - (compilation, { normalModuleFactory }) => { - compilation.dependencyTemplates.set( - ConstDependency, - new ConstDependency.Template() + // Create new chunk graph, chunk and entrypoint for the build time execution + const chunkGraph = new ChunkGraph( + this.moduleGraph, + this.outputOptions.hashFunction ); - const { runtimeTemplate } = compilation; + const runtime = "build time"; + const { hashFunction, hashDigest, hashDigestLength } = + this.outputOptions; + const runtimeTemplate = this.runtimeTemplate; - const mainHash = createHash(compilation.outputOptions.hashFunction); - mainHash.update( - /** @type {string} */ ( - compilation.valueCacheVersions.get(VALUE_DEP_MAIN) - ) || "" - ); + const chunk = new Chunk("build time chunk", this._backCompat); + chunk.id = chunk.name; + chunk.ids = [chunk.id]; + chunk.runtime = runtime; + + const entrypoint = new Entrypoint({ + runtime, + chunkLoading: false, + ...options.entryOptions + }); + chunkGraph.connectChunkAndEntryModule(chunk, module, entrypoint); + connectChunkGroupAndChunk(entrypoint, chunk); + entrypoint.setRuntimeChunk(chunk); + entrypoint.setEntrypointChunk(chunk); + + const chunks = new Set([chunk]); + + // Assign ids to modules and modules to the chunk + for (const module of modules) { + const id = module.identifier(); + chunkGraph.setModuleId(module, id); + chunkGraph.connectChunkAndModule(chunk, module); + } + + // Hash modules + for (const module of modules) { + this._createModuleHash( + module, + chunkGraph, + runtime, + hashFunction, + runtimeTemplate, + hashDigest, + hashDigestLength + ); + } + const codeGenerationResults = new CodeGenerationResults( + this.outputOptions.hashFunction + ); + /** @type {WebpackError[]} */ + const errors = []; /** - * Handler - * @param {JavascriptParser} parser Parser + * @param {Module} module the module + * @param {Callback} callback callback * @returns {void} */ - const handler = parser => { - const mainValue = compilation.valueCacheVersions.get(VALUE_DEP_MAIN); - parser.hooks.program.tap("DefinePlugin", () => { - const { buildInfo } = parser.state.module; - if (!buildInfo.valueDependencies) - buildInfo.valueDependencies = new Map(); - buildInfo.valueDependencies.set(VALUE_DEP_MAIN, mainValue); + const codeGen = (module, callback) => { + this._codeGenerationModule( + module, + runtime, + [runtime], + chunkGraph.getModuleHash(module, runtime), + this.dependencyTemplates, + chunkGraph, + this.moduleGraph, + runtimeTemplate, + errors, + codeGenerationResults, + (err, codeGenerated) => { + callback(err); + } + ); + }; + + const reportErrors = () => { + if (errors.length > 0) { + errors.sort( + compareSelect(err => err.module, compareModulesByIdentifier) + ); + for (const error of errors) { + this.errors.push(error); + } + errors.length = 0; + } + }; + + // Generate code for all aggregated modules + asyncLib.eachLimit(modules, 10, codeGen, err => { + if (err) return callback(err); + reportErrors(); + + // for backward-compat temporary set the chunk graph + // TODO webpack 6 + const old = this.chunkGraph; + this.chunkGraph = chunkGraph; + this.processRuntimeRequirements({ + chunkGraph, + modules, + chunks, + codeGenerationResults, + chunkGraphEntries: chunks }); + this.chunkGraph = old; - const addValueDependency = key => { - const { buildInfo } = parser.state.module; - buildInfo.valueDependencies.set( - VALUE_DEP_PREFIX + key, - compilation.valueCacheVersions.get(VALUE_DEP_PREFIX + key) + const runtimeModules = + chunkGraph.getChunkRuntimeModulesIterable(chunk); + + // Hash runtime modules + for (const module of runtimeModules) { + modules.add(module); + this._createModuleHash( + module, + chunkGraph, + runtime, + hashFunction, + runtimeTemplate, + hashDigest, + hashDigestLength ); - }; + } - const withValueDependency = - (key, fn) => - (...args) => { - addValueDependency(key); - return fn(...args); + // Generate code for all runtime modules + asyncLib.eachLimit(runtimeModules, 10, codeGen, err => { + if (err) return callback(err); + reportErrors(); + + /** @type {Map} */ + const moduleArgumentsMap = new Map(); + /** @type {Map} */ + const moduleArgumentsById = new Map(); + + /** @type {ExecuteModuleResult["fileDependencies"]} */ + const fileDependencies = new LazySet(); + /** @type {ExecuteModuleResult["contextDependencies"]} */ + const contextDependencies = new LazySet(); + /** @type {ExecuteModuleResult["missingDependencies"]} */ + const missingDependencies = new LazySet(); + /** @type {ExecuteModuleResult["buildDependencies"]} */ + const buildDependencies = new LazySet(); + + /** @type {ExecuteModuleResult["assets"]} */ + const assets = new Map(); + + let cacheable = true; + + /** @type {ExecuteModuleContext} */ + const context = { + assets, + __webpack_require__: undefined, + chunk, + chunkGraph }; - /** - * Walk definitions - * @param {Object} definitions Definitions map - * @param {string} prefix Prefix string - * @returns {void} - */ - const walkDefinitions = (definitions, prefix) => { - Object.keys(definitions).forEach(key => { - const code = definitions[key]; - if ( - code && - typeof code === "object" && - !(code instanceof RuntimeValue) && - !(code instanceof RegExp) - ) { - walkDefinitions(code, prefix + key + "."); - applyObjectDefine(prefix + key, code); - return; - } - applyDefineKey(prefix, key); - applyDefine(prefix + key, code); - }); - }; + // Prepare execution + asyncLib.eachLimit( + modules, + 10, + (module, callback) => { + const codeGenerationResult = codeGenerationResults.get( + module, + runtime + ); + /** @type {ExecuteModuleArgument} */ + const moduleArgument = { + module, + codeGenerationResult, + preparedInfo: undefined, + moduleObject: undefined + }; + moduleArgumentsMap.set(module, moduleArgument); + moduleArgumentsById.set(module.identifier(), moduleArgument); + module.addCacheDependencies( + fileDependencies, + contextDependencies, + missingDependencies, + buildDependencies + ); + if (module.buildInfo.cacheable === false) { + cacheable = false; + } + if (module.buildInfo && module.buildInfo.assets) { + const { assets: moduleAssets, assetsInfo } = module.buildInfo; + for (const assetName of Object.keys(moduleAssets)) { + assets.set(assetName, { + source: moduleAssets[assetName], + info: assetsInfo ? assetsInfo.get(assetName) : undefined + }); + } + } + this.hooks.prepareModuleExecution.callAsync( + moduleArgument, + context, + callback + ); + }, + err => { + if (err) return callback(err); - /** - * Apply define key - * @param {string} prefix Prefix - * @param {string} key Key - * @returns {void} - */ - const applyDefineKey = (prefix, key) => { - const splittedKey = key.split("."); - splittedKey.slice(1).forEach((_, i) => { - const fullKey = prefix + splittedKey.slice(0, i + 1).join("."); - parser.hooks.canRename.for(fullKey).tap("DefinePlugin", () => { - addValueDependency(key); - return true; - }); - }); - }; + let exports; + try { + const { + strictModuleErrorHandling, + strictModuleExceptionHandling + } = this.outputOptions; + const __nested_webpack_require_150834__ = id => { + const cached = moduleCache[id]; + if (cached !== undefined) { + if (cached.error) throw cached.error; + return cached.exports; + } + const moduleArgument = moduleArgumentsById.get(id); + return __webpack_require_module__(moduleArgument, id); + }; + const interceptModuleExecution = (__nested_webpack_require_150834__[ + RuntimeGlobals.interceptModuleExecution.replace( + "__webpack_require__.", + "" + ) + ] = []); + const moduleCache = (__nested_webpack_require_150834__[ + RuntimeGlobals.moduleCache.replace( + "__webpack_require__.", + "" + ) + ] = {}); + + context.__webpack_require__ = __nested_webpack_require_150834__; - /** - * Apply Code - * @param {string} key Key - * @param {CodeValue} code Code - * @returns {void} - */ - const applyDefine = (key, code) => { - const originalKey = key; - const isTypeof = /^typeof\s+/.test(key); - if (isTypeof) key = key.replace(/^typeof\s+/, ""); - let recurse = false; - let recurseTypeof = false; - if (!isTypeof) { - parser.hooks.canRename.for(key).tap("DefinePlugin", () => { - addValueDependency(originalKey); - return true; - }); - parser.hooks.evaluateIdentifier - .for(key) - .tap("DefinePlugin", expr => { /** - * this is needed in case there is a recursion in the DefinePlugin - * to prevent an endless recursion - * e.g.: new DefinePlugin({ - * "a": "b", - * "b": "a" - * }); + * @param {ExecuteModuleArgument} moduleArgument the module argument + * @param {string=} id id + * @returns {any} exports */ - if (recurse) return; - addValueDependency(originalKey); - recurse = true; - const res = parser.evaluate( - toCode( - code, - parser, - compilation.valueCacheVersions, - key, - runtimeTemplate, - null - ) - ); - recurse = false; - res.setRange(expr.range); - return res; - }); - parser.hooks.expression.for(key).tap("DefinePlugin", expr => { - addValueDependency(originalKey); - const strCode = toCode( - code, - parser, - compilation.valueCacheVersions, - originalKey, - runtimeTemplate, - !parser.isAsiPosition(expr.range[0]) - ); - if (/__webpack_require__\s*(!?\.)/.test(strCode)) { - return toConstantDependency(parser, strCode, [ - RuntimeGlobals.require - ])(expr); - } else if (/__webpack_require__/.test(strCode)) { - return toConstantDependency(parser, strCode, [ - RuntimeGlobals.requireScope - ])(expr); - } else { - return toConstantDependency(parser, strCode)(expr); - } - }); - } - parser.hooks.evaluateTypeof.for(key).tap("DefinePlugin", expr => { - /** - * this is needed in case there is a recursion in the DefinePlugin - * to prevent an endless recursion - * e.g.: new DefinePlugin({ - * "typeof a": "typeof b", - * "typeof b": "typeof a" - * }); - */ - if (recurseTypeof) return; - recurseTypeof = true; - addValueDependency(originalKey); - const codeCode = toCode( - code, - parser, - compilation.valueCacheVersions, - originalKey, - runtimeTemplate, - null - ); - const typeofCode = isTypeof - ? codeCode - : "typeof (" + codeCode + ")"; - const res = parser.evaluate(typeofCode); - recurseTypeof = false; - res.setRange(expr.range); - return res; - }); - parser.hooks.typeof.for(key).tap("DefinePlugin", expr => { - addValueDependency(originalKey); - const codeCode = toCode( - code, - parser, - compilation.valueCacheVersions, - originalKey, - runtimeTemplate, - null - ); - const typeofCode = isTypeof - ? codeCode - : "typeof (" + codeCode + ")"; - const res = parser.evaluate(typeofCode); - if (!res.isString()) return; - return toConstantDependency( - parser, - JSON.stringify(res.string) - ).bind(parser)(expr); - }); - }; + const __webpack_require_module__ = (moduleArgument, id) => { + var execOptions = { + id, + module: { + id, + exports: {}, + loaded: false, + error: undefined + }, + require: __nested_webpack_require_150834__ + }; + interceptModuleExecution.forEach(handler => + handler(execOptions) + ); + const module = moduleArgument.module; + this.buildTimeExecutedModules.add(module); + const moduleObject = execOptions.module; + moduleArgument.moduleObject = moduleObject; + try { + if (id) moduleCache[id] = moduleObject; - /** - * Apply Object - * @param {string} key Key - * @param {Object} obj Object - * @returns {void} - */ - const applyObjectDefine = (key, obj) => { - parser.hooks.canRename.for(key).tap("DefinePlugin", () => { - addValueDependency(key); - return true; - }); - parser.hooks.evaluateIdentifier - .for(key) - .tap("DefinePlugin", expr => { - addValueDependency(key); - return new BasicEvaluatedExpression() - .setTruthy() - .setSideEffects(false) - .setRange(expr.range); - }); - parser.hooks.evaluateTypeof - .for(key) - .tap( - "DefinePlugin", - withValueDependency(key, evaluateToString("object")) - ); - parser.hooks.expression.for(key).tap("DefinePlugin", expr => { - addValueDependency(key); - const strCode = stringifyObj( - obj, - parser, - compilation.valueCacheVersions, - key, - runtimeTemplate, - !parser.isAsiPosition(expr.range[0]) - ); + tryRunOrWebpackError( + () => + this.hooks.executeModule.call( + moduleArgument, + context + ), + "Compilation.hooks.executeModule" + ); + moduleObject.loaded = true; + return moduleObject.exports; + } catch (e) { + if (strictModuleExceptionHandling) { + if (id) delete moduleCache[id]; + } else if (strictModuleErrorHandling) { + moduleObject.error = e; + } + if (!e.module) e.module = module; + throw e; + } + }; - if (/__webpack_require__\s*(!?\.)/.test(strCode)) { - return toConstantDependency(parser, strCode, [ - RuntimeGlobals.require - ])(expr); - } else if (/__webpack_require__/.test(strCode)) { - return toConstantDependency(parser, strCode, [ - RuntimeGlobals.requireScope - ])(expr); - } else { - return toConstantDependency(parser, strCode)(expr); - } - }); - parser.hooks.typeof - .for(key) - .tap( - "DefinePlugin", - withValueDependency( - key, - toConstantDependency(parser, JSON.stringify("object")) - ) - ); - }; + for (const runtimeModule of chunkGraph.getChunkRuntimeModulesInOrder( + chunk + )) { + __webpack_require_module__( + moduleArgumentsMap.get(runtimeModule) + ); + } + exports = __nested_webpack_require_150834__(module.identifier()); + } catch (e) { + const err = new WebpackError( + `Execution of module code from module graph (${module.readableIdentifier( + this.requestShortener + )}) failed: ${e.message}` + ); + err.stack = e.stack; + err.module = e.module; + return callback(err); + } - walkDefinitions(definitions, ""); - }; + callback(null, { + exports, + assets, + cacheable, + fileDependencies, + contextDependencies, + missingDependencies, + buildDependencies + }); + } + ); + }); + }); + } + ); + } - normalModuleFactory.hooks.parser - .for("javascript/auto") - .tap("DefinePlugin", handler); - normalModuleFactory.hooks.parser - .for("javascript/dynamic") - .tap("DefinePlugin", handler); - normalModuleFactory.hooks.parser - .for("javascript/esm") - .tap("DefinePlugin", handler); + checkConstraints() { + const chunkGraph = this.chunkGraph; - /** - * Walk definitions - * @param {Object} definitions Definitions map - * @param {string} prefix Prefix string - * @returns {void} - */ - const walkDefinitionsForValues = (definitions, prefix) => { - Object.keys(definitions).forEach(key => { - const code = definitions[key]; - const version = toCacheVersion(code); - const name = VALUE_DEP_PREFIX + prefix + key; - mainHash.update("|" + prefix + key); - const oldVersion = compilation.valueCacheVersions.get(name); - if (oldVersion === undefined) { - compilation.valueCacheVersions.set(name, version); - } else if (oldVersion !== version) { - const warning = new WebpackError( - `DefinePlugin\nConflicting values for '${prefix + key}'` - ); - warning.details = `'${oldVersion}' !== '${version}'`; - warning.hideStack = true; - compilation.warnings.push(warning); - } - if ( - code && - typeof code === "object" && - !(code instanceof RuntimeValue) && - !(code instanceof RegExp) - ) { - walkDefinitionsForValues(code, prefix + key + "."); - } - }); - }; + /** @type {Set} */ + const usedIds = new Set(); - walkDefinitionsForValues(definitions, ""); + for (const module of this.modules) { + if (module.type === "runtime") continue; + const moduleId = chunkGraph.getModuleId(module); + if (moduleId === null) continue; + if (usedIds.has(moduleId)) { + throw new Error(`checkConstraints: duplicate module id ${moduleId}`); + } + usedIds.add(moduleId); + } - compilation.valueCacheVersions.set( - VALUE_DEP_MAIN, - /** @type {string} */ (mainHash.digest("hex").slice(0, 8)) - ); + for (const chunk of this.chunks) { + for (const module of chunkGraph.getChunkModulesIterable(chunk)) { + if (!this.modules.has(module)) { + throw new Error( + "checkConstraints: module in chunk but not in compilation " + + ` ${chunk.debugId} ${module.debugId}` + ); + } } - ); + for (const module of chunkGraph.getChunkEntryModulesIterable(chunk)) { + if (!this.modules.has(module)) { + throw new Error( + "checkConstraints: entry module in chunk but not in compilation " + + ` ${chunk.debugId} ${module.debugId}` + ); + } + } + } + + for (const chunkGroup of this.chunkGroups) { + chunkGroup.checkConstraints(); + } } } -module.exports = DefinePlugin; + +/** + * @typedef {Object} FactorizeModuleOptions + * @property {ModuleProfile} currentProfile + * @property {ModuleFactory} factory + * @property {Dependency[]} dependencies + * @property {boolean=} factoryResult return full ModuleFactoryResult instead of only module + * @property {Module | null} originModule + * @property {Partial=} contextInfo + * @property {string=} context + */ + +/** + * @param {FactorizeModuleOptions} options options object + * @param {ModuleCallback | ModuleFactoryResultCallback} callback callback + * @returns {void} + */ + +// Workaround for typescript as it doesn't support function overloading in jsdoc within a class +Compilation.prototype.factorizeModule = /** @type {{ + (options: FactorizeModuleOptions & { factoryResult?: false }, callback: ModuleCallback): void; + (options: FactorizeModuleOptions & { factoryResult: true }, callback: ModuleFactoryResultCallback): void; +}} */ ( + function (options, callback) { + this.factorizeQueue.add(options, callback); + } +); + +// Hide from typescript +const compilationPrototype = Compilation.prototype; + +// TODO webpack 6 remove +Object.defineProperty(compilationPrototype, "modifyHash", { + writable: false, + enumerable: false, + configurable: false, + value: () => { + throw new Error( + "Compilation.modifyHash was removed in favor of Compilation.hooks.fullHash" + ); + } +}); + +// TODO webpack 6 remove +Object.defineProperty(compilationPrototype, "cache", { + enumerable: false, + configurable: false, + get: util.deprecate( + /** + * @this {Compilation} the compilation + * @returns {Cache} the cache + */ + function () { + return this.compiler.cache; + }, + "Compilation.cache was removed in favor of Compilation.getCache()", + "DEP_WEBPACK_COMPILATION_CACHE" + ), + set: util.deprecate( + v => {}, + "Compilation.cache was removed in favor of Compilation.getCache()", + "DEP_WEBPACK_COMPILATION_CACHE" + ) +}); + +/** + * Add additional assets to the compilation. + */ +Compilation.PROCESS_ASSETS_STAGE_ADDITIONAL = -2000; + +/** + * Basic preprocessing of assets. + */ +Compilation.PROCESS_ASSETS_STAGE_PRE_PROCESS = -1000; + +/** + * Derive new assets from existing assets. + * Existing assets should not be treated as complete. + */ +Compilation.PROCESS_ASSETS_STAGE_DERIVED = -200; + +/** + * Add additional sections to existing assets, like a banner or initialization code. + */ +Compilation.PROCESS_ASSETS_STAGE_ADDITIONS = -100; + +/** + * Optimize existing assets in a general way. + */ +Compilation.PROCESS_ASSETS_STAGE_OPTIMIZE = 100; + +/** + * Optimize the count of existing assets, e. g. by merging them. + * Only assets of the same type should be merged. + * For assets of different types see PROCESS_ASSETS_STAGE_OPTIMIZE_INLINE. + */ +Compilation.PROCESS_ASSETS_STAGE_OPTIMIZE_COUNT = 200; + +/** + * Optimize the compatibility of existing assets, e. g. add polyfills or vendor-prefixes. + */ +Compilation.PROCESS_ASSETS_STAGE_OPTIMIZE_COMPATIBILITY = 300; + +/** + * Optimize the size of existing assets, e. g. by minimizing or omitting whitespace. + */ +Compilation.PROCESS_ASSETS_STAGE_OPTIMIZE_SIZE = 400; + +/** + * Add development tooling to assets, e. g. by extracting a SourceMap. + */ +Compilation.PROCESS_ASSETS_STAGE_DEV_TOOLING = 500; + +/** + * Optimize the count of existing assets, e. g. by inlining assets of into other assets. + * Only assets of different types should be inlined. + * For assets of the same type see PROCESS_ASSETS_STAGE_OPTIMIZE_COUNT. + */ +Compilation.PROCESS_ASSETS_STAGE_OPTIMIZE_INLINE = 700; + +/** + * Summarize the list of existing assets + * e. g. creating an assets manifest of Service Workers. + */ +Compilation.PROCESS_ASSETS_STAGE_SUMMARIZE = 1000; + +/** + * Optimize the hashes of the assets, e. g. by generating real hashes of the asset content. + */ +Compilation.PROCESS_ASSETS_STAGE_OPTIMIZE_HASH = 2500; + +/** + * Optimize the transfer of existing assets, e. g. by preparing a compressed (gzip) file as separate asset. + */ +Compilation.PROCESS_ASSETS_STAGE_OPTIMIZE_TRANSFER = 3000; + +/** + * Analyse existing assets. + */ +Compilation.PROCESS_ASSETS_STAGE_ANALYSE = 4000; + +/** + * Creating assets for reporting purposes. + */ +Compilation.PROCESS_ASSETS_STAGE_REPORT = 5000; + +module.exports = Compilation; /***/ }), -/***/ 68719: +/***/ 11777: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; @@ -37527,855 +35084,1168 @@ module.exports = DefinePlugin; -const { OriginalSource, RawSource } = __webpack_require__(96192); -const Module = __webpack_require__(85887); -const RuntimeGlobals = __webpack_require__(49404); -const DelegatedSourceDependency = __webpack_require__(82766); -const StaticExportsDependency = __webpack_require__(67967); -const makeSerializable = __webpack_require__(26522); +const parseJson = __webpack_require__(48335); +const asyncLib = __webpack_require__(36386); +const { + SyncHook, + SyncBailHook, + AsyncParallelHook, + AsyncSeriesHook +} = __webpack_require__(34718); +const { SizeOnlySource } = __webpack_require__(96192); +const webpack = __webpack_require__(48169); +const Cache = __webpack_require__(99453); +const CacheFacade = __webpack_require__(67014); +const ChunkGraph = __webpack_require__(97860); +const Compilation = __webpack_require__(59622); +const ConcurrentCompilationError = __webpack_require__(51684); +const ContextModuleFactory = __webpack_require__(26268); +const ModuleGraph = __webpack_require__(20258); +const NormalModuleFactory = __webpack_require__(99063); +const RequestShortener = __webpack_require__(43157); +const ResolverFactory = __webpack_require__(88810); +const Stats = __webpack_require__(87797); +const Watching = __webpack_require__(49819); +const WebpackError = __webpack_require__(68422); +const { Logger } = __webpack_require__(54667); +const { join, dirname, mkdirp } = __webpack_require__(93204); +const { makePathsRelative } = __webpack_require__(96236); +const { isSourceEqual } = __webpack_require__(4002); /** @typedef {import("webpack-sources").Source} Source */ +/** @typedef {import("../declarations/WebpackOptions").EntryNormalized} Entry */ +/** @typedef {import("../declarations/WebpackOptions").OutputNormalized} OutputOptions */ +/** @typedef {import("../declarations/WebpackOptions").WatchOptions} WatchOptions */ /** @typedef {import("../declarations/WebpackOptions").WebpackOptionsNormalized} WebpackOptions */ -/** @typedef {import("./ChunkGraph")} ChunkGraph */ -/** @typedef {import("./Compilation")} Compilation */ -/** @typedef {import("./Dependency").UpdateHashContext} UpdateHashContext */ -/** @typedef {import("./DependencyTemplates")} DependencyTemplates */ -/** @typedef {import("./LibManifestPlugin").ManifestModuleData} ManifestModuleData */ -/** @typedef {import("./Module").CodeGenerationContext} CodeGenerationContext */ -/** @typedef {import("./Module").CodeGenerationResult} CodeGenerationResult */ -/** @typedef {import("./Module").LibIdentOptions} LibIdentOptions */ -/** @typedef {import("./Module").NeedBuildContext} NeedBuildContext */ -/** @typedef {import("./Module").SourceContext} SourceContext */ -/** @typedef {import("./RequestShortener")} RequestShortener */ -/** @typedef {import("./ResolverFactory").ResolverWithOptions} ResolverWithOptions */ -/** @typedef {import("./RuntimeTemplate")} RuntimeTemplate */ -/** @typedef {import("./WebpackError")} WebpackError */ -/** @typedef {import("./dependencies/ModuleDependency")} ModuleDependency */ -/** @typedef {import("./util/Hash")} Hash */ +/** @typedef {import("../declarations/WebpackOptions").WebpackPluginInstance} WebpackPluginInstance */ +/** @typedef {import("./Chunk")} Chunk */ +/** @typedef {import("./Dependency")} Dependency */ +/** @typedef {import("./FileSystemInfo").FileSystemInfoEntry} FileSystemInfoEntry */ +/** @typedef {import("./Module")} Module */ +/** @typedef {import("./util/WeakTupleMap")} WeakTupleMap */ /** @typedef {import("./util/fs").InputFileSystem} InputFileSystem */ +/** @typedef {import("./util/fs").IntermediateFileSystem} IntermediateFileSystem */ +/** @typedef {import("./util/fs").OutputFileSystem} OutputFileSystem */ +/** @typedef {import("./util/fs").WatchFileSystem} WatchFileSystem */ -const TYPES = new Set(["javascript"]); -const RUNTIME_REQUIREMENTS = new Set([ - RuntimeGlobals.module, - RuntimeGlobals.require -]); +/** + * @typedef {Object} CompilationParams + * @property {NormalModuleFactory} normalModuleFactory + * @property {ContextModuleFactory} contextModuleFactory + */ -class DelegatedModule extends Module { - constructor(sourceRequest, data, type, userRequest, originalRequest) { - super("javascript/dynamic", null); +/** + * @template T + * @callback Callback + * @param {Error=} err + * @param {T=} result + */ - // Info from Factory - this.sourceRequest = sourceRequest; - this.request = data.id; - this.delegationType = type; - this.userRequest = userRequest; - this.originalRequest = originalRequest; - /** @type {ManifestModuleData} */ - this.delegateData = data; +/** + * @callback RunAsChildCallback + * @param {Error=} err + * @param {Chunk[]=} entries + * @param {Compilation=} compilation + */ - // Build info - this.delegatedSourceDependency = undefined; - } +/** + * @typedef {Object} AssetEmittedInfo + * @property {Buffer} content + * @property {Source} source + * @property {Compilation} compilation + * @property {string} outputPath + * @property {string} targetPath + */ - /** - * @returns {Set} types available (do not mutate) - */ - getSourceTypes() { - return TYPES; +/** + * @param {string[]} array an array + * @returns {boolean} true, if the array is sorted + */ +const isSorted = array => { + for (let i = 1; i < array.length; i++) { + if (array[i - 1] > array[i]) return false; } + return true; +}; - /** - * @param {LibIdentOptions} options options - * @returns {string | null} an identifier for library inclusion - */ - libIdent(options) { - return typeof this.originalRequest === "string" - ? this.originalRequest - : this.originalRequest.libIdent(options); +/** + * @param {Object} obj an object + * @param {string[]} keys the keys of the object + * @returns {Object} the object with properties sorted by property name + */ +const sortObject = (obj, keys) => { + const o = {}; + for (const k of keys.sort()) { + o[k] = obj[k]; } + return o; +}; - /** - * @returns {string} a unique identifier of the module - */ - identifier() { - return `delegated ${JSON.stringify(this.request)} from ${ - this.sourceRequest - }`; +/** + * @param {string} filename filename + * @param {string | string[] | undefined} hashes list of hashes + * @returns {boolean} true, if the filename contains any hash + */ +const includesHash = (filename, hashes) => { + if (!hashes) return false; + if (Array.isArray(hashes)) { + return hashes.some(hash => filename.includes(hash)); + } else { + return filename.includes(hashes); } +}; +class Compiler { /** - * @param {RequestShortener} requestShortener the request shortener - * @returns {string} a user readable identifier of the module + * @param {string} context the compilation path + * @param {WebpackOptions} options options */ - readableIdentifier(requestShortener) { - return `delegated ${this.userRequest} from ${this.sourceRequest}`; - } + constructor(context, options = /** @type {WebpackOptions} */ ({})) { + this.hooks = Object.freeze({ + /** @type {SyncHook<[]>} */ + initialize: new SyncHook([]), - /** - * @param {NeedBuildContext} context context info - * @param {function(WebpackError=, boolean=): void} callback callback function, returns true, if the module needs a rebuild - * @returns {void} - */ - needBuild(context, callback) { - return callback(null, !this.buildMeta); - } + /** @type {SyncBailHook<[Compilation], boolean>} */ + shouldEmit: new SyncBailHook(["compilation"]), + /** @type {AsyncSeriesHook<[Stats]>} */ + done: new AsyncSeriesHook(["stats"]), + /** @type {SyncHook<[Stats]>} */ + afterDone: new SyncHook(["stats"]), + /** @type {AsyncSeriesHook<[]>} */ + additionalPass: new AsyncSeriesHook([]), + /** @type {AsyncSeriesHook<[Compiler]>} */ + beforeRun: new AsyncSeriesHook(["compiler"]), + /** @type {AsyncSeriesHook<[Compiler]>} */ + run: new AsyncSeriesHook(["compiler"]), + /** @type {AsyncSeriesHook<[Compilation]>} */ + emit: new AsyncSeriesHook(["compilation"]), + /** @type {AsyncSeriesHook<[string, AssetEmittedInfo]>} */ + assetEmitted: new AsyncSeriesHook(["file", "info"]), + /** @type {AsyncSeriesHook<[Compilation]>} */ + afterEmit: new AsyncSeriesHook(["compilation"]), - /** - * @param {WebpackOptions} options webpack options - * @param {Compilation} compilation the compilation - * @param {ResolverWithOptions} resolver the resolver - * @param {InputFileSystem} fs the file system - * @param {function(WebpackError=): void} callback callback function - * @returns {void} - */ - build(options, compilation, resolver, fs, callback) { - this.buildMeta = { ...this.delegateData.buildMeta }; - this.buildInfo = {}; - this.dependencies.length = 0; - this.delegatedSourceDependency = new DelegatedSourceDependency( - this.sourceRequest - ); - this.addDependency(this.delegatedSourceDependency); - this.addDependency( - new StaticExportsDependency(this.delegateData.exports || true, false) - ); - callback(); - } + /** @type {SyncHook<[Compilation, CompilationParams]>} */ + thisCompilation: new SyncHook(["compilation", "params"]), + /** @type {SyncHook<[Compilation, CompilationParams]>} */ + compilation: new SyncHook(["compilation", "params"]), + /** @type {SyncHook<[NormalModuleFactory]>} */ + normalModuleFactory: new SyncHook(["normalModuleFactory"]), + /** @type {SyncHook<[ContextModuleFactory]>} */ + contextModuleFactory: new SyncHook(["contextModuleFactory"]), - /** - * @param {CodeGenerationContext} context context for code generation - * @returns {CodeGenerationResult} result - */ - codeGeneration({ runtimeTemplate, moduleGraph, chunkGraph }) { - const dep = /** @type {DelegatedSourceDependency} */ (this.dependencies[0]); - const sourceModule = moduleGraph.getModule(dep); - let str; + /** @type {AsyncSeriesHook<[CompilationParams]>} */ + beforeCompile: new AsyncSeriesHook(["params"]), + /** @type {SyncHook<[CompilationParams]>} */ + compile: new SyncHook(["params"]), + /** @type {AsyncParallelHook<[Compilation]>} */ + make: new AsyncParallelHook(["compilation"]), + /** @type {AsyncParallelHook<[Compilation]>} */ + finishMake: new AsyncSeriesHook(["compilation"]), + /** @type {AsyncSeriesHook<[Compilation]>} */ + afterCompile: new AsyncSeriesHook(["compilation"]), - if (!sourceModule) { - str = runtimeTemplate.throwMissingModuleErrorBlock({ - request: this.sourceRequest - }); - } else { - str = `module.exports = (${runtimeTemplate.moduleExports({ - module: sourceModule, - chunkGraph, - request: dep.request, - runtimeRequirements: new Set() - })})`; + /** @type {AsyncSeriesHook<[Compiler]>} */ + watchRun: new AsyncSeriesHook(["compiler"]), + /** @type {SyncHook<[Error]>} */ + failed: new SyncHook(["error"]), + /** @type {SyncHook<[string | null, number]>} */ + invalid: new SyncHook(["filename", "changeTime"]), + /** @type {SyncHook<[]>} */ + watchClose: new SyncHook([]), + /** @type {AsyncSeriesHook<[]>} */ + shutdown: new AsyncSeriesHook([]), - switch (this.delegationType) { - case "require": - str += `(${JSON.stringify(this.request)})`; - break; - case "object": - str += `[${JSON.stringify(this.request)}]`; - break; - } + /** @type {SyncBailHook<[string, string, any[]], true>} */ + infrastructureLog: new SyncBailHook(["origin", "type", "args"]), - str += ";"; - } + // TODO the following hooks are weirdly located here + // TODO move them for webpack 5 + /** @type {SyncHook<[]>} */ + environment: new SyncHook([]), + /** @type {SyncHook<[]>} */ + afterEnvironment: new SyncHook([]), + /** @type {SyncHook<[Compiler]>} */ + afterPlugins: new SyncHook(["compiler"]), + /** @type {SyncHook<[Compiler]>} */ + afterResolvers: new SyncHook(["compiler"]), + /** @type {SyncBailHook<[string, Entry], boolean>} */ + entryOption: new SyncBailHook(["context", "entry"]) + }); - const sources = new Map(); - if (this.useSourceMap || this.useSimpleSourceMap) { - sources.set("javascript", new OriginalSource(str, this.identifier())); - } else { - sources.set("javascript", new RawSource(str)); - } + this.webpack = webpack; - return { - sources, - runtimeRequirements: RUNTIME_REQUIREMENTS - }; + /** @type {string=} */ + this.name = undefined; + /** @type {Compilation=} */ + this.parentCompilation = undefined; + /** @type {Compiler} */ + this.root = this; + /** @type {string} */ + this.outputPath = ""; + /** @type {Watching} */ + this.watching = undefined; + + /** @type {OutputFileSystem} */ + this.outputFileSystem = null; + /** @type {IntermediateFileSystem} */ + this.intermediateFileSystem = null; + /** @type {InputFileSystem} */ + this.inputFileSystem = null; + /** @type {WatchFileSystem} */ + this.watchFileSystem = null; + + /** @type {string|null} */ + this.recordsInputPath = null; + /** @type {string|null} */ + this.recordsOutputPath = null; + this.records = {}; + /** @type {Set} */ + this.managedPaths = new Set(); + /** @type {Set} */ + this.immutablePaths = new Set(); + + /** @type {ReadonlySet} */ + this.modifiedFiles = undefined; + /** @type {ReadonlySet} */ + this.removedFiles = undefined; + /** @type {ReadonlyMap} */ + this.fileTimestamps = undefined; + /** @type {ReadonlyMap} */ + this.contextTimestamps = undefined; + /** @type {number} */ + this.fsStartTime = undefined; + + /** @type {ResolverFactory} */ + this.resolverFactory = new ResolverFactory(); + + this.infrastructureLogger = undefined; + + this.options = options; + + this.context = context; + + this.requestShortener = new RequestShortener(context, this.root); + + this.cache = new Cache(); + + /** @type {Map, memCache: WeakTupleMap }> | undefined} */ + this.moduleMemCaches = undefined; + + this.compilerPath = ""; + + /** @type {boolean} */ + this.running = false; + + /** @type {boolean} */ + this.idle = false; + + /** @type {boolean} */ + this.watchMode = false; + + this._backCompat = this.options.experiments.backCompat !== false; + + /** @type {Compilation} */ + this._lastCompilation = undefined; + /** @type {NormalModuleFactory} */ + this._lastNormalModuleFactory = undefined; + + /** @private @type {WeakMap }>} */ + this._assetEmittingSourceCache = new WeakMap(); + /** @private @type {Map} */ + this._assetEmittingWrittenFiles = new Map(); + /** @private @type {Set} */ + this._assetEmittingPreviousFiles = new Set(); } /** - * @param {string=} type the source type for which the size should be estimated - * @returns {number} the estimated size of the module (must be non-zero) + * @param {string} name cache name + * @returns {CacheFacade} the cache facade instance */ - size(type) { - return 42; + getCache(name) { + return new CacheFacade( + this.cache, + `${this.compilerPath}${name}`, + this.options.output.hashFunction + ); } /** - * @param {Hash} hash the hash used to track dependencies - * @param {UpdateHashContext} context context - * @returns {void} + * @param {string | (function(): string)} name name of the logger, or function called once to get the logger name + * @returns {Logger} a logger with that name */ - updateHash(hash, context) { - hash.update(this.delegationType); - hash.update(JSON.stringify(this.request)); - super.updateHash(hash, context); + getInfrastructureLogger(name) { + if (!name) { + throw new TypeError( + "Compiler.getInfrastructureLogger(name) called without a name" + ); + } + return new Logger( + (type, args) => { + if (typeof name === "function") { + name = name(); + if (!name) { + throw new TypeError( + "Compiler.getInfrastructureLogger(name) called with a function not returning a name" + ); + } + } + if (this.hooks.infrastructureLog.call(name, type, args) === undefined) { + if (this.infrastructureLogger !== undefined) { + this.infrastructureLogger(name, type, args); + } + } + }, + childName => { + if (typeof name === "function") { + if (typeof childName === "function") { + return this.getInfrastructureLogger(() => { + if (typeof name === "function") { + name = name(); + if (!name) { + throw new TypeError( + "Compiler.getInfrastructureLogger(name) called with a function not returning a name" + ); + } + } + if (typeof childName === "function") { + childName = childName(); + if (!childName) { + throw new TypeError( + "Logger.getChildLogger(name) called with a function not returning a name" + ); + } + } + return `${name}/${childName}`; + }); + } else { + return this.getInfrastructureLogger(() => { + if (typeof name === "function") { + name = name(); + if (!name) { + throw new TypeError( + "Compiler.getInfrastructureLogger(name) called with a function not returning a name" + ); + } + } + return `${name}/${childName}`; + }); + } + } else { + if (typeof childName === "function") { + return this.getInfrastructureLogger(() => { + if (typeof childName === "function") { + childName = childName(); + if (!childName) { + throw new TypeError( + "Logger.getChildLogger(name) called with a function not returning a name" + ); + } + } + return `${name}/${childName}`; + }); + } else { + return this.getInfrastructureLogger(`${name}/${childName}`); + } + } + } + ); } - serialize(context) { - const { write } = context; - // constructor - write(this.sourceRequest); - write(this.delegateData); - write(this.delegationType); - write(this.userRequest); - write(this.originalRequest); - super.serialize(context); + // TODO webpack 6: solve this in a better way + // e.g. move compilation specific info from Modules into ModuleGraph + _cleanupLastCompilation() { + if (this._lastCompilation !== undefined) { + for (const module of this._lastCompilation.modules) { + ChunkGraph.clearChunkGraphForModule(module); + ModuleGraph.clearModuleGraphForModule(module); + module.cleanupForCache(); + } + for (const chunk of this._lastCompilation.chunks) { + ChunkGraph.clearChunkGraphForChunk(chunk); + } + this._lastCompilation = undefined; + } } - static deserialize(context) { - const { read } = context; - const obj = new DelegatedModule( - read(), // sourceRequest - read(), // delegateData - read(), // delegationType - read(), // userRequest - read() // originalRequest - ); - obj.deserialize(context); - return obj; + // TODO webpack 6: solve this in a better way + _cleanupLastNormalModuleFactory() { + if (this._lastNormalModuleFactory !== undefined) { + this._lastNormalModuleFactory.cleanupForCache(); + this._lastNormalModuleFactory = undefined; + } } /** - * Assuming this module is in the cache. Update the (cached) module with - * the fresh module from the factory. Usually updates internal references - * and properties. - * @param {Module} module fresh module - * @returns {void} + * @param {WatchOptions} watchOptions the watcher's options + * @param {Callback} handler signals when the call finishes + * @returns {Watching} a compiler watcher */ - updateCacheModule(module) { - super.updateCacheModule(module); - const m = /** @type {DelegatedModule} */ (module); - this.delegationType = m.delegationType; - this.userRequest = m.userRequest; - this.originalRequest = m.originalRequest; - this.delegateData = m.delegateData; + watch(watchOptions, handler) { + if (this.running) { + return handler(new ConcurrentCompilationError()); + } + + this.running = true; + this.watchMode = true; + this.watching = new Watching(this, watchOptions, handler); + return this.watching; } /** - * Assuming this module is in the cache. Remove internal references to allow freeing some memory. + * @param {Callback} callback signals when the call finishes + * @returns {void} */ - cleanupForCache() { - super.cleanupForCache(); - this.delegateData = undefined; - } -} - -makeSerializable(DelegatedModule, "webpack/lib/DelegatedModule"); - -module.exports = DelegatedModule; + run(callback) { + if (this.running) { + return callback(new ConcurrentCompilationError()); + } + let logger; -/***/ }), + const finalCallback = (err, stats) => { + if (logger) logger.time("beginIdle"); + this.idle = true; + this.cache.beginIdle(); + this.idle = true; + if (logger) logger.timeEnd("beginIdle"); + this.running = false; + if (err) { + this.hooks.failed.call(err); + } + if (callback !== undefined) callback(err, stats); + this.hooks.afterDone.call(stats); + }; -/***/ 50756: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + const startTime = Date.now(); -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ + this.running = true; + const onCompiled = (err, compilation) => { + if (err) return finalCallback(err); + if (this.hooks.shouldEmit.call(compilation) === false) { + compilation.startTime = startTime; + compilation.endTime = Date.now(); + const stats = new Stats(compilation); + this.hooks.done.callAsync(stats, err => { + if (err) return finalCallback(err); + return finalCallback(null, stats); + }); + return; + } -const DelegatedModule = __webpack_require__(68719); + process.nextTick(() => { + logger = compilation.getLogger("webpack.Compiler"); + logger.time("emitAssets"); + this.emitAssets(compilation, err => { + logger.timeEnd("emitAssets"); + if (err) return finalCallback(err); -// options.source -// options.type -// options.context -// options.scope -// options.content -// options.associatedObjectForCache -class DelegatedModuleFactoryPlugin { - constructor(options) { - this.options = options; - options.type = options.type || "require"; - options.extensions = options.extensions || ["", ".js", ".json", ".wasm"]; - } + if (compilation.hooks.needAdditionalPass.call()) { + compilation.needAdditionalPass = true; - apply(normalModuleFactory) { - const scope = this.options.scope; - if (scope) { - normalModuleFactory.hooks.factorize.tapAsync( - "DelegatedModuleFactoryPlugin", - (data, callback) => { - const [dependency] = data.dependencies; - const { request } = dependency; - if (request && request.startsWith(`${scope}/`)) { - const innerRequest = "." + request.substr(scope.length); - let resolved; - if (innerRequest in this.options.content) { - resolved = this.options.content[innerRequest]; - return callback( - null, - new DelegatedModule( - this.options.source, - resolved, - this.options.type, - innerRequest, - request - ) - ); - } - for (let i = 0; i < this.options.extensions.length; i++) { - const extension = this.options.extensions[i]; - const requestPlusExt = innerRequest + extension; - if (requestPlusExt in this.options.content) { - resolved = this.options.content[requestPlusExt]; - return callback( - null, - new DelegatedModule( - this.options.source, - resolved, - this.options.type, - requestPlusExt, - request + extension - ) - ); - } - } - } - return callback(); - } - ); - } else { - normalModuleFactory.hooks.module.tap( - "DelegatedModuleFactoryPlugin", - module => { - const request = module.libIdent(this.options); - if (request) { - if (request in this.options.content) { - const resolved = this.options.content[request]; - return new DelegatedModule( - this.options.source, - resolved, - this.options.type, - request, - module - ); - } - } - return module; - } - ); - } - } -} -module.exports = DelegatedModuleFactoryPlugin; + compilation.startTime = startTime; + compilation.endTime = Date.now(); + logger.time("done hook"); + const stats = new Stats(compilation); + this.hooks.done.callAsync(stats, err => { + logger.timeEnd("done hook"); + if (err) return finalCallback(err); + this.hooks.additionalPass.callAsync(err => { + if (err) return finalCallback(err); + this.compile(onCompiled); + }); + }); + return; + } -/***/ }), + logger.time("emitRecords"); + this.emitRecords(err => { + logger.timeEnd("emitRecords"); + if (err) return finalCallback(err); -/***/ 48248: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + compilation.startTime = startTime; + compilation.endTime = Date.now(); + logger.time("done hook"); + const stats = new Stats(compilation); + this.hooks.done.callAsync(stats, err => { + logger.timeEnd("done hook"); + if (err) return finalCallback(err); + this.cache.storeBuildDependencies( + compilation.buildDependencies, + err => { + if (err) return finalCallback(err); + return finalCallback(null, stats); + } + ); + }); + }); + }); + }); + }; -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ + const run = () => { + this.hooks.beforeRun.callAsync(this, err => { + if (err) return finalCallback(err); + this.hooks.run.callAsync(this, err => { + if (err) return finalCallback(err); + this.readRecords(err => { + if (err) return finalCallback(err); -const DelegatedModuleFactoryPlugin = __webpack_require__(50756); -const DelegatedSourceDependency = __webpack_require__(82766); + this.compile(onCompiled); + }); + }); + }); + }; -/** @typedef {import("./Compiler")} Compiler */ + if (this.idle) { + this.cache.endIdle(err => { + if (err) return finalCallback(err); -class DelegatedPlugin { - constructor(options) { - this.options = options; + this.idle = false; + run(); + }); + } else { + run(); + } } /** - * Apply the plugin - * @param {Compiler} compiler the compiler instance + * @param {RunAsChildCallback} callback signals when the call finishes * @returns {void} */ - apply(compiler) { - compiler.hooks.compilation.tap( - "DelegatedPlugin", - (compilation, { normalModuleFactory }) => { - compilation.dependencyFactories.set( - DelegatedSourceDependency, - normalModuleFactory - ); - } - ); - - compiler.hooks.compile.tap("DelegatedPlugin", ({ normalModuleFactory }) => { - new DelegatedModuleFactoryPlugin({ - associatedObjectForCache: compiler.root, - ...this.options - }).apply(normalModuleFactory); - }); - } -} - -module.exports = DelegatedPlugin; - - -/***/ }), - -/***/ 21484: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ - - + runAsChild(callback) { + const startTime = Date.now(); + this.compile((err, compilation) => { + if (err) return callback(err); -const makeSerializable = __webpack_require__(26522); + this.parentCompilation.children.push(compilation); + for (const { name, source, info } of compilation.getAssets()) { + this.parentCompilation.emitAsset(name, source, info); + } -/** @typedef {import("./AsyncDependenciesBlock")} AsyncDependenciesBlock */ -/** @typedef {import("./ChunkGraph")} ChunkGraph */ -/** @typedef {import("./ChunkGroup")} ChunkGroup */ -/** @typedef {import("./Dependency")} Dependency */ -/** @typedef {import("./Dependency").UpdateHashContext} UpdateHashContext */ -/** @typedef {import("./util/Hash")} Hash */ + const entries = []; + for (const ep of compilation.entrypoints.values()) { + entries.push(...ep.chunks); + } -/** @typedef {(d: Dependency) => boolean} DependencyFilterFunction */ + compilation.startTime = startTime; + compilation.endTime = Date.now(); -class DependenciesBlock { - constructor() { - /** @type {Dependency[]} */ - this.dependencies = []; - /** @type {AsyncDependenciesBlock[]} */ - this.blocks = []; - /** @type {DependenciesBlock} */ - this.parent = undefined; + return callback(null, entries, compilation); + }); } - getRootBlock() { - /** @type {DependenciesBlock} */ - let current = this; - while (current.parent) current = current.parent; - return current; + purgeInputFileSystem() { + if (this.inputFileSystem && this.inputFileSystem.purge) { + this.inputFileSystem.purge(); + } } /** - * Adds a DependencyBlock to DependencyBlock relationship. - * This is used for when a Module has a AsyncDependencyBlock tie (for code-splitting) - * - * @param {AsyncDependenciesBlock} block block being added + * @param {Compilation} compilation the compilation + * @param {Callback} callback signals when the assets are emitted * @returns {void} */ - addBlock(block) { - this.blocks.push(block); - block.parent = this; - } + emitAssets(compilation, callback) { + let outputPath; - /** - * @param {Dependency} dependency dependency being tied to block. - * This is an "edge" pointing to another "node" on module graph. - * @returns {void} - */ - addDependency(dependency) { - this.dependencies.push(dependency); - } + const emitFiles = err => { + if (err) return callback(err); - /** - * @param {Dependency} dependency dependency being removed - * @returns {void} - */ - removeDependency(dependency) { - const idx = this.dependencies.indexOf(dependency); - if (idx >= 0) { - this.dependencies.splice(idx, 1); - } - } + const assets = compilation.getAssets(); + compilation.assets = { ...compilation.assets }; + /** @type {Map} */ + const caseInsensitiveMap = new Map(); + /** @type {Set} */ + const allTargetPaths = new Set(); + asyncLib.forEachLimit( + assets, + 15, + ({ name: file, source, info }, callback) => { + let targetFile = file; + let immutable = info.immutable; + const queryStringIdx = targetFile.indexOf("?"); + if (queryStringIdx >= 0) { + targetFile = targetFile.substr(0, queryStringIdx); + // We may remove the hash, which is in the query string + // So we recheck if the file is immutable + // This doesn't cover all cases, but immutable is only a performance optimization anyway + immutable = + immutable && + (includesHash(targetFile, info.contenthash) || + includesHash(targetFile, info.chunkhash) || + includesHash(targetFile, info.modulehash) || + includesHash(targetFile, info.fullhash)); + } - /** - * Removes all dependencies and blocks - * @returns {void} - */ - clearDependenciesAndBlocks() { - this.dependencies.length = 0; - this.blocks.length = 0; - } + const writeOut = err => { + if (err) return callback(err); + const targetPath = join( + this.outputFileSystem, + outputPath, + targetFile + ); + allTargetPaths.add(targetPath); - /** - * @param {Hash} hash the hash used to track dependencies - * @param {UpdateHashContext} context context - * @returns {void} - */ - updateHash(hash, context) { - for (const dep of this.dependencies) { - dep.updateHash(hash, context); - } - for (const block of this.blocks) { - block.updateHash(hash, context); - } - } + // check if the target file has already been written by this Compiler + const targetFileGeneration = + this._assetEmittingWrittenFiles.get(targetPath); - serialize({ write }) { - write(this.dependencies); - write(this.blocks); - } + // create an cache entry for this Source if not already existing + let cacheEntry = this._assetEmittingSourceCache.get(source); + if (cacheEntry === undefined) { + cacheEntry = { + sizeOnlySource: undefined, + writtenTo: new Map() + }; + this._assetEmittingSourceCache.set(source, cacheEntry); + } - deserialize({ read }) { - this.dependencies = read(); - this.blocks = read(); - for (const block of this.blocks) { - block.parent = this; - } - } -} + let similarEntry; -makeSerializable(DependenciesBlock, "webpack/lib/DependenciesBlock"); + const checkSimilarFile = () => { + const caseInsensitiveTargetPath = targetPath.toLowerCase(); + similarEntry = caseInsensitiveMap.get(caseInsensitiveTargetPath); + if (similarEntry !== undefined) { + const { path: other, source: otherSource } = similarEntry; + if (isSourceEqual(otherSource, source)) { + // Size may or may not be available at this point. + // If it's not available add to "waiting" list and it will be updated once available + if (similarEntry.size !== undefined) { + updateWithReplacementSource(similarEntry.size); + } else { + if (!similarEntry.waiting) similarEntry.waiting = []; + similarEntry.waiting.push({ file, cacheEntry }); + } + alreadyWritten(); + } else { + const err = + new WebpackError(`Prevent writing to file that only differs in casing or query string from already written file. +This will lead to a race-condition and corrupted files on case-insensitive file systems. +${targetPath} +${other}`); + err.file = file; + callback(err); + } + return true; + } else { + caseInsensitiveMap.set( + caseInsensitiveTargetPath, + (similarEntry = { + path: targetPath, + source, + size: undefined, + waiting: undefined + }) + ); + return false; + } + }; -module.exports = DependenciesBlock; + /** + * get the binary (Buffer) content from the Source + * @returns {Buffer} content for the source + */ + const getContent = () => { + if (typeof source.buffer === "function") { + return source.buffer(); + } else { + const bufferOrString = source.source(); + if (Buffer.isBuffer(bufferOrString)) { + return bufferOrString; + } else { + return Buffer.from(bufferOrString, "utf8"); + } + } + }; + const alreadyWritten = () => { + // cache the information that the Source has been already been written to that location + if (targetFileGeneration === undefined) { + const newGeneration = 1; + this._assetEmittingWrittenFiles.set(targetPath, newGeneration); + cacheEntry.writtenTo.set(targetPath, newGeneration); + } else { + cacheEntry.writtenTo.set(targetPath, targetFileGeneration); + } + callback(); + }; -/***/ }), + /** + * Write the file to output file system + * @param {Buffer} content content to be written + * @returns {void} + */ + const doWrite = content => { + this.outputFileSystem.writeFile(targetPath, content, err => { + if (err) return callback(err); -/***/ 50384: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + // information marker that the asset has been emitted + compilation.emittedAssets.add(file); -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ + // cache the information that the Source has been written to that location + const newGeneration = + targetFileGeneration === undefined + ? 1 + : targetFileGeneration + 1; + cacheEntry.writtenTo.set(targetPath, newGeneration); + this._assetEmittingWrittenFiles.set(targetPath, newGeneration); + this.hooks.assetEmitted.callAsync( + file, + { + content, + source, + outputPath, + compilation, + targetPath + }, + callback + ); + }); + }; + const updateWithReplacementSource = size => { + updateFileWithReplacementSource(file, cacheEntry, size); + similarEntry.size = size; + if (similarEntry.waiting !== undefined) { + for (const { file, cacheEntry } of similarEntry.waiting) { + updateFileWithReplacementSource(file, cacheEntry, size); + } + } + }; + const updateFileWithReplacementSource = ( + file, + cacheEntry, + size + ) => { + // Create a replacement resource which only allows to ask for size + // This allows to GC all memory allocated by the Source + // (expect when the Source is stored in any other cache) + if (!cacheEntry.sizeOnlySource) { + cacheEntry.sizeOnlySource = new SizeOnlySource(size); + } + compilation.updateAsset(file, cacheEntry.sizeOnlySource, { + size + }); + }; -const memoize = __webpack_require__(84297); + const processExistingFile = stats => { + // skip emitting if it's already there and an immutable file + if (immutable) { + updateWithReplacementSource(stats.size); + return alreadyWritten(); + } -/** @typedef {import("webpack-sources").Source} Source */ -/** @typedef {import("./ChunkGraph")} ChunkGraph */ -/** @typedef {import("./DependenciesBlock")} DependenciesBlock */ -/** @typedef {import("./DependencyTemplates")} DependencyTemplates */ -/** @typedef {import("./Module")} Module */ -/** @typedef {import("./ModuleGraph")} ModuleGraph */ -/** @typedef {import("./ModuleGraphConnection")} ModuleGraphConnection */ -/** @typedef {import("./ModuleGraphConnection").ConnectionState} ConnectionState */ -/** @typedef {import("./RuntimeTemplate")} RuntimeTemplate */ -/** @typedef {import("./WebpackError")} WebpackError */ -/** @typedef {import("./util/Hash")} Hash */ -/** @typedef {import("./util/runtime").RuntimeSpec} RuntimeSpec */ + const content = getContent(); -/** - * @typedef {Object} UpdateHashContext - * @property {ChunkGraph} chunkGraph - * @property {RuntimeSpec} runtime - * @property {RuntimeTemplate=} runtimeTemplate - */ + updateWithReplacementSource(content.length); -/** - * @typedef {Object} SourcePosition - * @property {number} line - * @property {number=} column - */ + // if it exists and content on disk matches content + // skip writing the same content again + // (to keep mtime and don't trigger watchers) + // for a fast negative match file size is compared first + if (content.length === stats.size) { + compilation.comparedForEmitAssets.add(file); + return this.outputFileSystem.readFile( + targetPath, + (err, existingContent) => { + if ( + err || + !content.equals(/** @type {Buffer} */ (existingContent)) + ) { + return doWrite(content); + } else { + return alreadyWritten(); + } + } + ); + } -/** - * @typedef {Object} RealDependencyLocation - * @property {SourcePosition} start - * @property {SourcePosition=} end - * @property {number=} index - */ + return doWrite(content); + }; -/** - * @typedef {Object} SyntheticDependencyLocation - * @property {string} name - * @property {number=} index - */ + const processMissingFile = () => { + const content = getContent(); -/** @typedef {SyntheticDependencyLocation|RealDependencyLocation} DependencyLocation */ + updateWithReplacementSource(content.length); -/** - * @typedef {Object} ExportSpec - * @property {string} name the name of the export - * @property {boolean=} canMangle can the export be renamed (defaults to true) - * @property {boolean=} terminalBinding is the export a terminal binding that should be checked for export star conflicts - * @property {(string | ExportSpec)[]=} exports nested exports - * @property {ModuleGraphConnection=} from when reexported: from which module - * @property {string[] | null=} export when reexported: from which export - * @property {number=} priority when reexported: with which priority - * @property {boolean=} hidden export is not visible, because another export blends over it - */ + return doWrite(content); + }; -/** - * @typedef {Object} ExportsSpec - * @property {(string | ExportSpec)[] | true | null} exports exported names, true for unknown exports or null for no exports - * @property {Set=} excludeExports when exports = true, list of unaffected exports - * @property {Set=} hideExports list of maybe prior exposed, but now hidden exports - * @property {ModuleGraphConnection=} from when reexported: from which module - * @property {number=} priority when reexported: with which priority - * @property {boolean=} canMangle can the export be renamed (defaults to true) - * @property {boolean=} terminalBinding are the exports terminal bindings that should be checked for export star conflicts - * @property {Module[]=} dependencies module on which the result depends on - */ + // if the target file has already been written + if (targetFileGeneration !== undefined) { + // check if the Source has been written to this target file + const writtenGeneration = cacheEntry.writtenTo.get(targetPath); + if (writtenGeneration === targetFileGeneration) { + // if yes, we may skip writing the file + // if it's already there + // (we assume one doesn't modify files while the Compiler is running, other then removing them) -/** - * @typedef {Object} ReferencedExport - * @property {string[]} name name of the referenced export - * @property {boolean=} canMangle when false, referenced export can not be mangled, defaults to true - */ + if (this._assetEmittingPreviousFiles.has(targetPath)) { + // We assume that assets from the last compilation say intact on disk (they are not removed) + compilation.updateAsset(file, cacheEntry.sizeOnlySource, { + size: cacheEntry.sizeOnlySource.size() + }); -const TRANSITIVE = Symbol("transitive"); + return callback(); + } else { + // Settings immutable will make it accept file content without comparing when file exist + immutable = true; + } + } else if (!immutable) { + if (checkSimilarFile()) return; + // We wrote to this file before which has very likely a different content + // skip comparing and assume content is different for performance + // This case happens often during watch mode. + return processMissingFile(); + } + } -const getIgnoredModule = memoize(() => { - const RawModule = __webpack_require__(82329); - return new RawModule("/* (ignored) */", `ignored`, `(ignored)`); -}); + if (checkSimilarFile()) return; + if (this.options.output.compareBeforeEmit) { + this.outputFileSystem.stat(targetPath, (err, stats) => { + const exists = !err && stats.isFile(); -class Dependency { - constructor() { - /** @type {Module} */ - this._parentModule = undefined; - /** @type {DependenciesBlock} */ - this._parentDependenciesBlock = undefined; - /** @type {number} */ - this._parentDependenciesBlockIndex = -1; - // TODO check if this can be moved into ModuleDependency - /** @type {boolean} */ - this.weak = false; - // TODO check if this can be moved into ModuleDependency - /** @type {boolean} */ - this.optional = false; - this._locSL = 0; - this._locSC = 0; - this._locEL = 0; - this._locEC = 0; - this._locI = undefined; - this._locN = undefined; - this._loc = undefined; + if (exists) { + processExistingFile(stats); + } else { + processMissingFile(); + } + }); + } else { + processMissingFile(); + } + }; + + if (targetFile.match(/\/|\\/)) { + const fs = this.outputFileSystem; + const dir = dirname(fs, join(fs, outputPath, targetFile)); + mkdirp(fs, dir, writeOut); + } else { + writeOut(); + } + }, + err => { + // Clear map to free up memory + caseInsensitiveMap.clear(); + if (err) { + this._assetEmittingPreviousFiles.clear(); + return callback(err); + } + + this._assetEmittingPreviousFiles = allTargetPaths; + + this.hooks.afterEmit.callAsync(compilation, err => { + if (err) return callback(err); + + return callback(); + }); + } + ); + }; + + this.hooks.emit.callAsync(compilation, err => { + if (err) return callback(err); + outputPath = compilation.getPath(this.outputPath, {}); + mkdirp(this.outputFileSystem, outputPath, emitFiles); + }); } /** - * @returns {string} a display name for the type of dependency + * @param {Callback} callback signals when the call finishes + * @returns {void} */ - get type() { - return "unknown"; + emitRecords(callback) { + if (!this.recordsOutputPath) return callback(); + + const writeFile = () => { + this.outputFileSystem.writeFile( + this.recordsOutputPath, + JSON.stringify( + this.records, + (n, value) => { + if ( + typeof value === "object" && + value !== null && + !Array.isArray(value) + ) { + const keys = Object.keys(value); + if (!isSorted(keys)) { + return sortObject(value, keys); + } + } + return value; + }, + 2 + ), + callback + ); + }; + + const recordsOutputPathDirectory = dirname( + this.outputFileSystem, + this.recordsOutputPath + ); + if (!recordsOutputPathDirectory) { + return writeFile(); + } + mkdirp(this.outputFileSystem, recordsOutputPathDirectory, err => { + if (err) return callback(err); + writeFile(); + }); } /** - * @returns {string} a dependency category, typical categories are "commonjs", "amd", "esm" + * @param {Callback} callback signals when the call finishes + * @returns {void} */ - get category() { - return "unknown"; + readRecords(callback) { + if (!this.recordsInputPath) { + this.records = {}; + return callback(); + } + this.inputFileSystem.stat(this.recordsInputPath, err => { + // It doesn't exist + // We can ignore this. + if (err) return callback(); + + this.inputFileSystem.readFile(this.recordsInputPath, (err, content) => { + if (err) return callback(err); + + try { + this.records = parseJson(content.toString("utf-8")); + } catch (e) { + e.message = "Cannot parse records: " + e.message; + return callback(e); + } + + return callback(); + }); + }); } /** - * @returns {DependencyLocation} location + * @param {Compilation} compilation the compilation + * @param {string} compilerName the compiler's name + * @param {number} compilerIndex the compiler's index + * @param {OutputOptions=} outputOptions the output options + * @param {WebpackPluginInstance[]=} plugins the plugins to apply + * @returns {Compiler} a child compiler */ - get loc() { - if (this._loc !== undefined) return this._loc; - /** @type {SyntheticDependencyLocation & RealDependencyLocation} */ - const loc = {}; - if (this._locSL > 0) { - loc.start = { line: this._locSL, column: this._locSC }; - } - if (this._locEL > 0) { - loc.end = { line: this._locEL, column: this._locEC }; - } - if (this._locN !== undefined) { - loc.name = this._locN; - } - if (this._locI !== undefined) { - loc.index = this._locI; - } - return (this._loc = loc); - } + createChildCompiler( + compilation, + compilerName, + compilerIndex, + outputOptions, + plugins + ) { + const childCompiler = new Compiler(this.context, { + ...this.options, + output: { + ...this.options.output, + ...outputOptions + } + }); + childCompiler.name = compilerName; + childCompiler.outputPath = this.outputPath; + childCompiler.inputFileSystem = this.inputFileSystem; + childCompiler.outputFileSystem = null; + childCompiler.resolverFactory = this.resolverFactory; + childCompiler.modifiedFiles = this.modifiedFiles; + childCompiler.removedFiles = this.removedFiles; + childCompiler.fileTimestamps = this.fileTimestamps; + childCompiler.contextTimestamps = this.contextTimestamps; + childCompiler.fsStartTime = this.fsStartTime; + childCompiler.cache = this.cache; + childCompiler.compilerPath = `${this.compilerPath}${compilerName}|${compilerIndex}|`; + childCompiler._backCompat = this._backCompat; - set loc(loc) { - if ("start" in loc && typeof loc.start === "object") { - this._locSL = loc.start.line || 0; - this._locSC = loc.start.column || 0; - } else { - this._locSL = 0; - this._locSC = 0; + const relativeCompilerName = makePathsRelative( + this.context, + compilerName, + this.root + ); + if (!this.records[relativeCompilerName]) { + this.records[relativeCompilerName] = []; } - if ("end" in loc && typeof loc.end === "object") { - this._locEL = loc.end.line || 0; - this._locEC = loc.end.column || 0; + if (this.records[relativeCompilerName][compilerIndex]) { + childCompiler.records = this.records[relativeCompilerName][compilerIndex]; } else { - this._locEL = 0; - this._locEC = 0; + this.records[relativeCompilerName].push((childCompiler.records = {})); } - if ("index" in loc) { - this._locI = loc.index; - } else { - this._locI = undefined; + + childCompiler.parentCompilation = compilation; + childCompiler.root = this.root; + if (Array.isArray(plugins)) { + for (const plugin of plugins) { + plugin.apply(childCompiler); + } } - if ("name" in loc) { - this._locN = loc.name; - } else { - this._locN = undefined; + for (const name in this.hooks) { + if ( + ![ + "make", + "compile", + "emit", + "afterEmit", + "invalid", + "done", + "thisCompilation" + ].includes(name) + ) { + if (childCompiler.hooks[name]) { + childCompiler.hooks[name].taps = this.hooks[name].taps.slice(); + } + } } - this._loc = loc; - } - /** - * @returns {string | null} an identifier to merge equal requests - */ - getResourceIdentifier() { - return null; - } + compilation.hooks.childCompiler.call( + childCompiler, + compilerName, + compilerIndex + ); - /** - * @returns {boolean | TRANSITIVE} true, when changes to the referenced module could affect the referencing module; TRANSITIVE, when changes to the referenced module could affect referencing modules of the referencing module - */ - couldAffectReferencingModule() { - return TRANSITIVE; + return childCompiler; } - /** - * Returns the referenced module and export - * @deprecated - * @param {ModuleGraph} moduleGraph module graph - * @returns {never} throws error - */ - getReference(moduleGraph) { - throw new Error( - "Dependency.getReference was removed in favor of Dependency.getReferencedExports, ModuleGraph.getModule and ModuleGraph.getConnection().active" - ); + isChild() { + return !!this.parentCompilation; } - /** - * Returns list of exports referenced by this dependency - * @param {ModuleGraph} moduleGraph module graph - * @param {RuntimeSpec} runtime the runtime for which the module is analysed - * @returns {(string[] | ReferencedExport)[]} referenced exports - */ - getReferencedExports(moduleGraph, runtime) { - return Dependency.EXPORTS_OBJECT_REFERENCED; + createCompilation(params) { + this._cleanupLastCompilation(); + return (this._lastCompilation = new Compilation(this, params)); } /** - * @param {ModuleGraph} moduleGraph module graph - * @returns {null | false | function(ModuleGraphConnection, RuntimeSpec): ConnectionState} function to determine if the connection is active + * @param {CompilationParams} params the compilation parameters + * @returns {Compilation} the created compilation */ - getCondition(moduleGraph) { - return null; + newCompilation(params) { + const compilation = this.createCompilation(params); + compilation.name = this.name; + compilation.records = this.records; + this.hooks.thisCompilation.call(compilation, params); + this.hooks.compilation.call(compilation, params); + return compilation; } - /** - * Returns the exported names - * @param {ModuleGraph} moduleGraph module graph - * @returns {ExportsSpec | undefined} export names - */ - getExports(moduleGraph) { - return undefined; + createNormalModuleFactory() { + this._cleanupLastNormalModuleFactory(); + const normalModuleFactory = new NormalModuleFactory({ + context: this.options.context, + fs: this.inputFileSystem, + resolverFactory: this.resolverFactory, + options: this.options.module, + associatedObjectForCache: this.root, + layers: this.options.experiments.layers + }); + this._lastNormalModuleFactory = normalModuleFactory; + this.hooks.normalModuleFactory.call(normalModuleFactory); + return normalModuleFactory; } - /** - * Returns warnings - * @param {ModuleGraph} moduleGraph module graph - * @returns {WebpackError[]} warnings - */ - getWarnings(moduleGraph) { - return null; + createContextModuleFactory() { + const contextModuleFactory = new ContextModuleFactory(this.resolverFactory); + this.hooks.contextModuleFactory.call(contextModuleFactory); + return contextModuleFactory; } - /** - * Returns errors - * @param {ModuleGraph} moduleGraph module graph - * @returns {WebpackError[]} errors - */ - getErrors(moduleGraph) { - return null; + newCompilationParams() { + const params = { + normalModuleFactory: this.createNormalModuleFactory(), + contextModuleFactory: this.createContextModuleFactory() + }; + return params; } /** - * Update the hash - * @param {Hash} hash hash to be updated - * @param {UpdateHashContext} context context + * @param {Callback} callback signals when the compilation finishes * @returns {void} */ - updateHash(hash, context) {} - - /** - * implement this method to allow the occurrence order plugin to count correctly - * @returns {number} count how often the id is used in this dependency - */ - getNumberOfIdOccurrences() { - return 1; - } + compile(callback) { + const params = this.newCompilationParams(); + this.hooks.beforeCompile.callAsync(params, err => { + if (err) return callback(err); - /** - * @param {ModuleGraph} moduleGraph the module graph - * @returns {ConnectionState} how this dependency connects the module to referencing modules - */ - getModuleEvaluationSideEffectsState(moduleGraph) { - return true; - } + this.hooks.compile.call(params); - /** - * @param {string} context context directory - * @returns {Module} a module - */ - createIgnoredModule(context) { - return getIgnoredModule(); - } + const compilation = this.newCompilation(params); - serialize({ write }) { - write(this.weak); - write(this.optional); - write(this._locSL); - write(this._locSC); - write(this._locEL); - write(this._locEC); - write(this._locI); - write(this._locN); - } + const logger = compilation.getLogger("webpack.Compiler"); - deserialize({ read }) { - this.weak = read(); - this.optional = read(); - this._locSL = read(); - this._locSC = read(); - this._locEL = read(); - this._locEC = read(); - this._locI = read(); - this._locN = read(); - } -} + logger.time("make hook"); + this.hooks.make.callAsync(compilation, err => { + logger.timeEnd("make hook"); + if (err) return callback(err); -/** @type {string[][]} */ -Dependency.NO_EXPORTS_REFERENCED = []; -/** @type {string[][]} */ -Dependency.EXPORTS_OBJECT_REFERENCED = [[]]; + logger.time("finish make hook"); + this.hooks.finishMake.callAsync(compilation, err => { + logger.timeEnd("finish make hook"); + if (err) return callback(err); -Object.defineProperty(Dependency.prototype, "module", { - /** - * @deprecated - * @returns {never} throws - */ - get() { - throw new Error( - "module property was removed from Dependency (use compilation.moduleGraph.getModule(dependency) instead)" - ); - }, + process.nextTick(() => { + logger.time("finish compilation"); + compilation.finish(err => { + logger.timeEnd("finish compilation"); + if (err) return callback(err); - /** - * @deprecated - * @returns {never} throws - */ - set() { - throw new Error( - "module property was removed from Dependency (use compilation.moduleGraph.updateModule(dependency, module) instead)" - ); - } -}); + logger.time("seal compilation"); + compilation.seal(err => { + logger.timeEnd("seal compilation"); + if (err) return callback(err); -Object.defineProperty(Dependency.prototype, "disconnect", { - get() { - throw new Error( - "disconnect was removed from Dependency (Dependency no longer carries graph specific information)" - ); + logger.time("afterCompile hook"); + this.hooks.afterCompile.callAsync(compilation, err => { + logger.timeEnd("afterCompile hook"); + if (err) return callback(err); + + return callback(null, compilation); + }); + }); + }); + }); + }); + }); + }); } -}); -Dependency.TRANSITIVE = TRANSITIVE; + /** + * @param {Callback} callback signals when the compiler closes + * @returns {void} + */ + close(callback) { + if (this.watching) { + // When there is still an active watching, close this first + this.watching.close(err => { + this.close(callback); + }); + return; + } + this.hooks.shutdown.callAsync(err => { + if (err) return callback(err); + // Get rid of reference to last compilation to avoid leaking memory + // We can't run this._cleanupLastCompilation() as the Stats to this compilation + // might be still in use. We try to get rid of the reference to the cache instead. + this._lastCompilation = undefined; + this._lastNormalModuleFactory = undefined; + this.cache.shutdown(callback); + }); + } +} -module.exports = Dependency; +module.exports = Compiler; /***/ }), -/***/ 17600: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { +/***/ 14067: +/***/ (function(module) { "use strict"; /* @@ -38385,190 +36255,189 @@ module.exports = Dependency; -/** @typedef {import("webpack-sources").ReplaceSource} ReplaceSource */ -/** @typedef {import("./ChunkGraph")} ChunkGraph */ -/** @typedef {import("./ConcatenationScope")} ConcatenationScope */ -/** @typedef {import("./Dependency")} Dependency */ -/** @typedef {import("./Dependency").RuntimeSpec} RuntimeSpec */ -/** @typedef {import("./DependencyTemplates")} DependencyTemplates */ -/** @typedef {import("./Generator").GenerateContext} GenerateContext */ -/** @template T @typedef {import("./InitFragment")} InitFragment */ /** @typedef {import("./Module")} Module */ -/** @typedef {import("./ModuleGraph")} ModuleGraph */ -/** @typedef {import("./RuntimeTemplate")} RuntimeTemplate */ - -/** - * @typedef {Object} DependencyTemplateContext - * @property {RuntimeTemplate} runtimeTemplate the runtime template - * @property {DependencyTemplates} dependencyTemplates the dependency templates - * @property {ModuleGraph} moduleGraph the module graph - * @property {ChunkGraph} chunkGraph the chunk graph - * @property {Set} runtimeRequirements the requirements for runtime - * @property {Module} module current module - * @property {RuntimeSpec} runtime current runtimes, for which code is generated - * @property {InitFragment[]} initFragments mutable array of init fragments for the current module - * @property {ConcatenationScope=} concatenationScope when in a concatenated module, information about other concatenated modules - */ - -class DependencyTemplate { - /* istanbul ignore next */ - /** - * @abstract - * @param {Dependency} dependency the dependency for which the template should be applied - * @param {ReplaceSource} source the current replace source which can be modified - * @param {DependencyTemplateContext} templateContext the context object - * @returns {void} - */ - apply(dependency, source, templateContext) { - const AbstractMethodError = __webpack_require__(570); - throw new AbstractMethodError(); - } -} - -module.exports = DependencyTemplate; +const MODULE_REFERENCE_REGEXP = + /^__WEBPACK_MODULE_REFERENCE__(\d+)_([\da-f]+|ns)(_call)?(_directImport)?(?:_asiSafe(\d))?__$/; -/***/ }), - -/***/ 31002: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { +const DEFAULT_EXPORT = "__WEBPACK_DEFAULT_EXPORT__"; +const NAMESPACE_OBJECT_EXPORT = "__WEBPACK_NAMESPACE_OBJECT__"; -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ +/** + * @typedef {Object} ExternalModuleInfo + * @property {number} index + * @property {Module} module + */ +/** + * @typedef {Object} ConcatenatedModuleInfo + * @property {number} index + * @property {Module} module + * @property {Map} exportMap mapping from export name to symbol + * @property {Map} rawExportMap mapping from export name to symbol + * @property {string=} namespaceExportSymbol + */ +/** @typedef {ConcatenatedModuleInfo | ExternalModuleInfo} ModuleInfo */ -const createHash = __webpack_require__(24123); +/** + * @typedef {Object} ModuleReferenceOptions + * @property {string[]} ids the properties/exports of the module + * @property {boolean} call true, when this referenced export is called + * @property {boolean} directImport true, when this referenced export is directly imported (not via property access) + * @property {boolean | undefined} asiSafe if the position is ASI safe or unknown + */ -/** @typedef {import("./Dependency")} Dependency */ -/** @typedef {import("./DependencyTemplate")} DependencyTemplate */ -/** @typedef {typeof import("./util/Hash")} Hash */ +class ConcatenationScope { + /** + * @param {ModuleInfo[] | Map} modulesMap all module info by module + * @param {ConcatenatedModuleInfo} currentModule the current module info + */ + constructor(modulesMap, currentModule) { + this._currentModule = currentModule; + if (Array.isArray(modulesMap)) { + const map = new Map(); + for (const info of modulesMap) { + map.set(info.module, info); + } + modulesMap = map; + } + this._modulesMap = modulesMap; + } -/** @typedef {new (...args: any[]) => Dependency} DependencyConstructor */ + /** + * @param {Module} module the referenced module + * @returns {boolean} true, when it's in the scope + */ + isModuleInScope(module) { + return this._modulesMap.has(module); + } -class DependencyTemplates { /** - * @param {string | Hash} hashFunction the hash function to use + * + * @param {string} exportName name of the export + * @param {string} symbol identifier of the export in source code */ - constructor(hashFunction = "md4") { - /** @type {Map} */ - this._map = new Map(); - /** @type {string} */ - this._hash = "31d6cfe0d16ae931b73c59d7e0c089c0"; - this._hashFunction = hashFunction; + registerExport(exportName, symbol) { + if (!this._currentModule.exportMap) { + this._currentModule.exportMap = new Map(); + } + if (!this._currentModule.exportMap.has(exportName)) { + this._currentModule.exportMap.set(exportName, symbol); + } } /** - * @param {DependencyConstructor} dependency Constructor of Dependency - * @returns {DependencyTemplate} template for this dependency + * + * @param {string} exportName name of the export + * @param {string} expression expression to be used */ - get(dependency) { - return this._map.get(dependency); + registerRawExport(exportName, expression) { + if (!this._currentModule.rawExportMap) { + this._currentModule.rawExportMap = new Map(); + } + if (!this._currentModule.rawExportMap.has(exportName)) { + this._currentModule.rawExportMap.set(exportName, expression); + } } /** - * @param {DependencyConstructor} dependency Constructor of Dependency - * @param {DependencyTemplate} dependencyTemplate template for this dependency - * @returns {void} + * @param {string} symbol identifier of the export in source code */ - set(dependency, dependencyTemplate) { - this._map.set(dependency, dependencyTemplate); + registerNamespaceExport(symbol) { + this._currentModule.namespaceExportSymbol = symbol; } /** - * @param {string} part additional hash contributor - * @returns {void} + * + * @param {Module} module the referenced module + * @param {Partial} options options + * @returns {string} the reference as identifier */ - updateHash(part) { - const hash = createHash(this._hashFunction); - hash.update(`${this._hash}${part}`); - this._hash = /** @type {string} */ (hash.digest("hex")); + createModuleReference( + module, + { ids = undefined, call = false, directImport = false, asiSafe = false } + ) { + const info = this._modulesMap.get(module); + const callFlag = call ? "_call" : ""; + const directImportFlag = directImport ? "_directImport" : ""; + const asiSafeFlag = asiSafe + ? "_asiSafe1" + : asiSafe === false + ? "_asiSafe0" + : ""; + const exportData = ids + ? Buffer.from(JSON.stringify(ids), "utf-8").toString("hex") + : "ns"; + // a "._" is appended to allow "delete ...", which would cause a SyntaxError in strict mode + return `__WEBPACK_MODULE_REFERENCE__${info.index}_${exportData}${callFlag}${directImportFlag}${asiSafeFlag}__._`; } - getHash() { - return this._hash; + /** + * @param {string} name the identifier + * @returns {boolean} true, when it's an module reference + */ + static isModuleReference(name) { + return MODULE_REFERENCE_REGEXP.test(name); } - clone() { - const newInstance = new DependencyTemplates(); - newInstance._map = new Map(this._map); - newInstance._hash = this._hash; - return newInstance; + /** + * @param {string} name the identifier + * @returns {ModuleReferenceOptions & { index: number }} parsed options and index + */ + static matchModuleReference(name) { + const match = MODULE_REFERENCE_REGEXP.exec(name); + if (!match) return null; + const index = +match[1]; + const asiSafe = match[5]; + return { + index, + ids: + match[2] === "ns" + ? [] + : JSON.parse(Buffer.from(match[2], "hex").toString("utf-8")), + call: !!match[3], + directImport: !!match[4], + asiSafe: asiSafe ? asiSafe === "1" : undefined + }; } } -module.exports = DependencyTemplates; +ConcatenationScope.DEFAULT_EXPORT = DEFAULT_EXPORT; +ConcatenationScope.NAMESPACE_OBJECT_EXPORT = NAMESPACE_OBJECT_EXPORT; + +module.exports = ConcatenationScope; /***/ }), -/***/ 28766: +/***/ 51684: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; /* MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra + Author Maksim Nazarjev @acupofspirt */ -const DllModuleFactory = __webpack_require__(77885); -const DllEntryDependency = __webpack_require__(57839); -const EntryDependency = __webpack_require__(41075); +const WebpackError = __webpack_require__(68422); -class DllEntryPlugin { - constructor(context, entries, options) { - this.context = context; - this.entries = entries; - this.options = options; - } +module.exports = class ConcurrentCompilationError extends WebpackError { + constructor() { + super(); - apply(compiler) { - compiler.hooks.compilation.tap( - "DllEntryPlugin", - (compilation, { normalModuleFactory }) => { - const dllModuleFactory = new DllModuleFactory(); - compilation.dependencyFactories.set( - DllEntryDependency, - dllModuleFactory - ); - compilation.dependencyFactories.set( - EntryDependency, - normalModuleFactory - ); - } - ); - compiler.hooks.make.tapAsync("DllEntryPlugin", (compilation, callback) => { - compilation.addEntry( - this.context, - new DllEntryDependency( - this.entries.map((e, idx) => { - const dep = new EntryDependency(e); - dep.loc = { - name: this.options.name, - index: idx - }; - return dep; - }), - this.options.name - ), - this.options, - callback - ); - }); + this.name = "ConcurrentCompilationError"; + this.message = + "You ran Webpack twice. Each instance only supports a single concurrent compilation at a time."; } -} - -module.exports = DllEntryPlugin; +}; /***/ }), -/***/ 52692: +/***/ 90921: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; @@ -38579,206 +36448,116 @@ module.exports = DllEntryPlugin; -const { RawSource } = __webpack_require__(96192); -const Module = __webpack_require__(85887); -const RuntimeGlobals = __webpack_require__(49404); -const makeSerializable = __webpack_require__(26522); +const { ConcatSource, PrefixSource } = __webpack_require__(96192); +const InitFragment = __webpack_require__(51739); +const Template = __webpack_require__(92066); +const { mergeRuntime } = __webpack_require__(19655); /** @typedef {import("webpack-sources").Source} Source */ -/** @typedef {import("../declarations/WebpackOptions").WebpackOptionsNormalized} WebpackOptions */ -/** @typedef {import("./ChunkGraph")} ChunkGraph */ -/** @typedef {import("./Compilation")} Compilation */ -/** @typedef {import("./Dependency").UpdateHashContext} UpdateHashContext */ -/** @typedef {import("./DependencyTemplates")} DependencyTemplates */ -/** @typedef {import("./Module").CodeGenerationContext} CodeGenerationContext */ -/** @typedef {import("./Module").CodeGenerationResult} CodeGenerationResult */ -/** @typedef {import("./Module").NeedBuildContext} NeedBuildContext */ -/** @typedef {import("./Module").SourceContext} SourceContext */ -/** @typedef {import("./RequestShortener")} RequestShortener */ -/** @typedef {import("./ResolverFactory").ResolverWithOptions} ResolverWithOptions */ -/** @typedef {import("./RuntimeTemplate")} RuntimeTemplate */ -/** @typedef {import("./WebpackError")} WebpackError */ -/** @typedef {import("./util/Hash")} Hash */ -/** @typedef {import("./util/fs").InputFileSystem} InputFileSystem */ - -const TYPES = new Set(["javascript"]); -const RUNTIME_REQUIREMENTS = new Set([ - RuntimeGlobals.require, - RuntimeGlobals.module -]); - -class DllModule extends Module { - constructor(context, dependencies, name) { - super("javascript/dynamic", context); - - // Info from Factory - this.dependencies = dependencies; - this.name = name; - } +/** @typedef {import("./Generator").GenerateContext} GenerateContext */ +/** @typedef {import("./util/runtime").RuntimeSpec} RuntimeSpec */ - /** - * @returns {Set} types available (do not mutate) - */ - getSourceTypes() { - return TYPES; +const wrapInCondition = (condition, source) => { + if (typeof source === "string") { + return Template.asString([ + `if (${condition}) {`, + Template.indent(source), + "}", + "" + ]); + } else { + return new ConcatSource( + `if (${condition}) {\n`, + new PrefixSource("\t", source), + "}\n" + ); } +}; +/** + * @typedef {GenerateContext} Context + */ +class ConditionalInitFragment extends InitFragment { /** - * @returns {string} a unique identifier of the module + * @param {string|Source} content the source code that will be included as initialization code + * @param {number} stage category of initialization code (contribute to order) + * @param {number} position position in the category (contribute to order) + * @param {string} key unique key to avoid emitting the same initialization code twice + * @param {RuntimeSpec | boolean} runtimeCondition in which runtime this fragment should be executed + * @param {string|Source=} endContent the source code that will be included at the end of the module */ - identifier() { - return `dll ${this.name}`; + constructor( + content, + stage, + position, + key, + runtimeCondition = true, + endContent + ) { + super(content, stage, position, key, endContent); + this.runtimeCondition = runtimeCondition; } /** - * @param {RequestShortener} requestShortener the request shortener - * @returns {string} a user readable identifier of the module + * @param {Context} context context + * @returns {string|Source} the source code that will be included as initialization code */ - readableIdentifier(requestShortener) { - return `dll ${this.name}`; + getContent(context) { + if (this.runtimeCondition === false || !this.content) return ""; + if (this.runtimeCondition === true) return this.content; + const expr = context.runtimeTemplate.runtimeConditionExpression({ + chunkGraph: context.chunkGraph, + runtimeRequirements: context.runtimeRequirements, + runtime: context.runtime, + runtimeCondition: this.runtimeCondition + }); + if (expr === "true") return this.content; + return wrapInCondition(expr, this.content); } /** - * @param {WebpackOptions} options webpack options - * @param {Compilation} compilation the compilation - * @param {ResolverWithOptions} resolver the resolver - * @param {InputFileSystem} fs the file system - * @param {function(WebpackError=): void} callback callback function - * @returns {void} + * @param {Context} context context + * @returns {string|Source=} the source code that will be included at the end of the module */ - build(options, compilation, resolver, fs, callback) { - this.buildMeta = {}; - this.buildInfo = {}; - return callback(); + getEndContent(context) { + if (this.runtimeCondition === false || !this.endContent) return ""; + if (this.runtimeCondition === true) return this.endContent; + const expr = context.runtimeTemplate.runtimeConditionExpression({ + chunkGraph: context.chunkGraph, + runtimeRequirements: context.runtimeRequirements, + runtime: context.runtime, + runtimeCondition: this.runtimeCondition + }); + if (expr === "true") return this.endContent; + return wrapInCondition(expr, this.endContent); } - /** - * @param {CodeGenerationContext} context context for code generation - * @returns {CodeGenerationResult} result - */ - codeGeneration(context) { - const sources = new Map(); - sources.set( - "javascript", - new RawSource("module.exports = __webpack_require__;") + merge(other) { + if (this.runtimeCondition === true) return this; + if (other.runtimeCondition === true) return other; + if (this.runtimeCondition === false) return other; + if (other.runtimeCondition === false) return this; + const runtimeCondition = mergeRuntime( + this.runtimeCondition, + other.runtimeCondition + ); + return new ConditionalInitFragment( + this.content, + this.stage, + this.position, + this.key, + runtimeCondition, + this.endContent ); - return { - sources, - runtimeRequirements: RUNTIME_REQUIREMENTS - }; } +} - /** - * @param {NeedBuildContext} context context info - * @param {function(WebpackError=, boolean=): void} callback callback function, returns true, if the module needs a rebuild - * @returns {void} - */ - needBuild(context, callback) { - return callback(null, !this.buildMeta); - } - - /** - * @param {string=} type the source type for which the size should be estimated - * @returns {number} the estimated size of the module (must be non-zero) - */ - size(type) { - return 12; - } - - /** - * @param {Hash} hash the hash used to track dependencies - * @param {UpdateHashContext} context context - * @returns {void} - */ - updateHash(hash, context) { - hash.update(`dll module${this.name || ""}`); - super.updateHash(hash, context); - } - - serialize(context) { - context.write(this.name); - super.serialize(context); - } - - deserialize(context) { - this.name = context.read(); - super.deserialize(context); - } - - /** - * Assuming this module is in the cache. Update the (cached) module with - * the fresh module from the factory. Usually updates internal references - * and properties. - * @param {Module} module fresh module - * @returns {void} - */ - updateCacheModule(module) { - super.updateCacheModule(module); - this.dependencies = module.dependencies; - } - - /** - * Assuming this module is in the cache. Remove internal references to allow freeing some memory. - */ - cleanupForCache() { - super.cleanupForCache(); - this.dependencies = undefined; - } -} - -makeSerializable(DllModule, "webpack/lib/DllModule"); - -module.exports = DllModule; - - -/***/ }), - -/***/ 77885: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ - - - -const DllModule = __webpack_require__(52692); -const ModuleFactory = __webpack_require__(61574); - -/** @typedef {import("./ModuleFactory").ModuleFactoryCreateData} ModuleFactoryCreateData */ -/** @typedef {import("./ModuleFactory").ModuleFactoryResult} ModuleFactoryResult */ -/** @typedef {import("./dependencies/DllEntryDependency")} DllEntryDependency */ - -class DllModuleFactory extends ModuleFactory { - constructor() { - super(); - this.hooks = Object.freeze({}); - } - /** - * @param {ModuleFactoryCreateData} data data object - * @param {function(Error=, ModuleFactoryResult=): void} callback callback - * @returns {void} - */ - create(data, callback) { - const dependency = /** @type {DllEntryDependency} */ (data.dependencies[0]); - callback(null, { - module: new DllModule( - data.context, - dependency.dependencies, - dependency.name - ) - }); - } -} - -module.exports = DllModuleFactory; +module.exports = ConditionalInitFragment; /***/ }), -/***/ 15232: +/***/ 53042: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; @@ -38789,457 +36568,519 @@ module.exports = DllModuleFactory; -const DllEntryPlugin = __webpack_require__(28766); -const FlagAllModulesAsUsedPlugin = __webpack_require__(85310); -const LibManifestPlugin = __webpack_require__(30711); -const createSchemaValidation = __webpack_require__(77695); +const CachedConstDependency = __webpack_require__(64177); +const ConstDependency = __webpack_require__(60864); +const { evaluateToString } = __webpack_require__(28723); +const { parseResource } = __webpack_require__(96236); -/** @typedef {import("../declarations/plugins/DllPlugin").DllPluginOptions} DllPluginOptions */ +/** @typedef {import("estree").Expression} ExpressionNode */ +/** @typedef {import("estree").Super} SuperNode */ /** @typedef {import("./Compiler")} Compiler */ -const validate = createSchemaValidation( - __webpack_require__(9145), - () => __webpack_require__(7754), - { - name: "Dll Plugin", - baseDataPath: "options" - } -); - -class DllPlugin { - /** - * @param {DllPluginOptions} options options object - */ - constructor(options) { - validate(options); - this.options = { - ...options, - entryOnly: options.entryOnly !== false - }; - } - - /** - * Apply the plugin - * @param {Compiler} compiler the compiler instance - * @returns {void} - */ - apply(compiler) { - compiler.hooks.entryOption.tap("DllPlugin", (context, entry) => { - if (typeof entry !== "function") { - for (const name of Object.keys(entry)) { - const options = { - name, - filename: entry.filename - }; - new DllEntryPlugin(context, entry[name].import, options).apply( - compiler - ); +const collectDeclaration = (declarations, pattern) => { + const stack = [pattern]; + while (stack.length > 0) { + const node = stack.pop(); + switch (node.type) { + case "Identifier": + declarations.add(node.name); + break; + case "ArrayPattern": + for (const element of node.elements) { + if (element) { + stack.push(element); + } } - } else { - throw new Error( - "DllPlugin doesn't support dynamic entry (function) yet" - ); - } - return true; - }); - new LibManifestPlugin(this.options).apply(compiler); - if (!this.options.entryOnly) { - new FlagAllModulesAsUsedPlugin("DllPlugin").apply(compiler); + break; + case "AssignmentPattern": + stack.push(node.left); + break; + case "ObjectPattern": + for (const property of node.properties) { + stack.push(property.value); + } + break; + case "RestElement": + stack.push(node.argument); + break; } } -} - -module.exports = DllPlugin; - - -/***/ }), - -/***/ 8904: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ - - - -const parseJson = __webpack_require__(48335); -const DelegatedModuleFactoryPlugin = __webpack_require__(50756); -const ExternalModuleFactoryPlugin = __webpack_require__(19364); -const WebpackError = __webpack_require__(68422); -const DelegatedSourceDependency = __webpack_require__(82766); -const createSchemaValidation = __webpack_require__(77695); -const makePathsRelative = __webpack_require__(96236).makePathsRelative; - -/** @typedef {import("../declarations/WebpackOptions").Externals} Externals */ -/** @typedef {import("../declarations/plugins/DllReferencePlugin").DllReferencePluginOptions} DllReferencePluginOptions */ -/** @typedef {import("../declarations/plugins/DllReferencePlugin").DllReferencePluginOptionsManifest} DllReferencePluginOptionsManifest */ - -const validate = createSchemaValidation( - __webpack_require__(15909), - () => __webpack_require__(15766), - { - name: "Dll Reference Plugin", - baseDataPath: "options" - } -); - -class DllReferencePlugin { - /** - * @param {DllReferencePluginOptions} options options object - */ - constructor(options) { - validate(options); - this.options = options; - /** @type {WeakMap} */ - this._compilationData = new WeakMap(); - } - - apply(compiler) { - compiler.hooks.compilation.tap( - "DllReferencePlugin", - (compilation, { normalModuleFactory }) => { - compilation.dependencyFactories.set( - DelegatedSourceDependency, - normalModuleFactory - ); - } - ); +}; - compiler.hooks.beforeCompile.tapAsync( - "DllReferencePlugin", - (params, callback) => { - if ("manifest" in this.options) { - const manifest = this.options.manifest; - if (typeof manifest === "string") { - compiler.inputFileSystem.readFile(manifest, (err, result) => { - if (err) return callback(err); - const data = { - path: manifest, - data: undefined, - error: undefined - }; - // Catch errors parsing the manifest so that blank - // or malformed manifest files don't kill the process. - try { - data.data = parseJson(result.toString("utf-8")); - } catch (e) { - // Store the error in the params so that it can - // be added as a compilation error later on. - const manifestPath = makePathsRelative( - compiler.options.context, - manifest, - compiler.root - ); - data.error = new DllManifestError(manifestPath, e.message); - } - this._compilationData.set(params, data); - return callback(); - }); - return; - } +const getHoistedDeclarations = (branch, includeFunctionDeclarations) => { + const declarations = new Set(); + const stack = [branch]; + while (stack.length > 0) { + const node = stack.pop(); + // Some node could be `null` or `undefined`. + if (!node) continue; + switch (node.type) { + // Walk through control statements to look for hoisted declarations. + // Some branches are skipped since they do not allow declarations. + case "BlockStatement": + for (const stmt of node.body) { + stack.push(stmt); } - return callback(); - } - ); - - compiler.hooks.compile.tap("DllReferencePlugin", params => { - let name = this.options.name; - let sourceType = this.options.sourceType; - let content = - "content" in this.options ? this.options.content : undefined; - if ("manifest" in this.options) { - let manifestParameter = this.options.manifest; - let manifest; - if (typeof manifestParameter === "string") { - const data = this._compilationData.get(params); - // If there was an error parsing the manifest - // file, exit now because the error will be added - // as a compilation error in the "compilation" hook. - if (data.error) { - return; + break; + case "IfStatement": + stack.push(node.consequent); + stack.push(node.alternate); + break; + case "ForStatement": + stack.push(node.init); + stack.push(node.body); + break; + case "ForInStatement": + case "ForOfStatement": + stack.push(node.left); + stack.push(node.body); + break; + case "DoWhileStatement": + case "WhileStatement": + case "LabeledStatement": + stack.push(node.body); + break; + case "SwitchStatement": + for (const cs of node.cases) { + for (const consequent of cs.consequent) { + stack.push(consequent); } - manifest = data.data; - } else { - manifest = manifestParameter; } - if (manifest) { - if (!name) name = manifest.name; - if (!sourceType) sourceType = manifest.type; - if (!content) content = manifest.content; + break; + case "TryStatement": + stack.push(node.block); + if (node.handler) { + stack.push(node.handler.body); } - } - /** @type {Externals} */ - const externals = {}; - const source = "dll-reference " + name; - externals[source] = name; - const normalModuleFactory = params.normalModuleFactory; - new ExternalModuleFactoryPlugin(sourceType || "var", externals).apply( - normalModuleFactory - ); - new DelegatedModuleFactoryPlugin({ - source: source, - type: this.options.type, - scope: this.options.scope, - context: this.options.context || compiler.options.context, - content, - extensions: this.options.extensions, - associatedObjectForCache: compiler.root - }).apply(normalModuleFactory); - }); - - compiler.hooks.compilation.tap( - "DllReferencePlugin", - (compilation, params) => { - if ("manifest" in this.options) { - let manifest = this.options.manifest; - if (typeof manifest === "string") { - const data = this._compilationData.get(params); - // If there was an error parsing the manifest file, add the - // error as a compilation error to make the compilation fail. - if (data.error) { - compilation.errors.push(data.error); - } - compilation.fileDependencies.add(manifest); + stack.push(node.finalizer); + break; + case "FunctionDeclaration": + if (includeFunctionDeclarations) { + collectDeclaration(declarations, node.id); + } + break; + case "VariableDeclaration": + if (node.kind === "var") { + for (const decl of node.declarations) { + collectDeclaration(declarations, decl.id); } } - } - ); - } -} - -class DllManifestError extends WebpackError { - constructor(filename, message) { - super(); - - this.name = "DllManifestError"; - this.message = `Dll manifest ${filename}\n${message}`; - } -} - -module.exports = DllReferencePlugin; - - -/***/ }), - -/***/ 60670: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Naoyuki Kanezawa @nkzawa -*/ - - - -const EntryOptionPlugin = __webpack_require__(59526); -const EntryPlugin = __webpack_require__(82430); -const EntryDependency = __webpack_require__(41075); - -/** @typedef {import("../declarations/WebpackOptions").EntryDynamicNormalized} EntryDynamic */ -/** @typedef {import("../declarations/WebpackOptions").EntryItem} EntryItem */ -/** @typedef {import("../declarations/WebpackOptions").EntryStaticNormalized} EntryStatic */ -/** @typedef {import("./Compiler")} Compiler */ - -class DynamicEntryPlugin { - /** - * @param {string} context the context path - * @param {EntryDynamic} entry the entry value - */ - constructor(context, entry) { - this.context = context; - this.entry = entry; + break; + } } + return Array.from(declarations); +}; +class ConstPlugin { /** * Apply the plugin * @param {Compiler} compiler the compiler instance * @returns {void} */ apply(compiler) { + const cachedParseResource = parseResource.bindCache(compiler.root); compiler.hooks.compilation.tap( - "DynamicEntryPlugin", + "ConstPlugin", (compilation, { normalModuleFactory }) => { - compilation.dependencyFactories.set( - EntryDependency, - normalModuleFactory + compilation.dependencyTemplates.set( + ConstDependency, + new ConstDependency.Template() ); - } - ); - - compiler.hooks.make.tapPromise( - "DynamicEntryPlugin", - (compilation, callback) => - Promise.resolve(this.entry()) - .then(entry => { - const promises = []; - for (const name of Object.keys(entry)) { - const desc = entry[name]; - const options = EntryOptionPlugin.entryDescriptionToOptions( - compiler, - name, - desc - ); - for (const entry of desc.import) { - promises.push( - new Promise((resolve, reject) => { - compilation.addEntry( - this.context, - EntryPlugin.createDependency(entry, options), - options, - err => { - if (err) return reject(err); - resolve(); - } - ); - }) - ); - } - } - return Promise.all(promises); - }) - .then(x => {}) - ); - } -} - -module.exports = DynamicEntryPlugin; - - -/***/ }), - -/***/ 59526: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ - + compilation.dependencyTemplates.set( + CachedConstDependency, + new CachedConstDependency.Template() + ); -/** @typedef {import("../declarations/WebpackOptions").EntryDescriptionNormalized} EntryDescription */ -/** @typedef {import("../declarations/WebpackOptions").EntryNormalized} Entry */ -/** @typedef {import("./Compiler")} Compiler */ -/** @typedef {import("./Entrypoint").EntryOptions} EntryOptions */ - -class EntryOptionPlugin { - /** - * @param {Compiler} compiler the compiler instance one is tapping into - * @returns {void} - */ - apply(compiler) { - compiler.hooks.entryOption.tap("EntryOptionPlugin", (context, entry) => { - EntryOptionPlugin.applyEntryOption(compiler, context, entry); - return true; - }); - } + const handler = parser => { + parser.hooks.statementIf.tap("ConstPlugin", statement => { + if (parser.scope.isAsmJs) return; + const param = parser.evaluateExpression(statement.test); + const bool = param.asBool(); + if (typeof bool === "boolean") { + if (!param.couldHaveSideEffects()) { + const dep = new ConstDependency(`${bool}`, param.range); + dep.loc = statement.loc; + parser.state.module.addPresentationalDependency(dep); + } else { + parser.walkExpression(statement.test); + } + const branchToRemove = bool + ? statement.alternate + : statement.consequent; + if (branchToRemove) { + // Before removing the dead branch, the hoisted declarations + // must be collected. + // + // Given the following code: + // + // if (true) f() else g() + // if (false) { + // function f() {} + // const g = function g() {} + // if (someTest) { + // let a = 1 + // var x, {y, z} = obj + // } + // } else { + // … + // } + // + // the generated code is: + // + // if (true) f() else {} + // if (false) { + // var f, x, y, z; (in loose mode) + // var x, y, z; (in strict mode) + // } else { + // … + // } + // + // NOTE: When code runs in strict mode, `var` declarations + // are hoisted but `function` declarations don't. + // + let declarations; + if (parser.scope.isStrict) { + // If the code runs in strict mode, variable declarations + // using `var` must be hoisted. + declarations = getHoistedDeclarations(branchToRemove, false); + } else { + // Otherwise, collect all hoisted declaration. + declarations = getHoistedDeclarations(branchToRemove, true); + } + let replacement; + if (declarations.length > 0) { + replacement = `{ var ${declarations.join(", ")}; }`; + } else { + replacement = "{}"; + } + const dep = new ConstDependency( + replacement, + branchToRemove.range + ); + dep.loc = branchToRemove.loc; + parser.state.module.addPresentationalDependency(dep); + } + return bool; + } + }); + parser.hooks.expressionConditionalOperator.tap( + "ConstPlugin", + expression => { + if (parser.scope.isAsmJs) return; + const param = parser.evaluateExpression(expression.test); + const bool = param.asBool(); + if (typeof bool === "boolean") { + if (!param.couldHaveSideEffects()) { + const dep = new ConstDependency(` ${bool}`, param.range); + dep.loc = expression.loc; + parser.state.module.addPresentationalDependency(dep); + } else { + parser.walkExpression(expression.test); + } + // Expressions do not hoist. + // It is safe to remove the dead branch. + // + // Given the following code: + // + // false ? someExpression() : otherExpression(); + // + // the generated code is: + // + // false ? 0 : otherExpression(); + // + const branchToRemove = bool + ? expression.alternate + : expression.consequent; + const dep = new ConstDependency("0", branchToRemove.range); + dep.loc = branchToRemove.loc; + parser.state.module.addPresentationalDependency(dep); + return bool; + } + } + ); + parser.hooks.expressionLogicalOperator.tap( + "ConstPlugin", + expression => { + if (parser.scope.isAsmJs) return; + if ( + expression.operator === "&&" || + expression.operator === "||" + ) { + const param = parser.evaluateExpression(expression.left); + const bool = param.asBool(); + if (typeof bool === "boolean") { + // Expressions do not hoist. + // It is safe to remove the dead branch. + // + // ------------------------------------------ + // + // Given the following code: + // + // falsyExpression() && someExpression(); + // + // the generated code is: + // + // falsyExpression() && false; + // + // ------------------------------------------ + // + // Given the following code: + // + // truthyExpression() && someExpression(); + // + // the generated code is: + // + // true && someExpression(); + // + // ------------------------------------------ + // + // Given the following code: + // + // truthyExpression() || someExpression(); + // + // the generated code is: + // + // truthyExpression() || false; + // + // ------------------------------------------ + // + // Given the following code: + // + // falsyExpression() || someExpression(); + // + // the generated code is: + // + // false && someExpression(); + // + const keepRight = + (expression.operator === "&&" && bool) || + (expression.operator === "||" && !bool); - /** - * @param {Compiler} compiler the compiler - * @param {string} context context directory - * @param {Entry} entry request - * @returns {void} - */ - static applyEntryOption(compiler, context, entry) { - if (typeof entry === "function") { - const DynamicEntryPlugin = __webpack_require__(60670); - new DynamicEntryPlugin(context, entry).apply(compiler); - } else { - const EntryPlugin = __webpack_require__(82430); - for (const name of Object.keys(entry)) { - const desc = entry[name]; - const options = EntryOptionPlugin.entryDescriptionToOptions( - compiler, - name, - desc - ); - for (const entry of desc.import) { - new EntryPlugin(context, entry, options).apply(compiler); - } - } - } - } + if ( + !param.couldHaveSideEffects() && + (param.isBoolean() || keepRight) + ) { + // for case like + // + // return'development'===process.env.NODE_ENV&&'foo' + // + // we need a space before the bool to prevent result like + // + // returnfalse&&'foo' + // + const dep = new ConstDependency(` ${bool}`, param.range); + dep.loc = expression.loc; + parser.state.module.addPresentationalDependency(dep); + } else { + parser.walkExpression(expression.left); + } + if (!keepRight) { + const dep = new ConstDependency( + "0", + expression.right.range + ); + dep.loc = expression.loc; + parser.state.module.addPresentationalDependency(dep); + } + return keepRight; + } + } else if (expression.operator === "??") { + const param = parser.evaluateExpression(expression.left); + const keepRight = param && param.asNullish(); + if (typeof keepRight === "boolean") { + // ------------------------------------------ + // + // Given the following code: + // + // nonNullish ?? someExpression(); + // + // the generated code is: + // + // nonNullish ?? 0; + // + // ------------------------------------------ + // + // Given the following code: + // + // nullish ?? someExpression(); + // + // the generated code is: + // + // null ?? someExpression(); + // + if (!param.couldHaveSideEffects() && keepRight) { + // cspell:word returnnull + // for case like + // + // return('development'===process.env.NODE_ENV&&null)??'foo' + // + // we need a space before the bool to prevent result like + // + // returnnull??'foo' + // + const dep = new ConstDependency(" null", param.range); + dep.loc = expression.loc; + parser.state.module.addPresentationalDependency(dep); + } else { + const dep = new ConstDependency( + "0", + expression.right.range + ); + dep.loc = expression.loc; + parser.state.module.addPresentationalDependency(dep); + parser.walkExpression(expression.left); + } - /** - * @param {Compiler} compiler the compiler - * @param {string} name entry name - * @param {EntryDescription} desc entry description - * @returns {EntryOptions} options for the entry - */ - static entryDescriptionToOptions(compiler, name, desc) { - /** @type {EntryOptions} */ - const options = { - name, - filename: desc.filename, - runtime: desc.runtime, - layer: desc.layer, - dependOn: desc.dependOn, - publicPath: desc.publicPath, - chunkLoading: desc.chunkLoading, - asyncChunks: desc.asyncChunks, - wasmLoading: desc.wasmLoading, - library: desc.library - }; - if (desc.layer !== undefined && !compiler.options.experiments.layers) { - throw new Error( - "'entryOptions.layer' is only allowed when 'experiments.layers' is enabled" - ); - } - if (desc.chunkLoading) { - const EnableChunkLoadingPlugin = __webpack_require__(34726); - EnableChunkLoadingPlugin.checkEnabled(compiler, desc.chunkLoading); - } - if (desc.wasmLoading) { - const EnableWasmLoadingPlugin = __webpack_require__(93943); - EnableWasmLoadingPlugin.checkEnabled(compiler, desc.wasmLoading); - } - if (desc.library) { - const EnableLibraryPlugin = __webpack_require__(35613); - EnableLibraryPlugin.checkEnabled(compiler, desc.library.type); - } - return options; + return keepRight; + } + } + } + ); + parser.hooks.optionalChaining.tap("ConstPlugin", expr => { + /** @type {ExpressionNode[]} */ + const optionalExpressionsStack = []; + /** @type {ExpressionNode|SuperNode} */ + let next = expr.expression; + + while ( + next.type === "MemberExpression" || + next.type === "CallExpression" + ) { + if (next.type === "MemberExpression") { + if (next.optional) { + // SuperNode can not be optional + optionalExpressionsStack.push( + /** @type {ExpressionNode} */ (next.object) + ); + } + next = next.object; + } else { + if (next.optional) { + // SuperNode can not be optional + optionalExpressionsStack.push( + /** @type {ExpressionNode} */ (next.callee) + ); + } + next = next.callee; + } + } + + while (optionalExpressionsStack.length) { + const expression = optionalExpressionsStack.pop(); + const evaluated = parser.evaluateExpression(expression); + + if (evaluated && evaluated.asNullish()) { + // ------------------------------------------ + // + // Given the following code: + // + // nullishMemberChain?.a.b(); + // + // the generated code is: + // + // undefined; + // + // ------------------------------------------ + // + const dep = new ConstDependency(" undefined", expr.range); + dep.loc = expr.loc; + parser.state.module.addPresentationalDependency(dep); + return true; + } + } + }); + parser.hooks.evaluateIdentifier + .for("__resourceQuery") + .tap("ConstPlugin", expr => { + if (parser.scope.isAsmJs) return; + if (!parser.state.module) return; + return evaluateToString( + cachedParseResource(parser.state.module.resource).query + )(expr); + }); + parser.hooks.expression + .for("__resourceQuery") + .tap("ConstPlugin", expr => { + if (parser.scope.isAsmJs) return; + if (!parser.state.module) return; + const dep = new CachedConstDependency( + JSON.stringify( + cachedParseResource(parser.state.module.resource).query + ), + expr.range, + "__resourceQuery" + ); + dep.loc = expr.loc; + parser.state.module.addPresentationalDependency(dep); + return true; + }); + + parser.hooks.evaluateIdentifier + .for("__resourceFragment") + .tap("ConstPlugin", expr => { + if (parser.scope.isAsmJs) return; + if (!parser.state.module) return; + return evaluateToString( + cachedParseResource(parser.state.module.resource).fragment + )(expr); + }); + parser.hooks.expression + .for("__resourceFragment") + .tap("ConstPlugin", expr => { + if (parser.scope.isAsmJs) return; + if (!parser.state.module) return; + const dep = new CachedConstDependency( + JSON.stringify( + cachedParseResource(parser.state.module.resource).fragment + ), + expr.range, + "__resourceFragment" + ); + dep.loc = expr.loc; + parser.state.module.addPresentationalDependency(dep); + return true; + }); + }; + + normalModuleFactory.hooks.parser + .for("javascript/auto") + .tap("ConstPlugin", handler); + normalModuleFactory.hooks.parser + .for("javascript/dynamic") + .tap("ConstPlugin", handler); + normalModuleFactory.hooks.parser + .for("javascript/esm") + .tap("ConstPlugin", handler); + } + ); } } -module.exports = EntryOptionPlugin; +module.exports = ConstPlugin; /***/ }), -/***/ 82430: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { +/***/ 30480: +/***/ (function(module) { "use strict"; /* MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra */ -const EntryDependency = __webpack_require__(41075); - /** @typedef {import("./Compiler")} Compiler */ -/** @typedef {import("./Entrypoint").EntryOptions} EntryOptions */ +/** @typedef {import("./ContextModuleFactory")} ContextModuleFactory */ -class EntryPlugin { +class ContextExclusionPlugin { /** - * An entry plugin which will handle - * creation of the EntryDependency - * - * @param {string} context context path - * @param {string} entry entry path - * @param {EntryOptions | string=} options entry options (passing a string is deprecated) + * @param {RegExp} negativeMatcher Matcher regular expression */ - constructor(context, entry, options) { - this.context = context; - this.entry = entry; - this.options = options || ""; + constructor(negativeMatcher) { + this.negativeMatcher = negativeMatcher; } /** @@ -39248,45 +37089,20 @@ class EntryPlugin { * @returns {void} */ apply(compiler) { - compiler.hooks.compilation.tap( - "EntryPlugin", - (compilation, { normalModuleFactory }) => { - compilation.dependencyFactories.set( - EntryDependency, - normalModuleFactory - ); - } - ); - - const { entry, options, context } = this; - const dep = EntryPlugin.createDependency(entry, options); - - compiler.hooks.make.tapAsync("EntryPlugin", (compilation, callback) => { - compilation.addEntry(context, dep, options, err => { - callback(err); + compiler.hooks.contextModuleFactory.tap("ContextExclusionPlugin", cmf => { + cmf.hooks.contextModuleFiles.tap("ContextExclusionPlugin", files => { + return files.filter(filePath => !this.negativeMatcher.test(filePath)); }); }); } - - /** - * @param {string} entry entry request - * @param {EntryOptions | string} options entry options (passing string is deprecated) - * @returns {EntryDependency} the dependency - */ - static createDependency(entry, options) { - const dep = new EntryDependency(entry); - // TODO webpack 6 remove string option - dep.loc = { name: typeof options === "object" ? options.name : options }; - return dep; - } } -module.exports = EntryPlugin; +module.exports = ContextExclusionPlugin; /***/ }), -/***/ 86695: +/***/ 80207: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; @@ -39297,2162 +37113,2258 @@ module.exports = EntryPlugin; -const ChunkGroup = __webpack_require__(96975); - -/** @typedef {import("../declarations/WebpackOptions").EntryDescriptionNormalized} EntryDescription */ -/** @typedef {import("./Chunk")} Chunk */ +const { OriginalSource, RawSource } = __webpack_require__(96192); +const AsyncDependenciesBlock = __webpack_require__(11315); +const { makeWebpackError } = __webpack_require__(89935); +const Module = __webpack_require__(85887); +const RuntimeGlobals = __webpack_require__(49404); +const Template = __webpack_require__(92066); +const WebpackError = __webpack_require__(68422); +const { + compareLocations, + concatComparators, + compareSelect, + keepOriginalOrder, + compareModulesById +} = __webpack_require__(26296); +const { contextify, parseResource } = __webpack_require__(96236); +const makeSerializable = __webpack_require__(26522); -/** @typedef {{ name?: string } & Omit} EntryOptions */ +/** @typedef {import("webpack-sources").Source} Source */ +/** @typedef {import("../declarations/WebpackOptions").WebpackOptionsNormalized} WebpackOptions */ +/** @typedef {import("./ChunkGraph")} ChunkGraph */ +/** @typedef {import("./ChunkGroup").RawChunkGroupOptions} RawChunkGroupOptions */ +/** @typedef {import("./Compilation")} Compilation */ +/** @typedef {import("./DependencyTemplates")} DependencyTemplates */ +/** @typedef {import("./Module").BuildMeta} BuildMeta */ +/** @typedef {import("./Module").CodeGenerationContext} CodeGenerationContext */ +/** @typedef {import("./Module").CodeGenerationResult} CodeGenerationResult */ +/** @typedef {import("./Module").LibIdentOptions} LibIdentOptions */ +/** @typedef {import("./Module").NeedBuildContext} NeedBuildContext */ +/** @typedef {import("./ModuleGraph")} ModuleGraph */ +/** @typedef {import("./RequestShortener")} RequestShortener */ +/** @typedef {import("./ResolverFactory").ResolverWithOptions} ResolverWithOptions */ +/** @typedef {import("./RuntimeTemplate")} RuntimeTemplate */ +/** @typedef {import("./dependencies/ContextElementDependency")} ContextElementDependency */ +/** @template T @typedef {import("./util/LazySet")} LazySet */ +/** @typedef {import("./util/fs").InputFileSystem} InputFileSystem */ + +/** @typedef {"sync" | "eager" | "weak" | "async-weak" | "lazy" | "lazy-once"} ContextMode Context mode */ /** - * Entrypoint serves as an encapsulation primitive for chunks that are - * a part of a single ChunkGroup. They represent all bundles that need to be loaded for a - * single instance of a page. Multi-page application architectures will typically yield multiple Entrypoint objects - * inside of the compilation, whereas a Single Page App may only contain one with many lazy-loaded chunks. + * @typedef {Object} ContextOptions + * @property {ContextMode} mode + * @property {boolean} recursive + * @property {RegExp} regExp + * @property {"strict"|boolean=} namespaceObject + * @property {string=} addon + * @property {string=} chunkName + * @property {RegExp=} include + * @property {RegExp=} exclude + * @property {RawChunkGroupOptions=} groupOptions + * @property {string=} typePrefix + * @property {string=} category + * @property {string[][]=} referencedExports exports referenced from modules (won't be mangled) */ -class Entrypoint extends ChunkGroup { + +/** + * @typedef {Object} ContextModuleOptionsExtras + * @property {string} resource + * @property {string=} resourceQuery + * @property {string=} resourceFragment + * @property {TODO} resolveOptions + */ + +/** @typedef {ContextOptions & ContextModuleOptionsExtras} ContextModuleOptions */ + +/** + * @callback ResolveDependenciesCallback + * @param {Error=} err + * @param {ContextElementDependency[]=} dependencies + */ + +/** + * @callback ResolveDependencies + * @param {InputFileSystem} fs + * @param {ContextModuleOptions} options + * @param {ResolveDependenciesCallback} callback + */ + +const SNAPSHOT_OPTIONS = { timestamp: true }; + +const TYPES = new Set(["javascript"]); + +class ContextModule extends Module { /** - * Creates an instance of Entrypoint. - * @param {EntryOptions | string} entryOptions the options for the entrypoint (or name) - * @param {boolean=} initial false, when the entrypoint is not initial loaded + * @param {ResolveDependencies} resolveDependencies function to get dependencies in this context + * @param {ContextModuleOptions} options options object */ - constructor(entryOptions, initial = true) { - if (typeof entryOptions === "string") { - entryOptions = { name: entryOptions }; + constructor(resolveDependencies, options) { + const parsed = parseResource(options ? options.resource : ""); + const resource = parsed.path; + const resourceQuery = (options && options.resourceQuery) || parsed.query; + const resourceFragment = + (options && options.resourceFragment) || parsed.fragment; + + super("javascript/dynamic", resource); + + // Info from Factory + this.resolveDependencies = resolveDependencies; + /** @type {ContextModuleOptions} */ + this.options = { + ...options, + resource, + resourceQuery, + resourceFragment + }; + if (options && options.resolveOptions !== undefined) { + this.resolveOptions = options.resolveOptions; } - super({ - name: entryOptions.name - }); - this.options = entryOptions; - /** @type {Chunk=} */ - this._runtimeChunk = undefined; - /** @type {Chunk=} */ - this._entrypointChunk = undefined; - /** @type {boolean} */ - this._initial = initial; + + if (options && typeof options.mode !== "string") { + throw new Error("options.mode is a required option"); + } + + this._identifier = this._createIdentifier(); + this._forceBuild = true; } /** - * @returns {boolean} true, when this chunk group will be loaded on initial page load + * @returns {Set} types available (do not mutate) */ - isInitial() { - return this._initial; + getSourceTypes() { + return TYPES; } /** - * Sets the runtimeChunk for an entrypoint. - * @param {Chunk} chunk the chunk being set as the runtime chunk. + * Assuming this module is in the cache. Update the (cached) module with + * the fresh module from the factory. Usually updates internal references + * and properties. + * @param {Module} module fresh module * @returns {void} */ - setRuntimeChunk(chunk) { - this._runtimeChunk = chunk; + updateCacheModule(module) { + const m = /** @type {ContextModule} */ (module); + this.resolveDependencies = m.resolveDependencies; + this.options = m.options; } /** - * Fetches the chunk reference containing the webpack bootstrap code - * @returns {Chunk | null} returns the runtime chunk or null if there is none + * Assuming this module is in the cache. Remove internal references to allow freeing some memory. */ - getRuntimeChunk() { - if (this._runtimeChunk) return this._runtimeChunk; - for (const parent of this.parentsIterable) { - if (parent instanceof Entrypoint) return parent.getRuntimeChunk(); + cleanupForCache() { + super.cleanupForCache(); + this.resolveDependencies = undefined; + } + + prettyRegExp(regexString) { + // remove the "/" at the front and the beginning + // "/foo/" -> "foo" + return regexString + .substring(1, regexString.length - 1) + .replace(/!/g, "%21"); + } + + _createIdentifier() { + let identifier = this.context; + if (this.options.resourceQuery) { + identifier += `|${this.options.resourceQuery}`; } - return null; + if (this.options.resourceFragment) { + identifier += `|${this.options.resourceFragment}`; + } + if (this.options.mode) { + identifier += `|${this.options.mode}`; + } + if (!this.options.recursive) { + identifier += "|nonrecursive"; + } + if (this.options.addon) { + identifier += `|${this.options.addon}`; + } + if (this.options.regExp) { + identifier += `|${this.options.regExp}`; + } + if (this.options.include) { + identifier += `|include: ${this.options.include}`; + } + if (this.options.exclude) { + identifier += `|exclude: ${this.options.exclude}`; + } + if (this.options.referencedExports) { + identifier += `|referencedExports: ${JSON.stringify( + this.options.referencedExports + )}`; + } + if (this.options.chunkName) { + identifier += `|chunkName: ${this.options.chunkName}`; + } + if (this.options.groupOptions) { + identifier += `|groupOptions: ${JSON.stringify( + this.options.groupOptions + )}`; + } + if (this.options.namespaceObject === "strict") { + identifier += "|strict namespace object"; + } else if (this.options.namespaceObject) { + identifier += "|namespace object"; + } + + return identifier; } /** - * Sets the chunk with the entrypoint modules for an entrypoint. - * @param {Chunk} chunk the chunk being set as the entrypoint chunk. - * @returns {void} + * @returns {string} a unique identifier of the module */ - setEntrypointChunk(chunk) { - this._entrypointChunk = chunk; + identifier() { + return this._identifier; } /** - * Returns the chunk which contains the entrypoint modules - * (or at least the execution of them) - * @returns {Chunk} chunk + * @param {RequestShortener} requestShortener the request shortener + * @returns {string} a user readable identifier of the module */ - getEntrypointChunk() { - return this._entrypointChunk; + readableIdentifier(requestShortener) { + let identifier = requestShortener.shorten(this.context) + "/"; + if (this.options.resourceQuery) { + identifier += ` ${this.options.resourceQuery}`; + } + if (this.options.mode) { + identifier += ` ${this.options.mode}`; + } + if (!this.options.recursive) { + identifier += " nonrecursive"; + } + if (this.options.addon) { + identifier += ` ${requestShortener.shorten(this.options.addon)}`; + } + if (this.options.regExp) { + identifier += ` ${this.prettyRegExp(this.options.regExp + "")}`; + } + if (this.options.include) { + identifier += ` include: ${this.prettyRegExp(this.options.include + "")}`; + } + if (this.options.exclude) { + identifier += ` exclude: ${this.prettyRegExp(this.options.exclude + "")}`; + } + if (this.options.referencedExports) { + identifier += ` referencedExports: ${this.options.referencedExports + .map(e => e.join(".")) + .join(", ")}`; + } + if (this.options.chunkName) { + identifier += ` chunkName: ${this.options.chunkName}`; + } + if (this.options.groupOptions) { + const groupOptions = this.options.groupOptions; + for (const key of Object.keys(groupOptions)) { + identifier += ` ${key}: ${groupOptions[key]}`; + } + } + if (this.options.namespaceObject === "strict") { + identifier += " strict namespace object"; + } else if (this.options.namespaceObject) { + identifier += " namespace object"; + } + + return identifier; } /** - * @param {Chunk} oldChunk chunk to be replaced - * @param {Chunk} newChunk New chunk that will be replaced with - * @returns {boolean} returns true if the replacement was successful + * @param {LibIdentOptions} options options + * @returns {string | null} an identifier for library inclusion */ - replaceChunk(oldChunk, newChunk) { - if (this._runtimeChunk === oldChunk) this._runtimeChunk = newChunk; - if (this._entrypointChunk === oldChunk) this._entrypointChunk = newChunk; - return super.replaceChunk(oldChunk, newChunk); - } -} - -module.exports = Entrypoint; - - -/***/ }), - -/***/ 43755: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Authors Simen Brekken @simenbrekken, Einar Löve @einarlove -*/ + libIdent(options) { + let identifier = contextify( + options.context, + this.context, + options.associatedObjectForCache + ); + if (this.options.mode) { + identifier += ` ${this.options.mode}`; + } + if (this.options.recursive) { + identifier += " recursive"; + } + if (this.options.addon) { + identifier += ` ${contextify( + options.context, + this.options.addon, + options.associatedObjectForCache + )}`; + } + if (this.options.regExp) { + identifier += ` ${this.prettyRegExp(this.options.regExp + "")}`; + } + if (this.options.include) { + identifier += ` include: ${this.prettyRegExp(this.options.include + "")}`; + } + if (this.options.exclude) { + identifier += ` exclude: ${this.prettyRegExp(this.options.exclude + "")}`; + } + if (this.options.referencedExports) { + identifier += ` referencedExports: ${this.options.referencedExports + .map(e => e.join(".")) + .join(", ")}`; + } + return identifier; + } + /** + * @returns {void} + */ + invalidateBuild() { + this._forceBuild = true; + } -const DefinePlugin = __webpack_require__(46754); -const WebpackError = __webpack_require__(68422); + /** + * @param {NeedBuildContext} context context info + * @param {function(WebpackError=, boolean=): void} callback callback function, returns true, if the module needs a rebuild + * @returns {void} + */ + needBuild({ fileSystemInfo }, callback) { + // build if enforced + if (this._forceBuild) return callback(null, true); -/** @typedef {import("./Compiler")} Compiler */ -/** @typedef {import("./DefinePlugin").CodeValue} CodeValue */ + // always build when we have no snapshot + if (!this.buildInfo.snapshot) return callback(null, true); -class EnvironmentPlugin { - constructor(...keys) { - if (keys.length === 1 && Array.isArray(keys[0])) { - this.keys = keys[0]; - this.defaultValues = {}; - } else if (keys.length === 1 && keys[0] && typeof keys[0] === "object") { - this.keys = Object.keys(keys[0]); - this.defaultValues = keys[0]; - } else { - this.keys = keys; - this.defaultValues = {}; - } + fileSystemInfo.checkSnapshotValid(this.buildInfo.snapshot, (err, valid) => { + callback(err, !valid); + }); } /** - * Apply the plugin - * @param {Compiler} compiler the compiler instance + * @param {WebpackOptions} options webpack options + * @param {Compilation} compilation the compilation + * @param {ResolverWithOptions} resolver the resolver + * @param {InputFileSystem} fs the file system + * @param {function(WebpackError=): void} callback callback function * @returns {void} */ - apply(compiler) { - /** @type {Record} */ - const definitions = {}; - for (const key of this.keys) { - const value = - process.env[key] !== undefined - ? process.env[key] - : this.defaultValues[key]; - - if (value === undefined) { - compiler.hooks.thisCompilation.tap("EnvironmentPlugin", compilation => { - const error = new WebpackError( - `EnvironmentPlugin - ${key} environment variable is undefined.\n\n` + - "You can pass an object with default values to suppress this warning.\n" + - "See https://webpack.js.org/plugins/environment-plugin for example." - ); + build(options, compilation, resolver, fs, callback) { + this._forceBuild = false; + /** @type {BuildMeta} */ + this.buildMeta = { + exportsType: "default", + defaultObject: "redirect-warn" + }; + this.buildInfo = { + snapshot: undefined + }; + this.dependencies.length = 0; + this.blocks.length = 0; + const startTime = Date.now(); + this.resolveDependencies(fs, this.options, (err, dependencies) => { + if (err) { + return callback( + makeWebpackError(err, "ContextModule.resolveDependencies") + ); + } - error.name = "EnvVariableNotDefinedError"; - compilation.errors.push(error); - }); + // abort if something failed + // this will create an empty context + if (!dependencies) { + callback(); + return; } - definitions[`process.env.${key}`] = - value === undefined ? "undefined" : JSON.stringify(value); - } + // enhance dependencies with meta info + for (const dep of dependencies) { + dep.loc = { + name: dep.userRequest + }; + dep.request = this.options.addon + dep.request; + } + dependencies.sort( + concatComparators( + compareSelect(a => a.loc, compareLocations), + keepOriginalOrder(this.dependencies) + ) + ); - new DefinePlugin(definitions).apply(compiler); + if (this.options.mode === "sync" || this.options.mode === "eager") { + // if we have an sync or eager context + // just add all dependencies and continue + this.dependencies = dependencies; + } else if (this.options.mode === "lazy-once") { + // for the lazy-once mode create a new async dependency block + // and add that block to this context + if (dependencies.length > 0) { + const block = new AsyncDependenciesBlock({ + ...this.options.groupOptions, + name: this.options.chunkName + }); + for (const dep of dependencies) { + block.addDependency(dep); + } + this.addBlock(block); + } + } else if ( + this.options.mode === "weak" || + this.options.mode === "async-weak" + ) { + // we mark all dependencies as weak + for (const dep of dependencies) { + dep.weak = true; + } + this.dependencies = dependencies; + } else if (this.options.mode === "lazy") { + // if we are lazy create a new async dependency block per dependency + // and add all blocks to this context + let index = 0; + for (const dep of dependencies) { + let chunkName = this.options.chunkName; + if (chunkName) { + if (!/\[(index|request)\]/.test(chunkName)) { + chunkName += "[index]"; + } + chunkName = chunkName.replace(/\[index\]/g, `${index++}`); + chunkName = chunkName.replace( + /\[request\]/g, + Template.toPath(dep.userRequest) + ); + } + const block = new AsyncDependenciesBlock( + { + ...this.options.groupOptions, + name: chunkName + }, + dep.loc, + dep.userRequest + ); + block.addDependency(dep); + this.addBlock(block); + } + } else { + callback( + new WebpackError(`Unsupported mode "${this.options.mode}" in context`) + ); + return; + } + compilation.fileSystemInfo.createSnapshot( + startTime, + null, + [this.context], + null, + SNAPSHOT_OPTIONS, + (err, snapshot) => { + if (err) return callback(err); + this.buildInfo.snapshot = snapshot; + callback(); + } + ); + }); } -} - -module.exports = EnvironmentPlugin; - - -/***/ }), -/***/ 22569: -/***/ (function(__unused_webpack_module, exports) { + /** + * @param {LazySet} fileDependencies set where file dependencies are added to + * @param {LazySet} contextDependencies set where context dependencies are added to + * @param {LazySet} missingDependencies set where missing dependencies are added to + * @param {LazySet} buildDependencies set where build dependencies are added to + */ + addCacheDependencies( + fileDependencies, + contextDependencies, + missingDependencies, + buildDependencies + ) { + contextDependencies.add(this.context); + } -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ - - - -const loaderFlag = "LOADER_EXECUTION"; - -const webpackOptionsFlag = "WEBPACK_OPTIONS"; - -exports.cutOffByFlag = (stack, flag) => { - stack = stack.split("\n"); - for (let i = 0; i < stack.length; i++) { - if (stack[i].includes(flag)) { - stack.length = i; + /** + * @param {ContextElementDependency[]} dependencies all dependencies + * @param {ChunkGraph} chunkGraph chunk graph + * @returns {TODO} TODO + */ + getUserRequestMap(dependencies, chunkGraph) { + const moduleGraph = chunkGraph.moduleGraph; + // if we filter first we get a new array + // therefore we don't need to create a clone of dependencies explicitly + // therefore the order of this is !important! + const sortedDependencies = dependencies + .filter(dependency => moduleGraph.getModule(dependency)) + .sort((a, b) => { + if (a.userRequest === b.userRequest) { + return 0; + } + return a.userRequest < b.userRequest ? -1 : 1; + }); + const map = Object.create(null); + for (const dep of sortedDependencies) { + const module = moduleGraph.getModule(dep); + map[dep.userRequest] = chunkGraph.getModuleId(module); } + return map; } - return stack.join("\n"); -}; -exports.cutOffLoaderExecution = stack => - exports.cutOffByFlag(stack, loaderFlag); + /** + * @param {ContextElementDependency[]} dependencies all dependencies + * @param {ChunkGraph} chunkGraph chunk graph + * @returns {TODO} TODO + */ + getFakeMap(dependencies, chunkGraph) { + if (!this.options.namespaceObject) { + return 9; + } + const moduleGraph = chunkGraph.moduleGraph; + // bitfield + let hasType = 0; + const comparator = compareModulesById(chunkGraph); + // if we filter first we get a new array + // therefore we don't need to create a clone of dependencies explicitly + // therefore the order of this is !important! + const sortedModules = dependencies + .map(dependency => moduleGraph.getModule(dependency)) + .filter(Boolean) + .sort(comparator); + const fakeMap = Object.create(null); + for (const module of sortedModules) { + const exportsType = module.getExportsType( + moduleGraph, + this.options.namespaceObject === "strict" + ); + const id = chunkGraph.getModuleId(module); + switch (exportsType) { + case "namespace": + fakeMap[id] = 9; + hasType |= 1; + break; + case "dynamic": + fakeMap[id] = 7; + hasType |= 2; + break; + case "default-only": + fakeMap[id] = 1; + hasType |= 4; + break; + case "default-with-named": + fakeMap[id] = 3; + hasType |= 8; + break; + default: + throw new Error(`Unexpected exports type ${exportsType}`); + } + } + if (hasType === 1) { + return 9; + } + if (hasType === 2) { + return 7; + } + if (hasType === 4) { + return 1; + } + if (hasType === 8) { + return 3; + } + if (hasType === 0) { + return 9; + } + return fakeMap; + } -exports.cutOffWebpackOptions = stack => - exports.cutOffByFlag(stack, webpackOptionsFlag); + getFakeMapInitStatement(fakeMap) { + return typeof fakeMap === "object" + ? `var fakeMap = ${JSON.stringify(fakeMap, null, "\t")};` + : ""; + } -exports.cutOffMultilineMessage = (stack, message) => { - stack = stack.split("\n"); - message = message.split("\n"); + getReturn(type, asyncModule) { + if (type === 9) { + return "__webpack_require__(id)"; + } + return `${RuntimeGlobals.createFakeNamespaceObject}(id, ${type}${ + asyncModule ? " | 16" : "" + })`; + } - const result = []; + getReturnModuleObjectSource( + fakeMap, + asyncModule, + fakeMapDataExpression = "fakeMap[id]" + ) { + if (typeof fakeMap === "number") { + return `return ${this.getReturn(fakeMap, asyncModule)};`; + } + return `return ${ + RuntimeGlobals.createFakeNamespaceObject + }(id, ${fakeMapDataExpression}${asyncModule ? " | 16" : ""})`; + } - stack.forEach((line, idx) => { - if (!line.includes(message[idx])) result.push(line); - }); + /** + * @param {TODO} dependencies TODO + * @param {TODO} id TODO + * @param {ChunkGraph} chunkGraph the chunk graph + * @returns {string} source code + */ + getSyncSource(dependencies, id, chunkGraph) { + const map = this.getUserRequestMap(dependencies, chunkGraph); + const fakeMap = this.getFakeMap(dependencies, chunkGraph); + const returnModuleObject = this.getReturnModuleObjectSource(fakeMap); - return result.join("\n"); -}; + return `var map = ${JSON.stringify(map, null, "\t")}; +${this.getFakeMapInitStatement(fakeMap)} -exports.cutOffMessage = (stack, message) => { - const nextLine = stack.indexOf("\n"); - if (nextLine === -1) { - return stack === message ? "" : stack; - } else { - const firstLine = stack.substr(0, nextLine); - return firstLine === message ? stack.substr(nextLine + 1) : stack; +function webpackContext(req) { + var id = webpackContextResolve(req); + ${returnModuleObject} +} +function webpackContextResolve(req) { + if(!${RuntimeGlobals.hasOwnProperty}(map, req)) { + var e = new Error("Cannot find module '" + req + "'"); + e.code = 'MODULE_NOT_FOUND'; + throw e; } + return map[req]; +} +webpackContext.keys = function webpackContextKeys() { + return Object.keys(map); }; +webpackContext.resolve = webpackContextResolve; +module.exports = webpackContext; +webpackContext.id = ${JSON.stringify(id)};`; + } -exports.cleanUp = (stack, message) => { - stack = exports.cutOffLoaderExecution(stack); - stack = exports.cutOffMessage(stack, message); - return stack; -}; - -exports.cleanUpWebpackOptions = (stack, message) => { - stack = exports.cutOffWebpackOptions(stack); - stack = exports.cutOffMultilineMessage(stack, message); - return stack; -}; - - -/***/ }), - -/***/ 4125: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ + /** + * @param {TODO} dependencies TODO + * @param {TODO} id TODO + * @param {ChunkGraph} chunkGraph the chunk graph + * @returns {string} source code + */ + getWeakSyncSource(dependencies, id, chunkGraph) { + const map = this.getUserRequestMap(dependencies, chunkGraph); + const fakeMap = this.getFakeMap(dependencies, chunkGraph); + const returnModuleObject = this.getReturnModuleObjectSource(fakeMap); + return `var map = ${JSON.stringify(map, null, "\t")}; +${this.getFakeMapInitStatement(fakeMap)} +function webpackContext(req) { + var id = webpackContextResolve(req); + if(!${RuntimeGlobals.moduleFactories}[id]) { + var e = new Error("Module '" + req + "' ('" + id + "') is not available (weak dependency)"); + e.code = 'MODULE_NOT_FOUND'; + throw e; + } + ${returnModuleObject} +} +function webpackContextResolve(req) { + if(!${RuntimeGlobals.hasOwnProperty}(map, req)) { + var e = new Error("Cannot find module '" + req + "'"); + e.code = 'MODULE_NOT_FOUND'; + throw e; + } + return map[req]; +} +webpackContext.keys = function webpackContextKeys() { + return Object.keys(map); +}; +webpackContext.resolve = webpackContextResolve; +webpackContext.id = ${JSON.stringify(id)}; +module.exports = webpackContext;`; + } -const { ConcatSource, RawSource } = __webpack_require__(96192); -const ExternalModule = __webpack_require__(89805); -const ModuleFilenameHelpers = __webpack_require__(80295); -const JavascriptModulesPlugin = __webpack_require__(76767); + /** + * @param {TODO} dependencies TODO + * @param {TODO} id TODO + * @param {Object} context context + * @param {ChunkGraph} context.chunkGraph the chunk graph + * @param {RuntimeTemplate} context.runtimeTemplate the chunk graph + * @returns {string} source code + */ + getAsyncWeakSource(dependencies, id, { chunkGraph, runtimeTemplate }) { + const arrow = runtimeTemplate.supportsArrowFunction(); + const map = this.getUserRequestMap(dependencies, chunkGraph); + const fakeMap = this.getFakeMap(dependencies, chunkGraph); + const returnModuleObject = this.getReturnModuleObjectSource(fakeMap, true); -/** @typedef {import("webpack-sources").Source} Source */ -/** @typedef {import("./Compiler")} Compiler */ + return `var map = ${JSON.stringify(map, null, "\t")}; +${this.getFakeMapInitStatement(fakeMap)} -/** @type {WeakMap} */ -const cache = new WeakMap(); +function webpackAsyncContext(req) { + return webpackAsyncContextResolve(req).then(${ + arrow ? "id =>" : "function(id)" + } { + if(!${RuntimeGlobals.moduleFactories}[id]) { + var e = new Error("Module '" + req + "' ('" + id + "') is not available (weak dependency)"); + e.code = 'MODULE_NOT_FOUND'; + throw e; + } + ${returnModuleObject} + }); +} +function webpackAsyncContextResolve(req) { + // Here Promise.resolve().then() is used instead of new Promise() to prevent + // uncaught exception popping up in devtools + return Promise.resolve().then(${arrow ? "() =>" : "function()"} { + if(!${RuntimeGlobals.hasOwnProperty}(map, req)) { + var e = new Error("Cannot find module '" + req + "'"); + e.code = 'MODULE_NOT_FOUND'; + throw e; + } + return map[req]; + }); +} +webpackAsyncContext.keys = ${runtimeTemplate.returningFunction( + "Object.keys(map)" + )}; +webpackAsyncContext.resolve = webpackAsyncContextResolve; +webpackAsyncContext.id = ${JSON.stringify(id)}; +module.exports = webpackAsyncContext;`; + } -const devtoolWarning = new RawSource(`/* - * ATTENTION: The "eval" devtool has been used (maybe by default in mode: "development"). - * This devtool is neither made for production nor for readable output files. - * It uses "eval()" calls to create a separate source file in the browser devtools. - * If you are trying to read the output file, select a different devtool (https://webpack.js.org/configuration/devtool/) - * or disable the default devtool with "devtool: false". - * If you are looking for production-ready output files, see mode: "production" (https://webpack.js.org/configuration/mode/). - */ -`); + /** + * @param {TODO} dependencies TODO + * @param {TODO} id TODO + * @param {Object} context context + * @param {ChunkGraph} context.chunkGraph the chunk graph + * @param {RuntimeTemplate} context.runtimeTemplate the chunk graph + * @returns {string} source code + */ + getEagerSource(dependencies, id, { chunkGraph, runtimeTemplate }) { + const arrow = runtimeTemplate.supportsArrowFunction(); + const map = this.getUserRequestMap(dependencies, chunkGraph); + const fakeMap = this.getFakeMap(dependencies, chunkGraph); + const thenFunction = + fakeMap !== 9 + ? `${arrow ? "id =>" : "function(id)"} { + ${this.getReturnModuleObjectSource(fakeMap)} + }` + : "__webpack_require__"; + return `var map = ${JSON.stringify(map, null, "\t")}; +${this.getFakeMapInitStatement(fakeMap)} -class EvalDevToolModulePlugin { - constructor(options) { - this.namespace = options.namespace || ""; - this.sourceUrlComment = options.sourceUrlComment || "\n//# sourceURL=[url]"; - this.moduleFilenameTemplate = - options.moduleFilenameTemplate || - "webpack://[namespace]/[resourcePath]?[loaders]"; +function webpackAsyncContext(req) { + return webpackAsyncContextResolve(req).then(${thenFunction}); +} +function webpackAsyncContextResolve(req) { + // Here Promise.resolve().then() is used instead of new Promise() to prevent + // uncaught exception popping up in devtools + return Promise.resolve().then(${arrow ? "() =>" : "function()"} { + if(!${RuntimeGlobals.hasOwnProperty}(map, req)) { + var e = new Error("Cannot find module '" + req + "'"); + e.code = 'MODULE_NOT_FOUND'; + throw e; + } + return map[req]; + }); +} +webpackAsyncContext.keys = ${runtimeTemplate.returningFunction( + "Object.keys(map)" + )}; +webpackAsyncContext.resolve = webpackAsyncContextResolve; +webpackAsyncContext.id = ${JSON.stringify(id)}; +module.exports = webpackAsyncContext;`; } /** - * Apply the plugin - * @param {Compiler} compiler the compiler instance - * @returns {void} + * @param {TODO} block TODO + * @param {TODO} dependencies TODO + * @param {TODO} id TODO + * @param {Object} options options object + * @param {RuntimeTemplate} options.runtimeTemplate the runtime template + * @param {ChunkGraph} options.chunkGraph the chunk graph + * @returns {string} source code */ - apply(compiler) { - compiler.hooks.compilation.tap("EvalDevToolModulePlugin", compilation => { - const hooks = JavascriptModulesPlugin.getCompilationHooks(compilation); - hooks.renderModuleContent.tap( - "EvalDevToolModulePlugin", - (source, module, { runtimeTemplate, chunkGraph }) => { - const cacheEntry = cache.get(source); - if (cacheEntry !== undefined) return cacheEntry; - if (module instanceof ExternalModule) { - cache.set(source, source); - return source; - } - const content = source.source(); - const str = ModuleFilenameHelpers.createFilename( - module, - { - moduleFilenameTemplate: this.moduleFilenameTemplate, - namespace: this.namespace - }, - { - requestShortener: runtimeTemplate.requestShortener, - chunkGraph, - hashFunction: compilation.outputOptions.hashFunction - } - ); - const footer = - "\n" + - this.sourceUrlComment.replace( - /\[url\]/g, - encodeURI(str) - .replace(/%2F/g, "/") - .replace(/%20/g, "_") - .replace(/%5E/g, "^") - .replace(/%5C/g, "\\") - .replace(/^\//, "") - ); - const result = new RawSource( - `eval(${JSON.stringify(content + footer)});` - ); - cache.set(source, result); - return result; - } - ); - hooks.inlineInRuntimeBailout.tap( - "EvalDevToolModulePlugin", - () => "the eval devtool is used." - ); - hooks.render.tap( - "EvalDevToolModulePlugin", - source => new ConcatSource(devtoolWarning, source) - ); - hooks.chunkHash.tap("EvalDevToolModulePlugin", (chunk, hash) => { - hash.update("EvalDevToolModulePlugin"); - hash.update("2"); - }); + getLazyOnceSource(block, dependencies, id, { runtimeTemplate, chunkGraph }) { + const promise = runtimeTemplate.blockPromise({ + chunkGraph, + block, + message: "lazy-once context", + runtimeRequirements: new Set() }); - } -} - -module.exports = EvalDevToolModulePlugin; - - -/***/ }), - -/***/ 42053: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ - - - -const { ConcatSource, RawSource } = __webpack_require__(96192); -const ModuleFilenameHelpers = __webpack_require__(80295); -const NormalModule = __webpack_require__(11026); -const SourceMapDevToolModuleOptionsPlugin = __webpack_require__(37661); -const JavascriptModulesPlugin = __webpack_require__(76767); -const ConcatenatedModule = __webpack_require__(1881); -const { makePathsAbsolute } = __webpack_require__(96236); - -/** @typedef {import("webpack-sources").Source} Source */ -/** @typedef {import("../declarations/WebpackOptions").DevTool} DevToolOptions */ -/** @typedef {import("../declarations/plugins/SourceMapDevToolPlugin").SourceMapDevToolPluginOptions} SourceMapDevToolPluginOptions */ -/** @typedef {import("./Compiler")} Compiler */ + const arrow = runtimeTemplate.supportsArrowFunction(); + const map = this.getUserRequestMap(dependencies, chunkGraph); + const fakeMap = this.getFakeMap(dependencies, chunkGraph); + const thenFunction = + fakeMap !== 9 + ? `${arrow ? "id =>" : "function(id)"} { + ${this.getReturnModuleObjectSource(fakeMap, true)}; + }` + : "__webpack_require__"; -/** @type {WeakMap} */ -const cache = new WeakMap(); + return `var map = ${JSON.stringify(map, null, "\t")}; +${this.getFakeMapInitStatement(fakeMap)} -const devtoolWarning = new RawSource(`/* - * ATTENTION: An "eval-source-map" devtool has been used. - * This devtool is neither made for production nor for readable output files. - * It uses "eval()" calls to create a separate source file with attached SourceMaps in the browser devtools. - * If you are trying to read the output file, select a different devtool (https://webpack.js.org/configuration/devtool/) - * or disable the default devtool with "devtool: false". - * If you are looking for production-ready output files, see mode: "production" (https://webpack.js.org/configuration/mode/). - */ -`); +function webpackAsyncContext(req) { + return webpackAsyncContextResolve(req).then(${thenFunction}); +} +function webpackAsyncContextResolve(req) { + return ${promise}.then(${arrow ? "() =>" : "function()"} { + if(!${RuntimeGlobals.hasOwnProperty}(map, req)) { + var e = new Error("Cannot find module '" + req + "'"); + e.code = 'MODULE_NOT_FOUND'; + throw e; + } + return map[req]; + }); +} +webpackAsyncContext.keys = ${runtimeTemplate.returningFunction( + "Object.keys(map)" + )}; +webpackAsyncContext.resolve = webpackAsyncContextResolve; +webpackAsyncContext.id = ${JSON.stringify(id)}; +module.exports = webpackAsyncContext;`; + } -class EvalSourceMapDevToolPlugin { /** - * @param {SourceMapDevToolPluginOptions|string} inputOptions Options object + * @param {TODO} blocks TODO + * @param {TODO} id TODO + * @param {Object} context context + * @param {ChunkGraph} context.chunkGraph the chunk graph + * @param {RuntimeTemplate} context.runtimeTemplate the chunk graph + * @returns {string} source code */ - constructor(inputOptions) { - /** @type {SourceMapDevToolPluginOptions} */ - let options; - if (typeof inputOptions === "string") { - options = { - append: inputOptions - }; - } else { - options = inputOptions; + getLazySource(blocks, id, { chunkGraph, runtimeTemplate }) { + const moduleGraph = chunkGraph.moduleGraph; + const arrow = runtimeTemplate.supportsArrowFunction(); + let hasMultipleOrNoChunks = false; + let hasNoChunk = true; + const fakeMap = this.getFakeMap( + blocks.map(b => b.dependencies[0]), + chunkGraph + ); + const hasFakeMap = typeof fakeMap === "object"; + const items = blocks + .map(block => { + const dependency = block.dependencies[0]; + return { + dependency: dependency, + module: moduleGraph.getModule(dependency), + block: block, + userRequest: dependency.userRequest, + chunks: undefined + }; + }) + .filter(item => item.module); + for (const item of items) { + const chunkGroup = chunkGraph.getBlockChunkGroup(item.block); + const chunks = (chunkGroup && chunkGroup.chunks) || []; + item.chunks = chunks; + if (chunks.length > 0) { + hasNoChunk = false; + } + if (chunks.length !== 1) { + hasMultipleOrNoChunks = true; + } } - this.sourceMapComment = - options.append || "//# sourceURL=[module]\n//# sourceMappingURL=[url]"; - this.moduleFilenameTemplate = - options.moduleFilenameTemplate || - "webpack://[namespace]/[resource-path]?[hash]"; - this.namespace = options.namespace || ""; - this.options = options; - } - - /** - * Apply the plugin - * @param {Compiler} compiler the compiler instance - * @returns {void} - */ - apply(compiler) { - const options = this.options; - compiler.hooks.compilation.tap( - "EvalSourceMapDevToolPlugin", - compilation => { - const hooks = JavascriptModulesPlugin.getCompilationHooks(compilation); - new SourceMapDevToolModuleOptionsPlugin(options).apply(compilation); - const matchModule = ModuleFilenameHelpers.matchObject.bind( - ModuleFilenameHelpers, - options - ); - hooks.renderModuleContent.tap( - "EvalSourceMapDevToolPlugin", - (source, m, { runtimeTemplate, chunkGraph }) => { - const cachedSource = cache.get(source); - if (cachedSource !== undefined) { - return cachedSource; - } - - const result = r => { - cache.set(source, r); - return r; - }; - - if (m instanceof NormalModule) { - const module = /** @type {NormalModule} */ (m); - if (!matchModule(module.resource)) { - return result(source); - } - } else if (m instanceof ConcatenatedModule) { - const concatModule = /** @type {ConcatenatedModule} */ (m); - if (concatModule.rootModule instanceof NormalModule) { - const module = /** @type {NormalModule} */ ( - concatModule.rootModule - ); - if (!matchModule(module.resource)) { - return result(source); - } - } else { - return result(source); - } - } else { - return result(source); - } - - /** @type {{ [key: string]: TODO; }} */ - let sourceMap; - let content; - if (source.sourceAndMap) { - const sourceAndMap = source.sourceAndMap(options); - sourceMap = sourceAndMap.map; - content = sourceAndMap.source; - } else { - sourceMap = source.map(options); - content = source.source(); - } - if (!sourceMap) { - return result(source); - } - - // Clone (flat) the sourcemap to ensure that the mutations below do not persist. - sourceMap = { ...sourceMap }; - const context = compiler.options.context; - const root = compiler.root; - const modules = sourceMap.sources.map(source => { - if (!source.startsWith("webpack://")) return source; - source = makePathsAbsolute(context, source.slice(10), root); - const module = compilation.findModule(source); - return module || source; - }); - let moduleFilenames = modules.map(module => { - return ModuleFilenameHelpers.createFilename( - module, - { - moduleFilenameTemplate: this.moduleFilenameTemplate, - namespace: this.namespace - }, - { - requestShortener: runtimeTemplate.requestShortener, - chunkGraph, - hashFunction: compilation.outputOptions.hashFunction - } - ); - }); - moduleFilenames = ModuleFilenameHelpers.replaceDuplicates( - moduleFilenames, - (filename, i, n) => { - for (let j = 0; j < n; j++) filename += "*"; - return filename; - } - ); - sourceMap.sources = moduleFilenames; - sourceMap.sourceRoot = options.sourceRoot || ""; - const moduleId = chunkGraph.getModuleId(m); - sourceMap.file = `${moduleId}.js`; - - const footer = - this.sourceMapComment.replace( - /\[url\]/g, - `data:application/json;charset=utf-8;base64,${Buffer.from( - JSON.stringify(sourceMap), - "utf8" - ).toString("base64")}` - ) + `\n//# sourceURL=webpack-internal:///${moduleId}\n`; // workaround for chrome bug - - return result( - new RawSource(`eval(${JSON.stringify(content + footer)});`) - ); - } - ); - hooks.inlineInRuntimeBailout.tap( - "EvalDevToolModulePlugin", - () => "the eval-source-map devtool is used." - ); - hooks.render.tap( - "EvalSourceMapDevToolPlugin", - source => new ConcatSource(devtoolWarning, source) + const shortMode = hasNoChunk && !hasFakeMap; + const sortedItems = items.sort((a, b) => { + if (a.userRequest === b.userRequest) return 0; + return a.userRequest < b.userRequest ? -1 : 1; + }); + const map = Object.create(null); + for (const item of sortedItems) { + const moduleId = chunkGraph.getModuleId(item.module); + if (shortMode) { + map[item.userRequest] = moduleId; + } else { + const arrayStart = [moduleId]; + if (hasFakeMap) { + arrayStart.push(fakeMap[moduleId]); + } + map[item.userRequest] = arrayStart.concat( + item.chunks.map(chunk => chunk.id) ); - hooks.chunkHash.tap("EvalSourceMapDevToolPlugin", (chunk, hash) => { - hash.update("EvalSourceMapDevToolPlugin"); - hash.update("2"); - }); } - ); - } -} - -module.exports = EvalSourceMapDevToolPlugin; - - -/***/ }), - -/***/ 4295: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ - - - -const { equals } = __webpack_require__(21537); -const SortableSet = __webpack_require__(67563); -const makeSerializable = __webpack_require__(26522); -const { forEachRuntime } = __webpack_require__(19655); - -/** @typedef {import("./Dependency").RuntimeSpec} RuntimeSpec */ -/** @typedef {import("./Module")} Module */ -/** @typedef {import("./ModuleGraph")} ModuleGraph */ -/** @typedef {import("./ModuleGraphConnection")} ModuleGraphConnection */ -/** @typedef {import("./util/Hash")} Hash */ - -/** @typedef {typeof UsageState.OnlyPropertiesUsed | typeof UsageState.NoInfo | typeof UsageState.Unknown | typeof UsageState.Used} RuntimeUsageStateType */ -/** @typedef {typeof UsageState.Unused | RuntimeUsageStateType} UsageStateType */ - -const UsageState = Object.freeze({ - Unused: /** @type {0} */ (0), - OnlyPropertiesUsed: /** @type {1} */ (1), - NoInfo: /** @type {2} */ (2), - Unknown: /** @type {3} */ (3), - Used: /** @type {4} */ (4) -}); + } -const RETURNS_TRUE = () => true; + const chunksStartPosition = hasFakeMap ? 2 : 1; + const requestPrefix = hasNoChunk + ? "Promise.resolve()" + : hasMultipleOrNoChunks + ? `Promise.all(ids.slice(${chunksStartPosition}).map(${RuntimeGlobals.ensureChunk}))` + : `${RuntimeGlobals.ensureChunk}(ids[${chunksStartPosition}])`; + const returnModuleObject = this.getReturnModuleObjectSource( + fakeMap, + true, + shortMode ? "invalid" : "ids[1]" + ); -const CIRCULAR = Symbol("circular target"); + const webpackAsyncContext = + requestPrefix === "Promise.resolve()" + ? ` +function webpackAsyncContext(req) { + return Promise.resolve().then(${arrow ? "() =>" : "function()"} { + if(!${RuntimeGlobals.hasOwnProperty}(map, req)) { + var e = new Error("Cannot find module '" + req + "'"); + e.code = 'MODULE_NOT_FOUND'; + throw e; + } -class RestoreProvidedData { - constructor( - exports, - otherProvided, - otherCanMangleProvide, - otherTerminalBinding - ) { - this.exports = exports; - this.otherProvided = otherProvided; - this.otherCanMangleProvide = otherCanMangleProvide; - this.otherTerminalBinding = otherTerminalBinding; + ${shortMode ? "var id = map[req];" : "var ids = map[req], id = ids[0];"} + ${returnModuleObject} + }); +}` + : `function webpackAsyncContext(req) { + if(!${RuntimeGlobals.hasOwnProperty}(map, req)) { + return Promise.resolve().then(${arrow ? "() =>" : "function()"} { + var e = new Error("Cannot find module '" + req + "'"); + e.code = 'MODULE_NOT_FOUND'; + throw e; + }); } - serialize({ write }) { - write(this.exports); - write(this.otherProvided); - write(this.otherCanMangleProvide); - write(this.otherTerminalBinding); - } + var ids = map[req], id = ids[0]; + return ${requestPrefix}.then(${arrow ? "() =>" : "function()"} { + ${returnModuleObject} + }); +}`; - static deserialize({ read }) { - return new RestoreProvidedData(read(), read(), read(), read()); + return `var map = ${JSON.stringify(map, null, "\t")}; +${webpackAsyncContext} +webpackAsyncContext.keys = ${runtimeTemplate.returningFunction( + "Object.keys(map)" + )}; +webpackAsyncContext.id = ${JSON.stringify(id)}; +module.exports = webpackAsyncContext;`; } -} - -makeSerializable( - RestoreProvidedData, - "webpack/lib/ModuleGraph", - "RestoreProvidedData" -); -class ExportsInfo { - constructor() { - /** @type {Map} */ - this._exports = new Map(); - this._otherExportsInfo = new ExportInfo(null); - this._sideEffectsOnlyInfo = new ExportInfo("*side effects only*"); - this._exportsAreOrdered = false; - /** @type {ExportsInfo=} */ - this._redirectTo = undefined; + getSourceForEmptyContext(id, runtimeTemplate) { + return `function webpackEmptyContext(req) { + var e = new Error("Cannot find module '" + req + "'"); + e.code = 'MODULE_NOT_FOUND'; + throw e; +} +webpackEmptyContext.keys = ${runtimeTemplate.returningFunction("[]")}; +webpackEmptyContext.resolve = webpackEmptyContext; +webpackEmptyContext.id = ${JSON.stringify(id)}; +module.exports = webpackEmptyContext;`; } - /** - * @returns {Iterable} all owned exports in any order - */ - get ownedExports() { - return this._exports.values(); + getSourceForEmptyAsyncContext(id, runtimeTemplate) { + const arrow = runtimeTemplate.supportsArrowFunction(); + return `function webpackEmptyAsyncContext(req) { + // Here Promise.resolve().then() is used instead of new Promise() to prevent + // uncaught exception popping up in devtools + return Promise.resolve().then(${arrow ? "() =>" : "function()"} { + var e = new Error("Cannot find module '" + req + "'"); + e.code = 'MODULE_NOT_FOUND'; + throw e; + }); +} +webpackEmptyAsyncContext.keys = ${runtimeTemplate.returningFunction("[]")}; +webpackEmptyAsyncContext.resolve = webpackEmptyAsyncContext; +webpackEmptyAsyncContext.id = ${JSON.stringify(id)}; +module.exports = webpackEmptyAsyncContext;`; } /** - * @returns {Iterable} all owned exports in order + * @param {string} asyncMode module mode + * @param {CodeGenerationContext} context context info + * @returns {string} the source code */ - get orderedOwnedExports() { - if (!this._exportsAreOrdered) { - this._sortExports(); + getSourceString(asyncMode, { runtimeTemplate, chunkGraph }) { + const id = chunkGraph.getModuleId(this); + if (asyncMode === "lazy") { + if (this.blocks && this.blocks.length > 0) { + return this.getLazySource(this.blocks, id, { + runtimeTemplate, + chunkGraph + }); + } + return this.getSourceForEmptyAsyncContext(id, runtimeTemplate); } - return this._exports.values(); + if (asyncMode === "eager") { + if (this.dependencies && this.dependencies.length > 0) { + return this.getEagerSource(this.dependencies, id, { + chunkGraph, + runtimeTemplate + }); + } + return this.getSourceForEmptyAsyncContext(id, runtimeTemplate); + } + if (asyncMode === "lazy-once") { + const block = this.blocks[0]; + if (block) { + return this.getLazyOnceSource(block, block.dependencies, id, { + runtimeTemplate, + chunkGraph + }); + } + return this.getSourceForEmptyAsyncContext(id, runtimeTemplate); + } + if (asyncMode === "async-weak") { + if (this.dependencies && this.dependencies.length > 0) { + return this.getAsyncWeakSource(this.dependencies, id, { + chunkGraph, + runtimeTemplate + }); + } + return this.getSourceForEmptyAsyncContext(id, runtimeTemplate); + } + if (asyncMode === "weak") { + if (this.dependencies && this.dependencies.length > 0) { + return this.getWeakSyncSource(this.dependencies, id, chunkGraph); + } + } + if (this.dependencies && this.dependencies.length > 0) { + return this.getSyncSource(this.dependencies, id, chunkGraph); + } + return this.getSourceForEmptyContext(id, runtimeTemplate); } - /** - * @returns {Iterable} all exports in any order - */ - get exports() { - if (this._redirectTo !== undefined) { - const map = new Map(this._redirectTo._exports); - for (const [key, value] of this._exports) { - map.set(key, value); - } - return map.values(); + getSource(sourceString) { + if (this.useSourceMap || this.useSimpleSourceMap) { + return new OriginalSource(sourceString, this.identifier()); } - return this._exports.values(); + return new RawSource(sourceString); } /** - * @returns {Iterable} all exports in order + * @param {CodeGenerationContext} context context for code generation + * @returns {CodeGenerationResult} result */ - get orderedExports() { - if (!this._exportsAreOrdered) { - this._sortExports(); - } - if (this._redirectTo !== undefined) { - const map = new Map( - Array.from(this._redirectTo.orderedExports, item => [item.name, item]) - ); - for (const [key, value] of this._exports) { - map.set(key, value); + codeGeneration(context) { + const { chunkGraph } = context; + const sources = new Map(); + sources.set( + "javascript", + this.getSource(this.getSourceString(this.options.mode, context)) + ); + const set = new Set(); + const allDeps = /** @type {ContextElementDependency[]} */ ( + this.dependencies.concat(this.blocks.map(b => b.dependencies[0])) + ); + set.add(RuntimeGlobals.module); + set.add(RuntimeGlobals.hasOwnProperty); + if (allDeps.length > 0) { + const asyncMode = this.options.mode; + set.add(RuntimeGlobals.require); + if (asyncMode === "weak") { + set.add(RuntimeGlobals.moduleFactories); + } else if (asyncMode === "async-weak") { + set.add(RuntimeGlobals.moduleFactories); + set.add(RuntimeGlobals.ensureChunk); + } else if (asyncMode === "lazy" || asyncMode === "lazy-once") { + set.add(RuntimeGlobals.ensureChunk); + } + if (this.getFakeMap(allDeps, chunkGraph) !== 9) { + set.add(RuntimeGlobals.createFakeNamespaceObject); } - // sorting should be pretty fast as map contains - // a lot of presorted items - this._sortExportsMap(map); - return map.values(); } - return this._exports.values(); + return { + sources, + runtimeRequirements: set + }; } /** - * @returns {ExportInfo} the export info of unlisted exports + * @param {string=} type the source type for which the size should be estimated + * @returns {number} the estimated size of the module (must be non-zero) */ - get otherExportsInfo() { - if (this._redirectTo !== undefined) - return this._redirectTo.otherExportsInfo; - return this._otherExportsInfo; - } + size(type) { + // base penalty + let size = 160; - _sortExportsMap(exports) { - if (exports.size > 1) { - const namesInOrder = []; - for (const entry of exports.values()) { - namesInOrder.push(entry.name); - } - namesInOrder.sort(); - let i = 0; - for (const entry of exports.values()) { - const name = namesInOrder[i]; - if (entry.name !== name) break; - i++; - } - for (; i < namesInOrder.length; i++) { - const name = namesInOrder[i]; - const correctEntry = exports.get(name); - exports.delete(name); - exports.set(name, correctEntry); - } + // if we don't have dependencies we stop here. + for (const dependency of this.dependencies) { + const element = /** @type {ContextElementDependency} */ (dependency); + size += 5 + element.userRequest.length; } + return size; } - _sortExports() { - this._sortExportsMap(this._exports); - this._exportsAreOrdered = true; + serialize(context) { + const { write } = context; + write(this._identifier); + write(this._forceBuild); + super.serialize(context); } - setRedirectNamedTo(exportsInfo) { - if (this._redirectTo === exportsInfo) return false; - this._redirectTo = exportsInfo; - return true; + deserialize(context) { + const { read } = context; + this._identifier = read(); + this._forceBuild = read(); + super.deserialize(context); } +} - setHasProvideInfo() { - for (const exportInfo of this._exports.values()) { - if (exportInfo.provided === undefined) { - exportInfo.provided = false; - } - if (exportInfo.canMangleProvide === undefined) { - exportInfo.canMangleProvide = true; - } - } - if (this._redirectTo !== undefined) { - this._redirectTo.setHasProvideInfo(); - } else { - if (this._otherExportsInfo.provided === undefined) { - this._otherExportsInfo.provided = false; - } - if (this._otherExportsInfo.canMangleProvide === undefined) { - this._otherExportsInfo.canMangleProvide = true; - } - } - } - - setHasUseInfo() { - for (const exportInfo of this._exports.values()) { - exportInfo.setHasUseInfo(); - } - this._sideEffectsOnlyInfo.setHasUseInfo(); - if (this._redirectTo !== undefined) { - this._redirectTo.setHasUseInfo(); - } else { - this._otherExportsInfo.setHasUseInfo(); - if (this._otherExportsInfo.canMangleUse === undefined) { - this._otherExportsInfo.canMangleUse = true; - } - } - } - - /** - * @param {string} name export name - * @returns {ExportInfo} export info for this name - */ - getOwnExportInfo(name) { - const info = this._exports.get(name); - if (info !== undefined) return info; - const newInfo = new ExportInfo(name, this._otherExportsInfo); - this._exports.set(name, newInfo); - this._exportsAreOrdered = false; - return newInfo; - } +makeSerializable(ContextModule, "webpack/lib/ContextModule"); - /** - * @param {string} name export name - * @returns {ExportInfo} export info for this name - */ - getExportInfo(name) { - const info = this._exports.get(name); - if (info !== undefined) return info; - if (this._redirectTo !== undefined) - return this._redirectTo.getExportInfo(name); - const newInfo = new ExportInfo(name, this._otherExportsInfo); - this._exports.set(name, newInfo); - this._exportsAreOrdered = false; - return newInfo; - } +module.exports = ContextModule; - /** - * @param {string} name export name - * @returns {ExportInfo} export info for this name - */ - getReadOnlyExportInfo(name) { - const info = this._exports.get(name); - if (info !== undefined) return info; - if (this._redirectTo !== undefined) - return this._redirectTo.getReadOnlyExportInfo(name); - return this._otherExportsInfo; - } - /** - * @param {string[]} name export name - * @returns {ExportInfo | undefined} export info for this name - */ - getReadOnlyExportInfoRecursive(name) { - const exportInfo = this.getReadOnlyExportInfo(name[0]); - if (name.length === 1) return exportInfo; - if (!exportInfo.exportsInfo) return undefined; - return exportInfo.exportsInfo.getReadOnlyExportInfoRecursive(name.slice(1)); - } +/***/ }), - /** - * @param {string[]=} name the export name - * @returns {ExportsInfo | undefined} the nested exports info - */ - getNestedExportsInfo(name) { - if (Array.isArray(name) && name.length > 0) { - const info = this.getReadOnlyExportInfo(name[0]); - if (!info.exportsInfo) return undefined; - return info.exportsInfo.getNestedExportsInfo(name.slice(1)); - } - return this; - } +/***/ 26268: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - /** - * @param {boolean=} canMangle true, if exports can still be mangled (defaults to false) - * @param {Set=} excludeExports list of unaffected exports - * @param {any=} targetKey use this as key for the target - * @param {ModuleGraphConnection=} targetModule set this module as target - * @param {number=} priority priority - * @returns {boolean} true, if this call changed something - */ - setUnknownExportsProvided( - canMangle, - excludeExports, - targetKey, - targetModule, - priority - ) { - let changed = false; - if (excludeExports) { - for (const name of excludeExports) { - // Make sure these entries exist, so they can get different info - this.getExportInfo(name); - } - } - for (const exportInfo of this._exports.values()) { - if (excludeExports && excludeExports.has(exportInfo.name)) continue; - if (exportInfo.provided !== true && exportInfo.provided !== null) { - exportInfo.provided = null; - changed = true; - } - if (!canMangle && exportInfo.canMangleProvide !== false) { - exportInfo.canMangleProvide = false; - changed = true; - } - if (targetKey) { - exportInfo.setTarget(targetKey, targetModule, [exportInfo.name], -1); - } - } - if (this._redirectTo !== undefined) { - if ( - this._redirectTo.setUnknownExportsProvided( - canMangle, - excludeExports, - targetKey, - targetModule, - priority - ) - ) { - changed = true; - } - } else { - if ( - this._otherExportsInfo.provided !== true && - this._otherExportsInfo.provided !== null - ) { - this._otherExportsInfo.provided = null; - changed = true; - } - if (!canMangle && this._otherExportsInfo.canMangleProvide !== false) { - this._otherExportsInfo.canMangleProvide = false; - changed = true; - } - if (targetKey) { - this._otherExportsInfo.setTarget( - targetKey, - targetModule, - undefined, - priority - ); - } - } - return changed; - } +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ - /** - * @param {RuntimeSpec} runtime the runtime - * @returns {boolean} true, when something changed - */ - setUsedInUnknownWay(runtime) { - let changed = false; - for (const exportInfo of this._exports.values()) { - if (exportInfo.setUsedInUnknownWay(runtime)) { - changed = true; - } - } - if (this._redirectTo !== undefined) { - if (this._redirectTo.setUsedInUnknownWay(runtime)) { - changed = true; - } - } else { - if ( - this._otherExportsInfo.setUsedConditionally( - used => used < UsageState.Unknown, - UsageState.Unknown, - runtime - ) - ) { - changed = true; - } - if (this._otherExportsInfo.canMangleUse !== false) { - this._otherExportsInfo.canMangleUse = false; - changed = true; - } - } - return changed; - } - /** - * @param {RuntimeSpec} runtime the runtime - * @returns {boolean} true, when something changed - */ - setUsedWithoutInfo(runtime) { - let changed = false; - for (const exportInfo of this._exports.values()) { - if (exportInfo.setUsedWithoutInfo(runtime)) { - changed = true; - } - } - if (this._redirectTo !== undefined) { - if (this._redirectTo.setUsedWithoutInfo(runtime)) { - changed = true; - } - } else { - if (this._otherExportsInfo.setUsed(UsageState.NoInfo, runtime)) { - changed = true; - } - if (this._otherExportsInfo.canMangleUse !== false) { - this._otherExportsInfo.canMangleUse = false; - changed = true; - } - } - return changed; - } - /** - * @param {RuntimeSpec} runtime the runtime - * @returns {boolean} true, when something changed - */ - setAllKnownExportsUsed(runtime) { - let changed = false; - for (const exportInfo of this._exports.values()) { - if (!exportInfo.provided) continue; - if (exportInfo.setUsed(UsageState.Used, runtime)) { - changed = true; - } - } - return changed; - } +const asyncLib = __webpack_require__(36386); +const { AsyncSeriesWaterfallHook, SyncWaterfallHook } = __webpack_require__(34718); +const ContextModule = __webpack_require__(80207); +const ModuleFactory = __webpack_require__(61574); +const ContextElementDependency = __webpack_require__(83853); +const LazySet = __webpack_require__(59534); +const { cachedSetProperty } = __webpack_require__(11217); +const { createFakeHook } = __webpack_require__(2594); +const { join } = __webpack_require__(93204); - /** - * @param {RuntimeSpec} runtime the runtime - * @returns {boolean} true, when something changed - */ - setUsedForSideEffectsOnly(runtime) { - return this._sideEffectsOnlyInfo.setUsedConditionally( - used => used === UsageState.Unused, - UsageState.Used, - runtime - ); - } +/** @typedef {import("./ContextModule").ContextModuleOptions} ContextModuleOptions */ +/** @typedef {import("./ContextModule").ResolveDependenciesCallback} ResolveDependenciesCallback */ +/** @typedef {import("./Module")} Module */ +/** @typedef {import("./ModuleFactory").ModuleFactoryCreateData} ModuleFactoryCreateData */ +/** @typedef {import("./ModuleFactory").ModuleFactoryResult} ModuleFactoryResult */ +/** @typedef {import("./ResolverFactory")} ResolverFactory */ +/** @typedef {import("./dependencies/ContextDependency")} ContextDependency */ +/** @template T @typedef {import("./util/deprecation").FakeHook} FakeHook */ +/** @typedef {import("./util/fs").InputFileSystem} InputFileSystem */ - /** - * @param {RuntimeSpec} runtime the runtime - * @returns {boolean} true, when the module exports are used in any way - */ - isUsed(runtime) { - if (this._redirectTo !== undefined) { - if (this._redirectTo.isUsed(runtime)) { - return true; - } - } else { - if (this._otherExportsInfo.getUsed(runtime) !== UsageState.Unused) { - return true; - } - } - for (const exportInfo of this._exports.values()) { - if (exportInfo.getUsed(runtime) !== UsageState.Unused) { - return true; - } - } - return false; - } +const EMPTY_RESOLVE_OPTIONS = {}; +module.exports = class ContextModuleFactory extends ModuleFactory { /** - * @param {RuntimeSpec} runtime the runtime - * @returns {boolean} true, when the module is used in any way + * @param {ResolverFactory} resolverFactory resolverFactory */ - isModuleUsed(runtime) { - if (this.isUsed(runtime)) return true; - if (this._sideEffectsOnlyInfo.getUsed(runtime) !== UsageState.Unused) - return true; - return false; + constructor(resolverFactory) { + super(); + /** @type {AsyncSeriesWaterfallHook<[TODO[], ContextModuleOptions]>} */ + const alternativeRequests = new AsyncSeriesWaterfallHook([ + "modules", + "options" + ]); + this.hooks = Object.freeze({ + /** @type {AsyncSeriesWaterfallHook<[TODO]>} */ + beforeResolve: new AsyncSeriesWaterfallHook(["data"]), + /** @type {AsyncSeriesWaterfallHook<[TODO]>} */ + afterResolve: new AsyncSeriesWaterfallHook(["data"]), + /** @type {SyncWaterfallHook<[string[]]>} */ + contextModuleFiles: new SyncWaterfallHook(["files"]), + /** @type {FakeHook, "tap" | "tapAsync" | "tapPromise" | "name">>} */ + alternatives: createFakeHook( + { + name: "alternatives", + /** @type {AsyncSeriesWaterfallHook<[TODO[]]>["intercept"]} */ + intercept: interceptor => { + throw new Error( + "Intercepting fake hook ContextModuleFactory.hooks.alternatives is not possible, use ContextModuleFactory.hooks.alternativeRequests instead" + ); + }, + /** @type {AsyncSeriesWaterfallHook<[TODO[]]>["tap"]} */ + tap: (options, fn) => { + alternativeRequests.tap(options, fn); + }, + /** @type {AsyncSeriesWaterfallHook<[TODO[]]>["tapAsync"]} */ + tapAsync: (options, fn) => { + alternativeRequests.tapAsync(options, (items, _options, callback) => + fn(items, callback) + ); + }, + /** @type {AsyncSeriesWaterfallHook<[TODO[]]>["tapPromise"]} */ + tapPromise: (options, fn) => { + alternativeRequests.tapPromise(options, fn); + } + }, + "ContextModuleFactory.hooks.alternatives has deprecated in favor of ContextModuleFactory.hooks.alternativeRequests with an additional options argument.", + "DEP_WEBPACK_CONTEXT_MODULE_FACTORY_ALTERNATIVES" + ), + alternativeRequests + }); + this.resolverFactory = resolverFactory; } /** - * @param {RuntimeSpec} runtime the runtime - * @returns {SortableSet | boolean | null} set of used exports, or true (when namespace object is used), or false (when unused), or null (when unknown) + * @param {ModuleFactoryCreateData} data data object + * @param {function(Error=, ModuleFactoryResult=): void} callback callback + * @returns {void} */ - getUsedExports(runtime) { - if (!this._redirectTo !== undefined) { - switch (this._otherExportsInfo.getUsed(runtime)) { - case UsageState.NoInfo: - return null; - case UsageState.Unknown: - case UsageState.OnlyPropertiesUsed: - case UsageState.Used: - return true; - } - } - const array = []; - if (!this._exportsAreOrdered) this._sortExports(); - for (const exportInfo of this._exports.values()) { - switch (exportInfo.getUsed(runtime)) { - case UsageState.NoInfo: - return null; - case UsageState.Unknown: - return true; - case UsageState.OnlyPropertiesUsed: - case UsageState.Used: - array.push(exportInfo.name); - } - } - if (this._redirectTo !== undefined) { - const inner = this._redirectTo.getUsedExports(runtime); - if (inner === null) return null; - if (inner === true) return true; - if (inner !== false) { - for (const item of inner) { - array.push(item); + create(data, callback) { + const context = data.context; + const dependencies = data.dependencies; + const resolveOptions = data.resolveOptions; + const dependency = /** @type {ContextDependency} */ (dependencies[0]); + const fileDependencies = new LazySet(); + const missingDependencies = new LazySet(); + const contextDependencies = new LazySet(); + this.hooks.beforeResolve.callAsync( + { + context: context, + dependencies: dependencies, + resolveOptions, + fileDependencies, + missingDependencies, + contextDependencies, + ...dependency.options + }, + (err, beforeResolveResult) => { + if (err) { + return callback(err, { + fileDependencies, + missingDependencies, + contextDependencies + }); } - } - } - if (array.length === 0) { - switch (this._sideEffectsOnlyInfo.getUsed(runtime)) { - case UsageState.NoInfo: - return null; - case UsageState.Unused: - return false; - } - } - return new SortableSet(array); - } - /** - * @returns {null | true | string[]} list of exports when known - */ - getProvidedExports() { - if (!this._redirectTo !== undefined) { - switch (this._otherExportsInfo.provided) { - case undefined: - return null; - case null: - return true; - case true: - return true; - } - } - const array = []; - if (!this._exportsAreOrdered) this._sortExports(); - for (const exportInfo of this._exports.values()) { - switch (exportInfo.provided) { - case undefined: - return null; - case null: - return true; - case true: - array.push(exportInfo.name); - } - } - if (this._redirectTo !== undefined) { - const inner = this._redirectTo.getProvidedExports(); - if (inner === null) return null; - if (inner === true) return true; - for (const item of inner) { - if (!array.includes(item)) { - array.push(item); + // Ignored + if (!beforeResolveResult) { + return callback(null, { + fileDependencies, + missingDependencies, + contextDependencies + }); } - } - } - return array; - } - - /** - * @param {RuntimeSpec} runtime the runtime - * @returns {ExportInfo[]} exports that are relevant (not unused and potential provided) - */ - getRelevantExports(runtime) { - const list = []; - for (const exportInfo of this._exports.values()) { - const used = exportInfo.getUsed(runtime); - if (used === UsageState.Unused) continue; - if (exportInfo.provided === false) continue; - list.push(exportInfo); - } - if (this._redirectTo !== undefined) { - for (const exportInfo of this._redirectTo.getRelevantExports(runtime)) { - if (!this._exports.has(exportInfo.name)) list.push(exportInfo); - } - } - if ( - this._otherExportsInfo.provided !== false && - this._otherExportsInfo.getUsed(runtime) !== UsageState.Unused - ) { - list.push(this._otherExportsInfo); - } - return list; - } - /** - * @param {string | string[]} name the name of the export - * @returns {boolean | undefined | null} if the export is provided - */ - isExportProvided(name) { - if (Array.isArray(name)) { - const info = this.getReadOnlyExportInfo(name[0]); - if (info.exportsInfo && name.length > 1) { - return info.exportsInfo.isExportProvided(name.slice(1)); - } - return info.provided; - } - const info = this.getReadOnlyExportInfo(name); - return info.provided; - } + const context = beforeResolveResult.context; + const request = beforeResolveResult.request; + const resolveOptions = beforeResolveResult.resolveOptions; - /** - * @param {RuntimeSpec} runtime runtime - * @returns {string} key representing the usage - */ - getUsageKey(runtime) { - const key = []; - if (this._redirectTo !== undefined) { - key.push(this._redirectTo.getUsageKey(runtime)); - } else { - key.push(this._otherExportsInfo.getUsed(runtime)); - } - key.push(this._sideEffectsOnlyInfo.getUsed(runtime)); - for (const exportInfo of this.orderedOwnedExports) { - key.push(exportInfo.getUsed(runtime)); - } - return key.join("|"); - } + let loaders, + resource, + loadersPrefix = ""; + const idx = request.lastIndexOf("!"); + if (idx >= 0) { + let loadersRequest = request.substr(0, idx + 1); + let i; + for ( + i = 0; + i < loadersRequest.length && loadersRequest[i] === "!"; + i++ + ) { + loadersPrefix += "!"; + } + loadersRequest = loadersRequest + .substr(i) + .replace(/!+$/, "") + .replace(/!!+/g, "!"); + if (loadersRequest === "") { + loaders = []; + } else { + loaders = loadersRequest.split("!"); + } + resource = request.substr(idx + 1); + } else { + loaders = []; + resource = request; + } - /** - * @param {RuntimeSpec} runtimeA first runtime - * @param {RuntimeSpec} runtimeB second runtime - * @returns {boolean} true, when equally used - */ - isEquallyUsed(runtimeA, runtimeB) { - if (this._redirectTo !== undefined) { - if (!this._redirectTo.isEquallyUsed(runtimeA, runtimeB)) return false; - } else { - if ( - this._otherExportsInfo.getUsed(runtimeA) !== - this._otherExportsInfo.getUsed(runtimeB) - ) { - return false; - } - } - if ( - this._sideEffectsOnlyInfo.getUsed(runtimeA) !== - this._sideEffectsOnlyInfo.getUsed(runtimeB) - ) { - return false; - } - for (const exportInfo of this.ownedExports) { - if (exportInfo.getUsed(runtimeA) !== exportInfo.getUsed(runtimeB)) - return false; - } - return true; - } + const contextResolver = this.resolverFactory.get( + "context", + dependencies.length > 0 + ? cachedSetProperty( + resolveOptions || EMPTY_RESOLVE_OPTIONS, + "dependencyType", + dependencies[0].category + ) + : resolveOptions + ); + const loaderResolver = this.resolverFactory.get("loader"); - /** - * @param {string | string[]} name export name - * @param {RuntimeSpec} runtime check usage for this runtime only - * @returns {UsageStateType} usage status - */ - getUsed(name, runtime) { - if (Array.isArray(name)) { - if (name.length === 0) return this.otherExportsInfo.getUsed(runtime); - let info = this.getReadOnlyExportInfo(name[0]); - if (info.exportsInfo && name.length > 1) { - return info.exportsInfo.getUsed(name.slice(1), runtime); - } - return info.getUsed(runtime); - } - let info = this.getReadOnlyExportInfo(name); - return info.getUsed(runtime); - } + asyncLib.parallel( + [ + callback => { + contextResolver.resolve( + {}, + context, + resource, + { + fileDependencies, + missingDependencies, + contextDependencies + }, + (err, result) => { + if (err) return callback(err); + callback(null, result); + } + ); + }, + callback => { + asyncLib.map( + loaders, + (loader, callback) => { + loaderResolver.resolve( + {}, + context, + loader, + { + fileDependencies, + missingDependencies, + contextDependencies + }, + (err, result) => { + if (err) return callback(err); + callback(null, result); + } + ); + }, + callback + ); + } + ], + (err, result) => { + if (err) { + return callback(err, { + fileDependencies, + missingDependencies, + contextDependencies + }); + } - /** - * @param {string | string[]} name the export name - * @param {RuntimeSpec} runtime check usage for this runtime only - * @returns {string | string[] | false} the used name - */ - getUsedName(name, runtime) { - if (Array.isArray(name)) { - // TODO improve this - if (name.length === 0) { - if (!this.isUsed(runtime)) return false; - return name; - } - let info = this.getReadOnlyExportInfo(name[0]); - const x = info.getUsedName(name[0], runtime); - if (x === false) return false; - const arr = x === name[0] && name.length === 1 ? name : [x]; - if (name.length === 1) { - return arr; - } - if ( - info.exportsInfo && - info.getUsed(runtime) === UsageState.OnlyPropertiesUsed - ) { - const nested = info.exportsInfo.getUsedName(name.slice(1), runtime); - if (!nested) return false; - return arr.concat(nested); - } else { - return arr.concat(name.slice(1)); + this.hooks.afterResolve.callAsync( + { + addon: + loadersPrefix + + result[1].join("!") + + (result[1].length > 0 ? "!" : ""), + resource: result[0], + resolveDependencies: this.resolveDependencies.bind(this), + ...beforeResolveResult + }, + (err, result) => { + if (err) { + return callback(err, { + fileDependencies, + missingDependencies, + contextDependencies + }); + } + + // Ignored + if (!result) { + return callback(null, { + fileDependencies, + missingDependencies, + contextDependencies + }); + } + + return callback(null, { + module: new ContextModule(result.resolveDependencies, result), + fileDependencies, + missingDependencies, + contextDependencies + }); + } + ); + } + ); } - } else { - let info = this.getReadOnlyExportInfo(name); - const usedName = info.getUsedName(name, runtime); - return usedName; - } + ); } /** - * @param {Hash} hash the hash - * @param {RuntimeSpec} runtime the runtime + * @param {InputFileSystem} fs file system + * @param {ContextModuleOptions} options options + * @param {ResolveDependenciesCallback} callback callback function * @returns {void} */ - updateHash(hash, runtime) { - this._updateHash(hash, runtime, new Set()); - } + resolveDependencies(fs, options, callback) { + const cmf = this; + const { + resource, + resourceQuery, + resourceFragment, + recursive, + regExp, + include, + exclude, + referencedExports, + category, + typePrefix + } = options; + if (!regExp || !resource) return callback(null, []); - /** - * @param {Hash} hash the hash - * @param {RuntimeSpec} runtime the runtime - * @param {Set} alreadyVisitedExportsInfo for circular references - * @returns {void} - */ - _updateHash(hash, runtime, alreadyVisitedExportsInfo) { - const set = new Set(alreadyVisitedExportsInfo); - set.add(this); - for (const exportInfo of this.orderedExports) { - if (exportInfo.hasInfo(this._otherExportsInfo, runtime)) { - exportInfo._updateHash(hash, runtime, set); - } - } - this._sideEffectsOnlyInfo._updateHash(hash, runtime, set); - this._otherExportsInfo._updateHash(hash, runtime, set); - if (this._redirectTo !== undefined) { - this._redirectTo._updateHash(hash, runtime, set); - } - } + const addDirectoryChecked = (directory, visited, callback) => { + fs.realpath(directory, (err, realPath) => { + if (err) return callback(err); + if (visited.has(realPath)) return callback(null, []); + let recursionStack; + addDirectory( + directory, + (dir, callback) => { + if (recursionStack === undefined) { + recursionStack = new Set(visited); + recursionStack.add(realPath); + } + addDirectoryChecked(dir, recursionStack, callback); + }, + callback + ); + }); + }; - getRestoreProvidedData() { - const otherProvided = this._otherExportsInfo.provided; - const otherCanMangleProvide = this._otherExportsInfo.canMangleProvide; - const otherTerminalBinding = this._otherExportsInfo.terminalBinding; - const exports = []; - for (const exportInfo of this.orderedExports) { - if ( - exportInfo.provided !== otherProvided || - exportInfo.canMangleProvide !== otherCanMangleProvide || - exportInfo.terminalBinding !== otherTerminalBinding || - exportInfo.exportsInfoOwned - ) { - exports.push({ - name: exportInfo.name, - provided: exportInfo.provided, - canMangleProvide: exportInfo.canMangleProvide, - terminalBinding: exportInfo.terminalBinding, - exportsInfo: exportInfo.exportsInfoOwned - ? exportInfo.exportsInfo.getRestoreProvidedData() - : undefined - }); - } + const addDirectory = (directory, addSubDirectory, callback) => { + fs.readdir(directory, (err, files) => { + if (err) return callback(err); + const processedFiles = cmf.hooks.contextModuleFiles.call( + /** @type {string[]} */ (files).map(file => file.normalize("NFC")) + ); + if (!processedFiles || processedFiles.length === 0) + return callback(null, []); + asyncLib.map( + processedFiles.filter(p => p.indexOf(".") !== 0), + (segment, callback) => { + const subResource = join(fs, directory, segment); + + if (!exclude || !subResource.match(exclude)) { + fs.stat(subResource, (err, stat) => { + if (err) { + if (err.code === "ENOENT") { + // ENOENT is ok here because the file may have been deleted between + // the readdir and stat calls. + return callback(); + } else { + return callback(err); + } + } + + if (stat.isDirectory()) { + if (!recursive) return callback(); + addSubDirectory(subResource, callback); + } else if ( + stat.isFile() && + (!include || subResource.match(include)) + ) { + const obj = { + context: resource, + request: + "." + + subResource.substr(resource.length).replace(/\\/g, "/") + }; + + this.hooks.alternativeRequests.callAsync( + [obj], + options, + (err, alternatives) => { + if (err) return callback(err); + alternatives = alternatives + .filter(obj => regExp.test(obj.request)) + .map(obj => { + const dep = new ContextElementDependency( + obj.request + resourceQuery + resourceFragment, + obj.request, + typePrefix, + category, + referencedExports + ); + dep.optional = true; + return dep; + }); + callback(null, alternatives); + } + ); + } else { + callback(); + } + }); + } else { + callback(); + } + }, + (err, result) => { + if (err) return callback(err); + + if (!result) return callback(null, []); + + const flattenedResult = []; + + for (const item of result) { + if (item) flattenedResult.push(...item); + } + + callback(null, flattenedResult); + } + ); + }); + }; + + if (typeof fs.realpath === "function") { + addDirectoryChecked(resource, new Set(), callback); + } else { + const addSubDirectory = (dir, callback) => + addDirectory(dir, addSubDirectory, callback); + addDirectory(resource, addSubDirectory, callback); } - return new RestoreProvidedData( - exports, - otherProvided, - otherCanMangleProvide, - otherTerminalBinding - ); } +}; - restoreProvided({ - otherProvided, - otherCanMangleProvide, - otherTerminalBinding, - exports - }) { - let wasEmpty = true; - for (const exportInfo of this._exports.values()) { - wasEmpty = false; - exportInfo.provided = otherProvided; - exportInfo.canMangleProvide = otherCanMangleProvide; - exportInfo.terminalBinding = otherTerminalBinding; - } - this._otherExportsInfo.provided = otherProvided; - this._otherExportsInfo.canMangleProvide = otherCanMangleProvide; - this._otherExportsInfo.terminalBinding = otherTerminalBinding; - for (const exp of exports) { - const exportInfo = this.getExportInfo(exp.name); - exportInfo.provided = exp.provided; - exportInfo.canMangleProvide = exp.canMangleProvide; - exportInfo.terminalBinding = exp.terminalBinding; - if (exp.exportsInfo) { - const exportsInfo = exportInfo.createNestedExportsInfo(); - exportsInfo.restoreProvided(exp.exportsInfo); + +/***/ }), + +/***/ 21542: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ + + + +const ContextElementDependency = __webpack_require__(83853); +const { join } = __webpack_require__(93204); + +class ContextReplacementPlugin { + constructor( + resourceRegExp, + newContentResource, + newContentRecursive, + newContentRegExp + ) { + this.resourceRegExp = resourceRegExp; + + if (typeof newContentResource === "function") { + this.newContentCallback = newContentResource; + } else if ( + typeof newContentResource === "string" && + typeof newContentRecursive === "object" + ) { + this.newContentResource = newContentResource; + this.newContentCreateContextMap = (fs, callback) => { + callback(null, newContentRecursive); + }; + } else if ( + typeof newContentResource === "string" && + typeof newContentRecursive === "function" + ) { + this.newContentResource = newContentResource; + this.newContentCreateContextMap = newContentRecursive; + } else { + if (typeof newContentResource !== "string") { + newContentRegExp = newContentRecursive; + newContentRecursive = newContentResource; + newContentResource = undefined; } + if (typeof newContentRecursive !== "boolean") { + newContentRegExp = newContentRecursive; + newContentRecursive = undefined; + } + this.newContentResource = newContentResource; + this.newContentRecursive = newContentRecursive; + this.newContentRegExp = newContentRegExp; } - if (wasEmpty) this._exportsAreOrdered = true; } -} -class ExportInfo { - /** - * @param {string} name the original name of the export - * @param {ExportInfo=} initFrom init values from this ExportInfo - */ - constructor(name, initFrom) { - /** @type {string} */ - this.name = name; - /** @private @type {string | null} */ - this._usedName = initFrom ? initFrom._usedName : null; - /** @private @type {UsageStateType} */ - this._globalUsed = initFrom ? initFrom._globalUsed : undefined; - /** @private @type {Map} */ - this._usedInRuntime = - initFrom && initFrom._usedInRuntime - ? new Map(initFrom._usedInRuntime) - : undefined; - /** @private @type {boolean} */ - this._hasUseInRuntimeInfo = initFrom - ? initFrom._hasUseInRuntimeInfo - : false; - /** - * true: it is provided - * false: it is not provided - * null: only the runtime knows if it is provided - * undefined: it was not determined if it is provided - * @type {boolean | null | undefined} - */ - this.provided = initFrom ? initFrom.provided : undefined; - /** - * is the export a terminal binding that should be checked for export star conflicts - * @type {boolean} - */ - this.terminalBinding = initFrom ? initFrom.terminalBinding : false; - /** - * true: it can be mangled - * false: is can not be mangled - * undefined: it was not determined if it can be mangled - * @type {boolean | undefined} - */ - this.canMangleProvide = initFrom ? initFrom.canMangleProvide : undefined; - /** - * true: it can be mangled - * false: is can not be mangled - * undefined: it was not determined if it can be mangled - * @type {boolean | undefined} - */ - this.canMangleUse = initFrom ? initFrom.canMangleUse : undefined; - /** @type {boolean} */ - this.exportsInfoOwned = false; - /** @type {ExportsInfo=} */ - this.exportsInfo = undefined; - /** @type {Map=} */ - this._target = undefined; - if (initFrom && initFrom._target) { - this._target = new Map(); - for (const [key, value] of initFrom._target) { - this._target.set(key, { - connection: value.connection, - export: value.export || [name], - priority: value.priority - }); - } - } - /** @type {Map=} */ - this._maxTarget = undefined; - } - - // TODO webpack 5 remove - /** @private */ - get used() { - throw new Error("REMOVED"); - } - /** @private */ - get usedName() { - throw new Error("REMOVED"); - } - /** - * @private - * @param {*} v v - */ - set used(v) { - throw new Error("REMOVED"); - } - /** - * @private - * @param {*} v v - */ - set usedName(v) { - throw new Error("REMOVED"); - } - - get canMangle() { - switch (this.canMangleProvide) { - case undefined: - return this.canMangleUse === false ? false : undefined; - case false: - return false; - case true: - switch (this.canMangleUse) { - case undefined: - return undefined; - case false: - return false; - case true: - return true; - } - } - throw new Error( - `Unexpected flags for canMangle ${this.canMangleProvide} ${this.canMangleUse}` - ); - } - - /** - * @param {RuntimeSpec} runtime only apply to this runtime - * @returns {boolean} true, when something changed - */ - setUsedInUnknownWay(runtime) { - let changed = false; - if ( - this.setUsedConditionally( - used => used < UsageState.Unknown, - UsageState.Unknown, - runtime - ) - ) { - changed = true; - } - if (this.canMangleUse !== false) { - this.canMangleUse = false; - changed = true; - } - return changed; - } - - /** - * @param {RuntimeSpec} runtime only apply to this runtime - * @returns {boolean} true, when something changed - */ - setUsedWithoutInfo(runtime) { - let changed = false; - if (this.setUsed(UsageState.NoInfo, runtime)) { - changed = true; - } - if (this.canMangleUse !== false) { - this.canMangleUse = false; - changed = true; - } - return changed; - } - - setHasUseInfo() { - if (!this._hasUseInRuntimeInfo) { - this._hasUseInRuntimeInfo = true; - } - if (this.canMangleUse === undefined) { - this.canMangleUse = true; - } - if (this.exportsInfoOwned) { - this.exportsInfo.setHasUseInfo(); - } - } + apply(compiler) { + const resourceRegExp = this.resourceRegExp; + const newContentCallback = this.newContentCallback; + const newContentResource = this.newContentResource; + const newContentRecursive = this.newContentRecursive; + const newContentRegExp = this.newContentRegExp; + const newContentCreateContextMap = this.newContentCreateContextMap; - /** - * @param {function(UsageStateType): boolean} condition compare with old value - * @param {UsageStateType} newValue set when condition is true - * @param {RuntimeSpec} runtime only apply to this runtime - * @returns {boolean} true when something has changed - */ - setUsedConditionally(condition, newValue, runtime) { - if (runtime === undefined) { - if (this._globalUsed === undefined) { - this._globalUsed = newValue; - return true; - } else { - if (this._globalUsed !== newValue && condition(this._globalUsed)) { - this._globalUsed = newValue; - return true; - } - } - } else if (this._usedInRuntime === undefined) { - if (newValue !== UsageState.Unused && condition(UsageState.Unused)) { - this._usedInRuntime = new Map(); - forEachRuntime(runtime, runtime => - this._usedInRuntime.set(runtime, newValue) - ); - return true; - } - } else { - let changed = false; - forEachRuntime(runtime, runtime => { - /** @type {UsageStateType} */ - let oldValue = this._usedInRuntime.get(runtime); - if (oldValue === undefined) oldValue = UsageState.Unused; - if (newValue !== oldValue && condition(oldValue)) { - if (newValue === UsageState.Unused) { - this._usedInRuntime.delete(runtime); + compiler.hooks.contextModuleFactory.tap("ContextReplacementPlugin", cmf => { + cmf.hooks.beforeResolve.tap("ContextReplacementPlugin", result => { + if (!result) return; + if (resourceRegExp.test(result.request)) { + if (newContentResource !== undefined) { + result.request = newContentResource; + } + if (newContentRecursive !== undefined) { + result.recursive = newContentRecursive; + } + if (newContentRegExp !== undefined) { + result.regExp = newContentRegExp; + } + if (typeof newContentCallback === "function") { + newContentCallback(result); } else { - this._usedInRuntime.set(runtime, newValue); + for (const d of result.dependencies) { + if (d.critical) d.critical = false; + } } - changed = true; } + return result; }); - if (changed) { - if (this._usedInRuntime.size === 0) this._usedInRuntime = undefined; - return true; - } - } - return false; - } - - /** - * @param {UsageStateType} newValue new value of the used state - * @param {RuntimeSpec} runtime only apply to this runtime - * @returns {boolean} true when something has changed - */ - setUsed(newValue, runtime) { - if (runtime === undefined) { - if (this._globalUsed !== newValue) { - this._globalUsed = newValue; - return true; - } - } else if (this._usedInRuntime === undefined) { - if (newValue !== UsageState.Unused) { - this._usedInRuntime = new Map(); - forEachRuntime(runtime, runtime => - this._usedInRuntime.set(runtime, newValue) - ); - return true; - } - } else { - let changed = false; - forEachRuntime(runtime, runtime => { - /** @type {UsageStateType} */ - let oldValue = this._usedInRuntime.get(runtime); - if (oldValue === undefined) oldValue = UsageState.Unused; - if (newValue !== oldValue) { - if (newValue === UsageState.Unused) { - this._usedInRuntime.delete(runtime); + cmf.hooks.afterResolve.tap("ContextReplacementPlugin", result => { + if (!result) return; + if (resourceRegExp.test(result.resource)) { + if (newContentResource !== undefined) { + if ( + newContentResource.startsWith("/") || + (newContentResource.length > 1 && newContentResource[1] === ":") + ) { + result.resource = newContentResource; + } else { + result.resource = join( + compiler.inputFileSystem, + result.resource, + newContentResource + ); + } + } + if (newContentRecursive !== undefined) { + result.recursive = newContentRecursive; + } + if (newContentRegExp !== undefined) { + result.regExp = newContentRegExp; + } + if (typeof newContentCreateContextMap === "function") { + result.resolveDependencies = + createResolveDependenciesFromContextMap( + newContentCreateContextMap + ); + } + if (typeof newContentCallback === "function") { + const origResource = result.resource; + newContentCallback(result); + if ( + result.resource !== origResource && + !result.resource.startsWith("/") && + (result.resource.length <= 1 || result.resource[1] !== ":") + ) { + // When the function changed it to an relative path + result.resource = join( + compiler.inputFileSystem, + origResource, + result.resource + ); + } } else { - this._usedInRuntime.set(runtime, newValue); + for (const d of result.dependencies) { + if (d.critical) d.critical = false; + } } - changed = true; } + return result; }); - if (changed) { - if (this._usedInRuntime.size === 0) this._usedInRuntime = undefined; - return true; - } - } - return false; + }); } +} + +const createResolveDependenciesFromContextMap = createContextMap => { + const resolveDependenciesFromContextMap = (fs, options, callback) => { + createContextMap(fs, (err, map) => { + if (err) return callback(err); + const dependencies = Object.keys(map).map(key => { + return new ContextElementDependency( + map[key] + options.resourceQuery + options.resourceFragment, + key, + options.category, + options.referencedExports + ); + }); + callback(null, dependencies); + }); + }; + return resolveDependenciesFromContextMap; +}; + +module.exports = ContextReplacementPlugin; + + +/***/ }), + +/***/ 46754: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ + + +const RuntimeGlobals = __webpack_require__(49404); +const WebpackError = __webpack_require__(68422); +const ConstDependency = __webpack_require__(60864); +const BasicEvaluatedExpression = __webpack_require__(2412); +const { + evaluateToString, + toConstantDependency +} = __webpack_require__(28723); +const createHash = __webpack_require__(24123); + +/** @typedef {import("estree").Expression} Expression */ +/** @typedef {import("./Compiler")} Compiler */ +/** @typedef {import("./NormalModule")} NormalModule */ +/** @typedef {import("./RuntimeTemplate")} RuntimeTemplate */ +/** @typedef {import("./javascript/JavascriptParser")} JavascriptParser */ + +/** @typedef {null|undefined|RegExp|Function|string|number|boolean|bigint|undefined} CodeValuePrimitive */ +/** @typedef {RecursiveArrayOrRecord} CodeValue */ + +/** + * @typedef {Object} RuntimeValueOptions + * @property {string[]=} fileDependencies + * @property {string[]=} contextDependencies + * @property {string[]=} missingDependencies + * @property {string[]=} buildDependencies + * @property {string|function(): string=} version + */ + +class RuntimeValue { /** - * @param {any} key the key - * @returns {boolean} true, if something has changed + * @param {function({ module: NormalModule, key: string, readonly version: string | undefined }): CodeValuePrimitive} fn generator function + * @param {true | string[] | RuntimeValueOptions=} options options */ - unsetTarget(key) { - if (!this._target) return false; - if (this._target.delete(key)) { - this._maxTarget = undefined; - return true; + constructor(fn, options) { + this.fn = fn; + if (Array.isArray(options)) { + options = { + fileDependencies: options + }; } - return false; + this.options = options || {}; } - /** - * @param {any} key the key - * @param {ModuleGraphConnection} connection the target module if a single one - * @param {string[]=} exportName the exported name - * @param {number=} priority priority - * @returns {boolean} true, if something has changed - */ - setTarget(key, connection, exportName, priority = 0) { - if (exportName) exportName = [...exportName]; - if (!this._target) { - this._target = new Map(); - this._target.set(key, { connection, export: exportName, priority }); - return true; - } - const oldTarget = this._target.get(key); - if (!oldTarget) { - if (oldTarget === null && !connection) return false; - this._target.set(key, { connection, export: exportName, priority }); - this._maxTarget = undefined; - return true; - } - if ( - oldTarget.connection !== connection || - oldTarget.priority !== priority || - (exportName - ? !oldTarget.export || !equals(oldTarget.export, exportName) - : oldTarget.export) - ) { - oldTarget.connection = connection; - oldTarget.export = exportName; - oldTarget.priority = priority; - this._maxTarget = undefined; - return true; - } - return false; + get fileDependencies() { + return this.options === true ? true : this.options.fileDependencies; } /** - * @param {RuntimeSpec} runtime for this runtime - * @returns {UsageStateType} usage state + * @param {JavascriptParser} parser the parser + * @param {Map>} valueCacheVersions valueCacheVersions + * @param {string} key the defined key + * @returns {CodeValuePrimitive} code */ - getUsed(runtime) { - if (!this._hasUseInRuntimeInfo) return UsageState.NoInfo; - if (this._globalUsed !== undefined) return this._globalUsed; - if (this._usedInRuntime === undefined) { - return UsageState.Unused; - } else if (typeof runtime === "string") { - const value = this._usedInRuntime.get(runtime); - return value === undefined ? UsageState.Unused : value; - } else if (runtime === undefined) { - /** @type {UsageStateType} */ - let max = UsageState.Unused; - for (const value of this._usedInRuntime.values()) { - if (value === UsageState.Used) { - return UsageState.Used; + exec(parser, valueCacheVersions, key) { + const buildInfo = parser.state.module.buildInfo; + if (this.options === true) { + buildInfo.cacheable = false; + } else { + if (this.options.fileDependencies) { + for (const dep of this.options.fileDependencies) { + buildInfo.fileDependencies.add(dep); } - if (max < value) max = value; } - return max; - } else { - /** @type {UsageStateType} */ - let max = UsageState.Unused; - for (const item of runtime) { - const value = this._usedInRuntime.get(item); - if (value !== undefined) { - if (value === UsageState.Used) { - return UsageState.Used; - } - if (max < value) max = value; + if (this.options.contextDependencies) { + for (const dep of this.options.contextDependencies) { + buildInfo.contextDependencies.add(dep); } } - return max; - } - } - - /** - * get used name - * @param {string | undefined} fallbackName fallback name for used exports with no name - * @param {RuntimeSpec} runtime check usage for this runtime only - * @returns {string | false} used name - */ - getUsedName(fallbackName, runtime) { - if (this._hasUseInRuntimeInfo) { - if (this._globalUsed !== undefined) { - if (this._globalUsed === UsageState.Unused) return false; - } else { - if (this._usedInRuntime === undefined) return false; - if (typeof runtime === "string") { - if (!this._usedInRuntime.has(runtime)) { - return false; - } - } else if (runtime !== undefined) { - if ( - Array.from(runtime).every( - runtime => !this._usedInRuntime.has(runtime) - ) - ) { - return false; - } + if (this.options.missingDependencies) { + for (const dep of this.options.missingDependencies) { + buildInfo.missingDependencies.add(dep); + } + } + if (this.options.buildDependencies) { + for (const dep of this.options.buildDependencies) { + buildInfo.buildDependencies.add(dep); } } } - if (this._usedName !== null) return this._usedName; - return this.name || fallbackName; + + return this.fn({ + module: parser.state.module, + key, + get version() { + return /** @type {string} */ ( + valueCacheVersions.get(VALUE_DEP_PREFIX + key) + ); + } + }); } - /** - * @returns {boolean} true, when a mangled name of this export is set - */ - hasUsedName() { - return this._usedName !== null; + getCacheVersion() { + return this.options === true + ? undefined + : (typeof this.options.version === "function" + ? this.options.version() + : this.options.version) || "unset"; } +} - /** - * Sets the mangled name of this export - * @param {string} name the new name - * @returns {void} - */ - setUsedName(name) { - this._usedName = name; +/** + * @param {any[]|{[k: string]: any}} obj obj + * @param {JavascriptParser} parser Parser + * @param {Map>} valueCacheVersions valueCacheVersions + * @param {string} key the defined key + * @param {RuntimeTemplate} runtimeTemplate the runtime template + * @param {boolean|undefined|null=} asiSafe asi safe (undefined: unknown, null: unneeded) + * @returns {string} code converted to string that evaluates + */ +const stringifyObj = ( + obj, + parser, + valueCacheVersions, + key, + runtimeTemplate, + asiSafe +) => { + let code; + let arr = Array.isArray(obj); + if (arr) { + code = `[${obj + .map(code => + toCode(code, parser, valueCacheVersions, key, runtimeTemplate, null) + ) + .join(",")}]`; + } else { + code = `{${Object.keys(obj) + .map(key => { + const code = obj[key]; + return ( + JSON.stringify(key) + + ":" + + toCode(code, parser, valueCacheVersions, key, runtimeTemplate, null) + ); + }) + .join(",")}}`; } - /** - * @param {ModuleGraph} moduleGraph the module graph - * @param {function({ module: Module, export: string[] | undefined }): boolean} resolveTargetFilter filter function to further resolve target - * @returns {ExportInfo | ExportsInfo | undefined} the terminal binding export(s) info if known - */ - getTerminalBinding(moduleGraph, resolveTargetFilter = RETURNS_TRUE) { - if (this.terminalBinding) return this; - const target = this.getTarget(moduleGraph, resolveTargetFilter); - if (!target) return undefined; - const exportsInfo = moduleGraph.getExportsInfo(target.module); - if (!target.export) return exportsInfo; - return exportsInfo.getReadOnlyExportInfoRecursive(target.export); + switch (asiSafe) { + case null: + return code; + case true: + return arr ? code : `(${code})`; + case false: + return arr ? `;${code}` : `;(${code})`; + default: + return `/*#__PURE__*/Object(${code})`; } +}; - isReexport() { - return !this.terminalBinding && this._target && this._target.size > 0; +/** + * Convert code to a string that evaluates + * @param {CodeValue} code Code to evaluate + * @param {JavascriptParser} parser Parser + * @param {Map>} valueCacheVersions valueCacheVersions + * @param {string} key the defined key + * @param {RuntimeTemplate} runtimeTemplate the runtime template + * @param {boolean|undefined|null=} asiSafe asi safe (undefined: unknown, null: unneeded) + * @returns {string} code converted to string that evaluates + */ +const toCode = ( + code, + parser, + valueCacheVersions, + key, + runtimeTemplate, + asiSafe +) => { + if (code === null) { + return "null"; } - - _getMaxTarget() { - if (this._maxTarget !== undefined) return this._maxTarget; - if (this._target.size <= 1) return (this._maxTarget = this._target); - let maxPriority = -Infinity; - let minPriority = Infinity; - for (const { priority } of this._target.values()) { - if (maxPriority < priority) maxPriority = priority; - if (minPriority > priority) minPriority = priority; - } - // This should be very common - if (maxPriority === minPriority) return (this._maxTarget = this._target); - - // This is an edge case - const map = new Map(); - for (const [key, value] of this._target) { - if (maxPriority === value.priority) { - map.set(key, value); - } - } - this._maxTarget = map; - return map; + if (code === undefined) { + return "undefined"; } - - /** - * @param {ModuleGraph} moduleGraph the module graph - * @param {function(Module): boolean} validTargetModuleFilter a valid target module - * @returns {{ module: Module, export: string[] | undefined } | undefined | false} the target, undefined when there is no target, false when no target is valid - */ - findTarget(moduleGraph, validTargetModuleFilter) { - return this._findTarget(moduleGraph, validTargetModuleFilter, new Set()); + if (Object.is(code, -0)) { + return "-0"; } - - /** - * @param {ModuleGraph} moduleGraph the module graph - * @param {function(Module): boolean} validTargetModuleFilter a valid target module - * @param {Set | undefined} alreadyVisited set of already visited export info to avoid circular references - * @returns {{ module: Module, export: string[] | undefined } | undefined | false} the target, undefined when there is no target, false when no target is valid - */ - _findTarget(moduleGraph, validTargetModuleFilter, alreadyVisited) { - if (!this._target || this._target.size === 0) return undefined; - let rawTarget = this._getMaxTarget().values().next().value; - if (!rawTarget) return undefined; - /** @type {{ module: Module, export: string[] | undefined }} */ - let target = { - module: rawTarget.connection.module, - export: rawTarget.export - }; - for (;;) { - if (validTargetModuleFilter(target.module)) return target; - const exportsInfo = moduleGraph.getExportsInfo(target.module); - const exportInfo = exportsInfo.getExportInfo(target.export[0]); - if (alreadyVisited.has(exportInfo)) return null; - const newTarget = exportInfo._findTarget( - moduleGraph, - validTargetModuleFilter, - alreadyVisited - ); - if (!newTarget) return false; - if (target.export.length === 1) { - target = newTarget; - } else { - target = { - module: newTarget.module, - export: newTarget.export - ? newTarget.export.concat(target.export.slice(1)) - : target.export.slice(1) - }; - } - } + if (code instanceof RuntimeValue) { + return toCode( + code.exec(parser, valueCacheVersions, key), + parser, + valueCacheVersions, + key, + runtimeTemplate, + asiSafe + ); } - - /** - * @param {ModuleGraph} moduleGraph the module graph - * @param {function({ module: Module, export: string[] | undefined }): boolean} resolveTargetFilter filter function to further resolve target - * @returns {{ module: Module, export: string[] | undefined } | undefined} the target - */ - getTarget(moduleGraph, resolveTargetFilter = RETURNS_TRUE) { - const result = this._getTarget(moduleGraph, resolveTargetFilter, undefined); - if (result === CIRCULAR) return undefined; - return result; + if (code instanceof RegExp && code.toString) { + return code.toString(); } - - /** - * @param {ModuleGraph} moduleGraph the module graph - * @param {function({ module: Module, connection: ModuleGraphConnection, export: string[] | undefined }): boolean} resolveTargetFilter filter function to further resolve target - * @param {Set | undefined} alreadyVisited set of already visited export info to avoid circular references - * @returns {{ module: Module, connection: ModuleGraphConnection, export: string[] | undefined } | CIRCULAR | undefined} the target - */ - _getTarget(moduleGraph, resolveTargetFilter, alreadyVisited) { - /** - * @param {{ connection: ModuleGraphConnection, export: string[] | undefined } | null} inputTarget unresolved target - * @param {Set} alreadyVisited set of already visited export info to avoid circular references - * @returns {{ module: Module, connection: ModuleGraphConnection, export: string[] | undefined } | CIRCULAR | null} resolved target - */ - const resolveTarget = (inputTarget, alreadyVisited) => { - if (!inputTarget) return null; - if (!inputTarget.export) { - return { - module: inputTarget.connection.module, - connection: inputTarget.connection, - export: undefined - }; - } - /** @type {{ module: Module, connection: ModuleGraphConnection, export: string[] | undefined }} */ - let target = { - module: inputTarget.connection.module, - connection: inputTarget.connection, - export: inputTarget.export - }; - if (!resolveTargetFilter(target)) return target; - let alreadyVisitedOwned = false; - for (;;) { - const exportsInfo = moduleGraph.getExportsInfo(target.module); - const exportInfo = exportsInfo.getExportInfo(target.export[0]); - if (!exportInfo) return target; - if (alreadyVisited.has(exportInfo)) return CIRCULAR; - const newTarget = exportInfo._getTarget( - moduleGraph, - resolveTargetFilter, - alreadyVisited - ); - if (newTarget === CIRCULAR) return CIRCULAR; - if (!newTarget) return target; - if (target.export.length === 1) { - target = newTarget; - if (!target.export) return target; - } else { - target = { - module: newTarget.module, - connection: newTarget.connection, - export: newTarget.export - ? newTarget.export.concat(target.export.slice(1)) - : target.export.slice(1) - }; - } - if (!resolveTargetFilter(target)) return target; - if (!alreadyVisitedOwned) { - alreadyVisited = new Set(alreadyVisited); - alreadyVisitedOwned = true; - } - alreadyVisited.add(exportInfo); - } - }; - - if (!this._target || this._target.size === 0) return undefined; - if (alreadyVisited && alreadyVisited.has(this)) return CIRCULAR; - const newAlreadyVisited = new Set(alreadyVisited); - newAlreadyVisited.add(this); - const values = this._getMaxTarget().values(); - const target = resolveTarget(values.next().value, newAlreadyVisited); - if (target === CIRCULAR) return CIRCULAR; - if (target === null) return undefined; - let result = values.next(); - while (!result.done) { - const t = resolveTarget(result.value, newAlreadyVisited); - if (t === CIRCULAR) return CIRCULAR; - if (t === null) return undefined; - if (t.module !== target.module) return undefined; - if (!t.export !== !target.export) return undefined; - if (target.export && !equals(t.export, target.export)) return undefined; - result = values.next(); - } - return target; + if (typeof code === "function" && code.toString) { + return "(" + code.toString() + ")"; } - - /** - * Move the target forward as long resolveTargetFilter is fulfilled - * @param {ModuleGraph} moduleGraph the module graph - * @param {function({ module: Module, export: string[] | undefined }): boolean} resolveTargetFilter filter function to further resolve target - * @param {function({ module: Module, export: string[] | undefined }): ModuleGraphConnection=} updateOriginalConnection updates the original connection instead of using the target connection - * @returns {{ module: Module, export: string[] | undefined } | undefined} the resolved target when moved - */ - moveTarget(moduleGraph, resolveTargetFilter, updateOriginalConnection) { - const target = this._getTarget(moduleGraph, resolveTargetFilter, undefined); - if (target === CIRCULAR) return undefined; - if (!target) return undefined; - const originalTarget = this._getMaxTarget().values().next().value; - if ( - originalTarget.connection === target.connection && - originalTarget.export === target.export - ) { - return undefined; - } - this._target.clear(); - this._target.set(undefined, { - connection: updateOriginalConnection - ? updateOriginalConnection(target) - : target.connection, - export: target.export, - priority: 0 - }); - return target; + if (typeof code === "object") { + return stringifyObj( + code, + parser, + valueCacheVersions, + key, + runtimeTemplate, + asiSafe + ); } - - createNestedExportsInfo() { - if (this.exportsInfoOwned) return this.exportsInfo; - this.exportsInfoOwned = true; - const oldExportsInfo = this.exportsInfo; - this.exportsInfo = new ExportsInfo(); - this.exportsInfo.setHasProvideInfo(); - if (oldExportsInfo) { - this.exportsInfo.setRedirectNamedTo(oldExportsInfo); - } - return this.exportsInfo; + if (typeof code === "bigint") { + return runtimeTemplate.supportsBigIntLiteral() + ? `${code}n` + : `BigInt("${code}")`; } + return code + ""; +}; - getNestedExportsInfo() { - return this.exportsInfo; +const toCacheVersion = code => { + if (code === null) { + return "null"; } - - hasInfo(baseInfo, runtime) { - return ( - (this._usedName && this._usedName !== this.name) || - this.provided || - this.terminalBinding || - this.getUsed(runtime) !== baseInfo.getUsed(runtime) - ); + if (code === undefined) { + return "undefined"; } - - updateHash(hash, runtime) { - this._updateHash(hash, runtime, new Set()); + if (Object.is(code, -0)) { + return "-0"; } - - _updateHash(hash, runtime, alreadyVisitedExportsInfo) { - hash.update( - `${this._usedName || this.name}${this.getUsed(runtime)}${this.provided}${ - this.terminalBinding - }` - ); - if (this.exportsInfo && !alreadyVisitedExportsInfo.has(this.exportsInfo)) { - this.exportsInfo._updateHash(hash, runtime, alreadyVisitedExportsInfo); - } + if (code instanceof RuntimeValue) { + return code.getCacheVersion(); } - - getUsedInfo() { - if (this._globalUsed !== undefined) { - switch (this._globalUsed) { - case UsageState.Unused: - return "unused"; - case UsageState.NoInfo: - return "no usage info"; - case UsageState.Unknown: - return "maybe used (runtime-defined)"; - case UsageState.Used: - return "used"; - case UsageState.OnlyPropertiesUsed: - return "only properties used"; - } - } else if (this._usedInRuntime !== undefined) { - /** @type {Map} */ - const map = new Map(); - for (const [runtime, used] of this._usedInRuntime) { - const list = map.get(used); - if (list !== undefined) list.push(runtime); - else map.set(used, [runtime]); - } - const specificInfo = Array.from(map, ([used, runtimes]) => { - switch (used) { - case UsageState.NoInfo: - return `no usage info in ${runtimes.join(", ")}`; - case UsageState.Unknown: - return `maybe used in ${runtimes.join(", ")} (runtime-defined)`; - case UsageState.Used: - return `used in ${runtimes.join(", ")}`; - case UsageState.OnlyPropertiesUsed: - return `only properties used in ${runtimes.join(", ")}`; - } - }); - if (specificInfo.length > 0) { - return specificInfo.join("; "); - } - } - return this._hasUseInRuntimeInfo ? "unused" : "no usage info"; + if (code instanceof RegExp && code.toString) { + return code.toString(); } - - getProvidedInfo() { - switch (this.provided) { - case undefined: - return "no provided info"; - case null: - return "maybe provided (runtime-defined)"; - case true: - return "provided"; - case false: - return "not provided"; - } + if (typeof code === "function" && code.toString) { + return "(" + code.toString() + ")"; } - - getRenameInfo() { - if (this._usedName !== null && this._usedName !== this.name) { - return `renamed to ${JSON.stringify(this._usedName).slice(1, -1)}`; - } - switch (this.canMangleProvide) { - case undefined: - switch (this.canMangleUse) { - case undefined: - return "missing provision and use info prevents renaming"; - case false: - return "usage prevents renaming (no provision info)"; - case true: - return "missing provision info prevents renaming"; - } - break; - case true: - switch (this.canMangleUse) { - case undefined: - return "missing usage info prevents renaming"; - case false: - return "usage prevents renaming"; - case true: - return "could be renamed"; - } - break; - case false: - switch (this.canMangleUse) { - case undefined: - return "provision prevents renaming (no use info)"; - case false: - return "usage and provision prevents renaming"; - case true: - return "provision prevents renaming"; - } - break; - } - throw new Error( - `Unexpected flags for getRenameInfo ${this.canMangleProvide} ${this.canMangleUse}` - ); + if (typeof code === "object") { + const items = Object.keys(code).map(key => ({ + key, + value: toCacheVersion(code[key]) + })); + if (items.some(({ value }) => value === undefined)) return undefined; + return `{${items.map(({ key, value }) => `${key}: ${value}`).join(", ")}}`; } -} - -module.exports = ExportsInfo; -module.exports.ExportInfo = ExportInfo; -module.exports.UsageState = UsageState; - - -/***/ }), - -/***/ 75529: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ - + if (typeof code === "bigint") { + return `${code}n`; + } + return code + ""; +}; +const VALUE_DEP_PREFIX = "webpack/DefinePlugin "; +const VALUE_DEP_MAIN = "webpack/DefinePlugin_hash"; -const ConstDependency = __webpack_require__(60864); -const ExportsInfoDependency = __webpack_require__(30474); +class DefinePlugin { + /** + * Create a new define plugin + * @param {Record} definitions A map of global object definitions + */ + constructor(definitions) { + this.definitions = definitions; + } -/** @typedef {import("./Compiler")} Compiler */ -/** @typedef {import("./javascript/JavascriptParser")} JavascriptParser */ + /** + * @param {function({ module: NormalModule, key: string, readonly version: string | undefined }): CodeValuePrimitive} fn generator function + * @param {true | string[] | RuntimeValueOptions=} options options + * @returns {RuntimeValue} runtime value + */ + static runtimeValue(fn, options) { + return new RuntimeValue(fn, options); + } -class ExportsInfoApiPlugin { /** * Apply the plugin * @param {Compiler} compiler the compiler instance * @returns {void} */ apply(compiler) { + const definitions = this.definitions; compiler.hooks.compilation.tap( - "ExportsInfoApiPlugin", + "DefinePlugin", (compilation, { normalModuleFactory }) => { compilation.dependencyTemplates.set( - ExportsInfoDependency, - new ExportsInfoDependency.Template() + ConstDependency, + new ConstDependency.Template() + ); + const { runtimeTemplate } = compilation; + + const mainHash = createHash(compilation.outputOptions.hashFunction); + mainHash.update( + /** @type {string} */ ( + compilation.valueCacheVersions.get(VALUE_DEP_MAIN) + ) || "" ); + /** - * @param {JavascriptParser} parser the parser - * @returns {void} + * Handler + * @param {JavascriptParser} parser Parser + * @returns {void} */ const handler = parser => { - parser.hooks.expressionMemberChain - .for("__webpack_exports_info__") - .tap("ExportsInfoApiPlugin", (expr, members) => { - const dep = - members.length >= 2 - ? new ExportsInfoDependency( - expr.range, - members.slice(0, -1), - members[members.length - 1] - ) - : new ExportsInfoDependency(expr.range, null, members[0]); - dep.loc = expr.loc; - parser.state.module.addDependency(dep); - return true; + const mainValue = compilation.valueCacheVersions.get(VALUE_DEP_MAIN); + parser.hooks.program.tap("DefinePlugin", () => { + const { buildInfo } = parser.state.module; + if (!buildInfo.valueDependencies) + buildInfo.valueDependencies = new Map(); + buildInfo.valueDependencies.set(VALUE_DEP_MAIN, mainValue); + }); + + const addValueDependency = key => { + const { buildInfo } = parser.state.module; + buildInfo.valueDependencies.set( + VALUE_DEP_PREFIX + key, + compilation.valueCacheVersions.get(VALUE_DEP_PREFIX + key) + ); + }; + + const withValueDependency = + (key, fn) => + (...args) => { + addValueDependency(key); + return fn(...args); + }; + + /** + * Walk definitions + * @param {Object} definitions Definitions map + * @param {string} prefix Prefix string + * @returns {void} + */ + const walkDefinitions = (definitions, prefix) => { + Object.keys(definitions).forEach(key => { + const code = definitions[key]; + if ( + code && + typeof code === "object" && + !(code instanceof RuntimeValue) && + !(code instanceof RegExp) + ) { + walkDefinitions(code, prefix + key + "."); + applyObjectDefine(prefix + key, code); + return; + } + applyDefineKey(prefix, key); + applyDefine(prefix + key, code); }); - parser.hooks.expression - .for("__webpack_exports_info__") - .tap("ExportsInfoApiPlugin", expr => { - const dep = new ConstDependency("true", expr.range); - dep.loc = expr.loc; - parser.state.module.addPresentationalDependency(dep); + }; + + /** + * Apply define key + * @param {string} prefix Prefix + * @param {string} key Key + * @returns {void} + */ + const applyDefineKey = (prefix, key) => { + const splittedKey = key.split("."); + splittedKey.slice(1).forEach((_, i) => { + const fullKey = prefix + splittedKey.slice(0, i + 1).join("."); + parser.hooks.canRename.for(fullKey).tap("DefinePlugin", () => { + addValueDependency(key); + return true; + }); + }); + }; + + /** + * Apply Code + * @param {string} key Key + * @param {CodeValue} code Code + * @returns {void} + */ + const applyDefine = (key, code) => { + const originalKey = key; + const isTypeof = /^typeof\s+/.test(key); + if (isTypeof) key = key.replace(/^typeof\s+/, ""); + let recurse = false; + let recurseTypeof = false; + if (!isTypeof) { + parser.hooks.canRename.for(key).tap("DefinePlugin", () => { + addValueDependency(originalKey); + return true; + }); + parser.hooks.evaluateIdentifier + .for(key) + .tap("DefinePlugin", expr => { + /** + * this is needed in case there is a recursion in the DefinePlugin + * to prevent an endless recursion + * e.g.: new DefinePlugin({ + * "a": "b", + * "b": "a" + * }); + */ + if (recurse) return; + addValueDependency(originalKey); + recurse = true; + const res = parser.evaluate( + toCode( + code, + parser, + compilation.valueCacheVersions, + key, + runtimeTemplate, + null + ) + ); + recurse = false; + res.setRange(expr.range); + return res; + }); + parser.hooks.expression.for(key).tap("DefinePlugin", expr => { + addValueDependency(originalKey); + const strCode = toCode( + code, + parser, + compilation.valueCacheVersions, + originalKey, + runtimeTemplate, + !parser.isAsiPosition(expr.range[0]) + ); + if (/__webpack_require__\s*(!?\.)/.test(strCode)) { + return toConstantDependency(parser, strCode, [ + RuntimeGlobals.require + ])(expr); + } else if (/__webpack_require__/.test(strCode)) { + return toConstantDependency(parser, strCode, [ + RuntimeGlobals.requireScope + ])(expr); + } else { + return toConstantDependency(parser, strCode)(expr); + } + }); + } + parser.hooks.evaluateTypeof.for(key).tap("DefinePlugin", expr => { + /** + * this is needed in case there is a recursion in the DefinePlugin + * to prevent an endless recursion + * e.g.: new DefinePlugin({ + * "typeof a": "typeof b", + * "typeof b": "typeof a" + * }); + */ + if (recurseTypeof) return; + recurseTypeof = true; + addValueDependency(originalKey); + const codeCode = toCode( + code, + parser, + compilation.valueCacheVersions, + originalKey, + runtimeTemplate, + null + ); + const typeofCode = isTypeof + ? codeCode + : "typeof (" + codeCode + ")"; + const res = parser.evaluate(typeofCode); + recurseTypeof = false; + res.setRange(expr.range); + return res; + }); + parser.hooks.typeof.for(key).tap("DefinePlugin", expr => { + addValueDependency(originalKey); + const codeCode = toCode( + code, + parser, + compilation.valueCacheVersions, + originalKey, + runtimeTemplate, + null + ); + const typeofCode = isTypeof + ? codeCode + : "typeof (" + codeCode + ")"; + const res = parser.evaluate(typeofCode); + if (!res.isString()) return; + return toConstantDependency( + parser, + JSON.stringify(res.string) + ).bind(parser)(expr); + }); + }; + + /** + * Apply Object + * @param {string} key Key + * @param {Object} obj Object + * @returns {void} + */ + const applyObjectDefine = (key, obj) => { + parser.hooks.canRename.for(key).tap("DefinePlugin", () => { + addValueDependency(key); return true; }); + parser.hooks.evaluateIdentifier + .for(key) + .tap("DefinePlugin", expr => { + addValueDependency(key); + return new BasicEvaluatedExpression() + .setTruthy() + .setSideEffects(false) + .setRange(expr.range); + }); + parser.hooks.evaluateTypeof + .for(key) + .tap( + "DefinePlugin", + withValueDependency(key, evaluateToString("object")) + ); + parser.hooks.expression.for(key).tap("DefinePlugin", expr => { + addValueDependency(key); + const strCode = stringifyObj( + obj, + parser, + compilation.valueCacheVersions, + key, + runtimeTemplate, + !parser.isAsiPosition(expr.range[0]) + ); + + if (/__webpack_require__\s*(!?\.)/.test(strCode)) { + return toConstantDependency(parser, strCode, [ + RuntimeGlobals.require + ])(expr); + } else if (/__webpack_require__/.test(strCode)) { + return toConstantDependency(parser, strCode, [ + RuntimeGlobals.requireScope + ])(expr); + } else { + return toConstantDependency(parser, strCode)(expr); + } + }); + parser.hooks.typeof + .for(key) + .tap( + "DefinePlugin", + withValueDependency( + key, + toConstantDependency(parser, JSON.stringify("object")) + ) + ); + }; + + walkDefinitions(definitions, ""); }; + normalModuleFactory.hooks.parser .for("javascript/auto") - .tap("ExportsInfoApiPlugin", handler); + .tap("DefinePlugin", handler); normalModuleFactory.hooks.parser .for("javascript/dynamic") - .tap("ExportsInfoApiPlugin", handler); + .tap("DefinePlugin", handler); normalModuleFactory.hooks.parser .for("javascript/esm") - .tap("ExportsInfoApiPlugin", handler); + .tap("DefinePlugin", handler); + + /** + * Walk definitions + * @param {Object} definitions Definitions map + * @param {string} prefix Prefix string + * @returns {void} + */ + const walkDefinitionsForValues = (definitions, prefix) => { + Object.keys(definitions).forEach(key => { + const code = definitions[key]; + const version = toCacheVersion(code); + const name = VALUE_DEP_PREFIX + prefix + key; + mainHash.update("|" + prefix + key); + const oldVersion = compilation.valueCacheVersions.get(name); + if (oldVersion === undefined) { + compilation.valueCacheVersions.set(name, version); + } else if (oldVersion !== version) { + const warning = new WebpackError( + `DefinePlugin\nConflicting values for '${prefix + key}'` + ); + warning.details = `'${oldVersion}' !== '${version}'`; + warning.hideStack = true; + compilation.warnings.push(warning); + } + if ( + code && + typeof code === "object" && + !(code instanceof RuntimeValue) && + !(code instanceof RegExp) + ) { + walkDefinitionsForValues(code, prefix + key + "."); + } + }); + }; + + walkDefinitionsForValues(definitions, ""); + + compilation.valueCacheVersions.set( + VALUE_DEP_MAIN, + /** @type {string} */ (mainHash.digest("hex").slice(0, 8)) + ); } ); } } - -module.exports = ExportsInfoApiPlugin; +module.exports = DefinePlugin; /***/ }), -/***/ 89805: +/***/ 68719: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; @@ -41464,425 +39376,87 @@ module.exports = ExportsInfoApiPlugin; const { OriginalSource, RawSource } = __webpack_require__(96192); -const ConcatenationScope = __webpack_require__(14067); -const { UsageState } = __webpack_require__(4295); -const InitFragment = __webpack_require__(51739); const Module = __webpack_require__(85887); const RuntimeGlobals = __webpack_require__(49404); -const Template = __webpack_require__(92066); +const DelegatedSourceDependency = __webpack_require__(82766); const StaticExportsDependency = __webpack_require__(67967); -const createHash = __webpack_require__(24123); -const extractUrlAndGlobal = __webpack_require__(31670); const makeSerializable = __webpack_require__(26522); -const propertyAccess = __webpack_require__(86709); -const { register } = __webpack_require__(99551); /** @typedef {import("webpack-sources").Source} Source */ /** @typedef {import("../declarations/WebpackOptions").WebpackOptionsNormalized} WebpackOptions */ -/** @typedef {import("./Chunk")} Chunk */ /** @typedef {import("./ChunkGraph")} ChunkGraph */ /** @typedef {import("./Compilation")} Compilation */ /** @typedef {import("./Dependency").UpdateHashContext} UpdateHashContext */ /** @typedef {import("./DependencyTemplates")} DependencyTemplates */ -/** @typedef {import("./ExportsInfo")} ExportsInfo */ +/** @typedef {import("./LibManifestPlugin").ManifestModuleData} ManifestModuleData */ /** @typedef {import("./Module").CodeGenerationContext} CodeGenerationContext */ /** @typedef {import("./Module").CodeGenerationResult} CodeGenerationResult */ -/** @typedef {import("./Module").ConcatenationBailoutReasonContext} ConcatenationBailoutReasonContext */ /** @typedef {import("./Module").LibIdentOptions} LibIdentOptions */ /** @typedef {import("./Module").NeedBuildContext} NeedBuildContext */ -/** @typedef {import("./NormalModuleFactory")} NormalModuleFactory */ +/** @typedef {import("./Module").SourceContext} SourceContext */ /** @typedef {import("./RequestShortener")} RequestShortener */ /** @typedef {import("./ResolverFactory").ResolverWithOptions} ResolverWithOptions */ /** @typedef {import("./RuntimeTemplate")} RuntimeTemplate */ /** @typedef {import("./WebpackError")} WebpackError */ -/** @typedef {import("./javascript/JavascriptModulesPlugin").ChunkRenderContext} ChunkRenderContext */ +/** @typedef {import("./dependencies/ModuleDependency")} ModuleDependency */ /** @typedef {import("./util/Hash")} Hash */ -/** @typedef {typeof import("./util/Hash")} HashConstructor */ /** @typedef {import("./util/fs").InputFileSystem} InputFileSystem */ -/** @typedef {import("./util/runtime").RuntimeSpec} RuntimeSpec */ - -/** - * @typedef {Object} SourceData - * @property {boolean=} iife - * @property {string=} init - * @property {string} expression - * @property {InitFragment[]=} chunkInitFragments - * @property {ReadonlySet=} runtimeRequirements - */ const TYPES = new Set(["javascript"]); -const RUNTIME_REQUIREMENTS = new Set([RuntimeGlobals.module]); -const RUNTIME_REQUIREMENTS_FOR_SCRIPT = new Set([RuntimeGlobals.loadScript]); -const RUNTIME_REQUIREMENTS_FOR_MODULE = new Set([ - RuntimeGlobals.definePropertyGetters +const RUNTIME_REQUIREMENTS = new Set([ + RuntimeGlobals.module, + RuntimeGlobals.require ]); -const EMPTY_RUNTIME_REQUIREMENTS = new Set([]); -/** - * @param {string|string[]} variableName the variable name or path - * @param {string} type the module system - * @returns {SourceData} the generated source - */ -const getSourceForGlobalVariableExternal = (variableName, type) => { - if (!Array.isArray(variableName)) { - // make it an array as the look up works the same basically - variableName = [variableName]; - } +class DelegatedModule extends Module { + constructor(sourceRequest, data, type, userRequest, originalRequest) { + super("javascript/dynamic", null); - // needed for e.g. window["some"]["thing"] - const objectLookup = variableName.map(r => `[${JSON.stringify(r)}]`).join(""); - return { - iife: type === "this", - expression: `${type}${objectLookup}` - }; -}; + // Info from Factory + this.sourceRequest = sourceRequest; + this.request = data.id; + this.delegationType = type; + this.userRequest = userRequest; + this.originalRequest = originalRequest; + /** @type {ManifestModuleData} */ + this.delegateData = data; -/** - * @param {string|string[]} moduleAndSpecifiers the module request - * @returns {SourceData} the generated source - */ -const getSourceForCommonJsExternal = moduleAndSpecifiers => { - if (!Array.isArray(moduleAndSpecifiers)) { - return { - expression: `require(${JSON.stringify(moduleAndSpecifiers)})` - }; + // Build info + this.delegatedSourceDependency = undefined; } - const moduleName = moduleAndSpecifiers[0]; - return { - expression: `require(${JSON.stringify(moduleName)})${propertyAccess( - moduleAndSpecifiers, - 1 - )}` - }; -}; -/** - * @param {string|string[]} moduleAndSpecifiers the module request - * @returns {SourceData} the generated source - */ -const getSourceForCommonJsExternalInNodeModule = moduleAndSpecifiers => { - const chunkInitFragments = [ - new InitFragment( - 'import { createRequire as __WEBPACK_EXTERNAL_createRequire } from "module";\n', - InitFragment.STAGE_HARMONY_IMPORTS, - 0, - "external module node-commonjs" - ) - ]; - if (!Array.isArray(moduleAndSpecifiers)) { - return { - expression: `__WEBPACK_EXTERNAL_createRequire(import.meta.url)(${JSON.stringify( - moduleAndSpecifiers - )})`, - chunkInitFragments - }; + /** + * @returns {Set} types available (do not mutate) + */ + getSourceTypes() { + return TYPES; } - const moduleName = moduleAndSpecifiers[0]; - return { - expression: `__WEBPACK_EXTERNAL_createRequire(import.meta.url)(${JSON.stringify( - moduleName - )})${propertyAccess(moduleAndSpecifiers, 1)}`, - chunkInitFragments - }; -}; -/** - * @param {string|string[]} moduleAndSpecifiers the module request - * @param {RuntimeTemplate} runtimeTemplate the runtime template - * @returns {SourceData} the generated source - */ -const getSourceForImportExternal = (moduleAndSpecifiers, runtimeTemplate) => { - const importName = runtimeTemplate.outputOptions.importFunctionName; - if (!runtimeTemplate.supportsDynamicImport() && importName === "import") { - throw new Error( - "The target environment doesn't support 'import()' so it's not possible to use external type 'import'" - ); - } - if (!Array.isArray(moduleAndSpecifiers)) { - return { - expression: `${importName}(${JSON.stringify(moduleAndSpecifiers)});` - }; - } - if (moduleAndSpecifiers.length === 1) { - return { - expression: `${importName}(${JSON.stringify(moduleAndSpecifiers[0])});` - }; + /** + * @param {LibIdentOptions} options options + * @returns {string | null} an identifier for library inclusion + */ + libIdent(options) { + return typeof this.originalRequest === "string" + ? this.originalRequest + : this.originalRequest.libIdent(options); } - const moduleName = moduleAndSpecifiers[0]; - return { - expression: `${importName}(${JSON.stringify( - moduleName - )}).then(${runtimeTemplate.returningFunction( - `module${propertyAccess(moduleAndSpecifiers, 1)}`, - "module" - )});` - }; -}; -class ModuleExternalInitFragment extends InitFragment { /** - * @param {string} request import source - * @param {string=} ident recomputed ident - * @param {string | HashConstructor=} hashFunction the hash function to use + * @returns {string} a unique identifier of the module */ - constructor(request, ident, hashFunction = "md4") { - if (ident === undefined) { - ident = Template.toIdentifier(request); - if (ident !== request) { - ident += `_${createHash(hashFunction) - .update(request) - .digest("hex") - .slice(0, 8)}`; - } - } - const identifier = `__WEBPACK_EXTERNAL_MODULE_${ident}__`; - super( - `import * as ${identifier} from ${JSON.stringify(request)};\n`, - InitFragment.STAGE_HARMONY_IMPORTS, - 0, - `external module import ${ident}` - ); - this._ident = ident; - this._identifier = identifier; - this._request = request; + identifier() { + return `delegated ${JSON.stringify(this.request)} from ${ + this.sourceRequest + }`; } - getNamespaceIdentifier() { - return this._identifier; - } -} - -register( - ModuleExternalInitFragment, - "webpack/lib/ExternalModule", - "ModuleExternalInitFragment", - { - serialize(obj, { write }) { - write(obj._request); - write(obj._ident); - }, - deserialize({ read }) { - return new ModuleExternalInitFragment(read(), read()); - } - } -); - -const generateModuleRemapping = (input, exportsInfo, runtime) => { - if (exportsInfo.otherExportsInfo.getUsed(runtime) === UsageState.Unused) { - const properties = []; - for (const exportInfo of exportsInfo.orderedExports) { - const used = exportInfo.getUsedName(exportInfo.name, runtime); - if (!used) continue; - const nestedInfo = exportInfo.getNestedExportsInfo(); - if (nestedInfo) { - const nestedExpr = generateModuleRemapping( - `${input}${propertyAccess([exportInfo.name])}`, - nestedInfo - ); - if (nestedExpr) { - properties.push(`[${JSON.stringify(used)}]: y(${nestedExpr})`); - continue; - } - } - properties.push( - `[${JSON.stringify(used)}]: () => ${input}${propertyAccess([ - exportInfo.name - ])}` - ); - } - return `x({ ${properties.join(", ")} })`; - } -}; - -/** - * @param {string|string[]} moduleAndSpecifiers the module request - * @param {ExportsInfo} exportsInfo exports info of this module - * @param {RuntimeSpec} runtime the runtime - * @param {string | HashConstructor=} hashFunction the hash function to use - * @returns {SourceData} the generated source - */ -const getSourceForModuleExternal = ( - moduleAndSpecifiers, - exportsInfo, - runtime, - hashFunction -) => { - if (!Array.isArray(moduleAndSpecifiers)) - moduleAndSpecifiers = [moduleAndSpecifiers]; - const initFragment = new ModuleExternalInitFragment( - moduleAndSpecifiers[0], - undefined, - hashFunction - ); - const baseAccess = `${initFragment.getNamespaceIdentifier()}${propertyAccess( - moduleAndSpecifiers, - 1 - )}`; - const moduleRemapping = generateModuleRemapping( - baseAccess, - exportsInfo, - runtime - ); - let expression = moduleRemapping || baseAccess; - return { - expression, - init: `var x = y => { var x = {}; ${RuntimeGlobals.definePropertyGetters}(x, y); return x; }\nvar y = x => () => x`, - runtimeRequirements: moduleRemapping - ? RUNTIME_REQUIREMENTS_FOR_MODULE - : undefined, - chunkInitFragments: [initFragment] - }; -}; - -/** - * @param {string|string[]} urlAndGlobal the script request - * @param {RuntimeTemplate} runtimeTemplate the runtime template - * @returns {SourceData} the generated source - */ -const getSourceForScriptExternal = (urlAndGlobal, runtimeTemplate) => { - if (typeof urlAndGlobal === "string") { - urlAndGlobal = extractUrlAndGlobal(urlAndGlobal); - } - const url = urlAndGlobal[0]; - const globalName = urlAndGlobal[1]; - return { - init: "var __webpack_error__ = new Error();", - expression: `new Promise(${runtimeTemplate.basicFunction( - "resolve, reject", - [ - `if(typeof ${globalName} !== "undefined") return resolve();`, - `${RuntimeGlobals.loadScript}(${JSON.stringify( - url - )}, ${runtimeTemplate.basicFunction("event", [ - `if(typeof ${globalName} !== "undefined") return resolve();`, - "var errorType = event && (event.type === 'load' ? 'missing' : event.type);", - "var realSrc = event && event.target && event.target.src;", - "__webpack_error__.message = 'Loading script failed.\\n(' + errorType + ': ' + realSrc + ')';", - "__webpack_error__.name = 'ScriptExternalLoadError';", - "__webpack_error__.type = errorType;", - "__webpack_error__.request = realSrc;", - "reject(__webpack_error__);" - ])}, ${JSON.stringify(globalName)});` - ] - )}).then(${runtimeTemplate.returningFunction( - `${globalName}${propertyAccess(urlAndGlobal, 2)}` - )})`, - runtimeRequirements: RUNTIME_REQUIREMENTS_FOR_SCRIPT - }; -}; - -/** - * @param {string} variableName the variable name to check - * @param {string} request the request path - * @param {RuntimeTemplate} runtimeTemplate the runtime template - * @returns {string} the generated source - */ -const checkExternalVariable = (variableName, request, runtimeTemplate) => { - return `if(typeof ${variableName} === 'undefined') { ${runtimeTemplate.throwMissingModuleErrorBlock( - { request } - )} }\n`; -}; - -/** - * @param {string|number} id the module id - * @param {boolean} optional true, if the module is optional - * @param {string|string[]} request the request path - * @param {RuntimeTemplate} runtimeTemplate the runtime template - * @returns {SourceData} the generated source - */ -const getSourceForAmdOrUmdExternal = ( - id, - optional, - request, - runtimeTemplate -) => { - const externalVariable = `__WEBPACK_EXTERNAL_MODULE_${Template.toIdentifier( - `${id}` - )}__`; - return { - init: optional - ? checkExternalVariable( - externalVariable, - Array.isArray(request) ? request.join(".") : request, - runtimeTemplate - ) - : undefined, - expression: externalVariable - }; -}; - -/** - * @param {boolean} optional true, if the module is optional - * @param {string|string[]} request the request path - * @param {RuntimeTemplate} runtimeTemplate the runtime template - * @returns {SourceData} the generated source - */ -const getSourceForDefaultCase = (optional, request, runtimeTemplate) => { - if (!Array.isArray(request)) { - // make it an array as the look up works the same basically - request = [request]; - } - - const variableName = request[0]; - const objectLookup = propertyAccess(request, 1); - return { - init: optional - ? checkExternalVariable(variableName, request.join("."), runtimeTemplate) - : undefined, - expression: `${variableName}${objectLookup}` - }; -}; - -class ExternalModule extends Module { - constructor(request, type, userRequest) { - super("javascript/dynamic", null); - - // Info from Factory - /** @type {string | string[] | Record} */ - this.request = request; - /** @type {string} */ - this.externalType = type; - /** @type {string} */ - this.userRequest = userRequest; - } - - /** - * @returns {Set} types available (do not mutate) - */ - getSourceTypes() { - return TYPES; - } - - /** - * @param {LibIdentOptions} options options - * @returns {string | null} an identifier for library inclusion - */ - libIdent(options) { - return this.userRequest; - } - - /** - * @param {Chunk} chunk the chunk which condition should be checked - * @param {Compilation} compilation the compilation - * @returns {boolean} true, if the chunk is ok for the module - */ - chunkCondition(chunk, { chunkGraph }) { - return chunkGraph.getNumberOfEntryModules(chunk) > 0; - } - - /** - * @returns {string} a unique identifier of the module - */ - identifier() { - return `external ${this.externalType} ${JSON.stringify(this.request)}`; - } - - /** - * @param {RequestShortener} requestShortener the request shortener - * @returns {string} a user readable identifier of the module - */ - readableIdentifier(requestShortener) { - return "external " + JSON.stringify(this.request); + /** + * @param {RequestShortener} requestShortener the request shortener + * @returns {string} a user readable identifier of the module + */ + readableIdentifier(requestShortener) { + return `delegated ${this.userRequest} from ${this.sourceRequest}`; } /** @@ -41903,227 +39477,62 @@ class ExternalModule extends Module { * @returns {void} */ build(options, compilation, resolver, fs, callback) { - this.buildMeta = { - async: false, - exportsType: undefined - }; - this.buildInfo = { - strict: true, - topLevelDeclarations: new Set(), - module: compilation.outputOptions.module - }; - const { request, externalType } = this._getRequestAndExternalType(); - this.buildMeta.exportsType = "dynamic"; - let canMangle = false; - this.clearDependenciesAndBlocks(); - switch (externalType) { - case "this": - this.buildInfo.strict = false; - break; - case "system": - if (!Array.isArray(request) || request.length === 1) { - this.buildMeta.exportsType = "namespace"; - canMangle = true; - } - break; - case "module": - if (this.buildInfo.module) { - if (!Array.isArray(request) || request.length === 1) { - this.buildMeta.exportsType = "namespace"; - canMangle = true; - } - } else { - this.buildMeta.async = true; - if (!Array.isArray(request) || request.length === 1) { - this.buildMeta.exportsType = "namespace"; - canMangle = false; - } - } - break; - case "script": - case "promise": - this.buildMeta.async = true; - break; - case "import": - this.buildMeta.async = true; - if (!Array.isArray(request) || request.length === 1) { - this.buildMeta.exportsType = "namespace"; - canMangle = false; - } - break; - } - this.addDependency(new StaticExportsDependency(true, canMangle)); + this.buildMeta = { ...this.delegateData.buildMeta }; + this.buildInfo = {}; + this.dependencies.length = 0; + this.delegatedSourceDependency = new DelegatedSourceDependency( + this.sourceRequest + ); + this.addDependency(this.delegatedSourceDependency); + this.addDependency( + new StaticExportsDependency(this.delegateData.exports || true, false) + ); callback(); } - restoreFromUnsafeCache(unsafeCacheData, normalModuleFactory) { - this._restoreFromUnsafeCache(unsafeCacheData, normalModuleFactory); - } - - /** - * @param {ConcatenationBailoutReasonContext} context context - * @returns {string | undefined} reason why this module can't be concatenated, undefined when it can be concatenated - */ - getConcatenationBailoutReason({ moduleGraph }) { - switch (this.externalType) { - case "amd": - case "amd-require": - case "umd": - case "umd2": - case "system": - case "jsonp": - return `${this.externalType} externals can't be concatenated`; - } - return undefined; - } - - _getRequestAndExternalType() { - let { request, externalType } = this; - if (typeof request === "object" && !Array.isArray(request)) - request = request[externalType]; - return { request, externalType }; - } - - _getSourceData(runtimeTemplate, moduleGraph, chunkGraph, runtime) { - const { request, externalType } = this._getRequestAndExternalType(); - switch (externalType) { - case "this": - case "window": - case "self": - return getSourceForGlobalVariableExternal(request, this.externalType); - case "global": - return getSourceForGlobalVariableExternal( - request, - runtimeTemplate.outputOptions.globalObject - ); - case "commonjs": - case "commonjs2": - case "commonjs-module": - return getSourceForCommonJsExternal(request); - case "node-commonjs": - return this.buildInfo.module - ? getSourceForCommonJsExternalInNodeModule(request) - : getSourceForCommonJsExternal(request); - case "amd": - case "amd-require": - case "umd": - case "umd2": - case "system": - case "jsonp": { - const id = chunkGraph.getModuleId(this); - return getSourceForAmdOrUmdExternal( - id !== null ? id : this.identifier(), - this.isOptional(moduleGraph), - request, - runtimeTemplate - ); - } - case "import": - return getSourceForImportExternal(request, runtimeTemplate); - case "script": - return getSourceForScriptExternal(request, runtimeTemplate); - case "module": { - if (!this.buildInfo.module) { - if (!runtimeTemplate.supportsDynamicImport()) { - throw new Error( - "The target environment doesn't support dynamic import() syntax so it's not possible to use external type 'module' within a script" + - (runtimeTemplate.supportsEcmaScriptModuleSyntax() - ? "\nDid you mean to build a EcmaScript Module ('output.module: true')?" - : "") - ); - } - return getSourceForImportExternal(request, runtimeTemplate); - } - if (!runtimeTemplate.supportsEcmaScriptModuleSyntax()) { - throw new Error( - "The target environment doesn't support EcmaScriptModule syntax so it's not possible to use external type 'module'" - ); - } - return getSourceForModuleExternal( - request, - moduleGraph.getExportsInfo(this), - runtime, - runtimeTemplate.outputOptions.hashFunction - ); - } - case "var": - case "promise": - case "const": - case "let": - case "assign": - default: - return getSourceForDefaultCase( - this.isOptional(moduleGraph), - request, - runtimeTemplate - ); - } - } - /** * @param {CodeGenerationContext} context context for code generation * @returns {CodeGenerationResult} result */ - codeGeneration({ - runtimeTemplate, - moduleGraph, - chunkGraph, - runtime, - concatenationScope - }) { - const sourceData = this._getSourceData( - runtimeTemplate, - moduleGraph, - chunkGraph, - runtime - ); + codeGeneration({ runtimeTemplate, moduleGraph, chunkGraph }) { + const dep = /** @type {DelegatedSourceDependency} */ (this.dependencies[0]); + const sourceModule = moduleGraph.getModule(dep); + let str; - let sourceString = sourceData.expression; - if (sourceData.iife) - sourceString = `(function() { return ${sourceString}; }())`; - if (concatenationScope) { - sourceString = `${runtimeTemplate.supportsConst() ? "const" : "var"} ${ - ConcatenationScope.NAMESPACE_OBJECT_EXPORT - } = ${sourceString};`; - concatenationScope.registerNamespaceExport( - ConcatenationScope.NAMESPACE_OBJECT_EXPORT - ); + if (!sourceModule) { + str = runtimeTemplate.throwMissingModuleErrorBlock({ + request: this.sourceRequest + }); } else { - sourceString = `module.exports = ${sourceString};`; - } - if (sourceData.init) sourceString = `${sourceData.init}\n${sourceString}`; + str = `module.exports = (${runtimeTemplate.moduleExports({ + module: sourceModule, + chunkGraph, + request: dep.request, + runtimeRequirements: new Set() + })})`; - let data = undefined; - if (sourceData.chunkInitFragments) { - data = new Map(); - data.set("chunkInitFragments", sourceData.chunkInitFragments); + switch (this.delegationType) { + case "require": + str += `(${JSON.stringify(this.request)})`; + break; + case "object": + str += `[${JSON.stringify(this.request)}]`; + break; + } + + str += ";"; } const sources = new Map(); if (this.useSourceMap || this.useSimpleSourceMap) { - sources.set( - "javascript", - new OriginalSource(sourceString, this.identifier()) - ); + sources.set("javascript", new OriginalSource(str, this.identifier())); } else { - sources.set("javascript", new RawSource(sourceString)); - } - - let runtimeRequirements = sourceData.runtimeRequirements; - if (!concatenationScope) { - if (!runtimeRequirements) { - runtimeRequirements = RUNTIME_REQUIREMENTS; - } else { - const set = new Set(runtimeRequirements); - set.add(RuntimeGlobals.module); - runtimeRequirements = set; - } + sources.set("javascript", new RawSource(str)); } return { sources, - runtimeRequirements: runtimeRequirements || EMPTY_RUNTIME_REQUIREMENTS, - data + runtimeRequirements: RUNTIME_REQUIREMENTS }; } @@ -42141,44 +39550,68 @@ class ExternalModule extends Module { * @returns {void} */ updateHash(hash, context) { - const { chunkGraph } = context; - hash.update( - `${this.externalType}${JSON.stringify(this.request)}${this.isOptional( - chunkGraph.moduleGraph - )}` - ); + hash.update(this.delegationType); + hash.update(JSON.stringify(this.request)); super.updateHash(hash, context); } serialize(context) { const { write } = context; - - write(this.request); - write(this.externalType); + // constructor + write(this.sourceRequest); + write(this.delegateData); + write(this.delegationType); write(this.userRequest); - + write(this.originalRequest); super.serialize(context); } - deserialize(context) { + static deserialize(context) { const { read } = context; - - this.request = read(); - this.externalType = read(); - this.userRequest = read(); - - super.deserialize(context); + const obj = new DelegatedModule( + read(), // sourceRequest + read(), // delegateData + read(), // delegationType + read(), // userRequest + read() // originalRequest + ); + obj.deserialize(context); + return obj; } -} -makeSerializable(ExternalModule, "webpack/lib/ExternalModule"); - -module.exports = ExternalModule; - - -/***/ }), - -/***/ 19364: + /** + * Assuming this module is in the cache. Update the (cached) module with + * the fresh module from the factory. Usually updates internal references + * and properties. + * @param {Module} module fresh module + * @returns {void} + */ + updateCacheModule(module) { + super.updateCacheModule(module); + const m = /** @type {DelegatedModule} */ (module); + this.delegationType = m.delegationType; + this.userRequest = m.userRequest; + this.originalRequest = m.originalRequest; + this.delegateData = m.delegateData; + } + + /** + * Assuming this module is in the cache. Remove internal references to allow freeing some memory. + */ + cleanupForCache() { + super.cleanupForCache(); + this.delegateData = undefined; + } +} + +makeSerializable(DelegatedModule, "webpack/lib/DelegatedModule"); + +module.exports = DelegatedModule; + + +/***/ }), + +/***/ 50756: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; @@ -42189,258 +39622,95 @@ module.exports = ExternalModule; -const util = __webpack_require__(31669); -const ExternalModule = __webpack_require__(89805); -const { resolveByProperty, cachedSetProperty } = __webpack_require__(11217); - -/** @typedef {import("../declarations/WebpackOptions").Externals} Externals */ -/** @typedef {import("./NormalModuleFactory")} NormalModuleFactory */ - -const UNSPECIFIED_EXTERNAL_TYPE_REGEXP = /^[a-z0-9-]+ /; -const EMPTY_RESOLVE_OPTIONS = {}; - -// TODO webpack 6 remove this -const callDeprecatedExternals = util.deprecate( - (externalsFunction, context, request, cb) => { - externalsFunction.call(null, context, request, cb); - }, - "The externals-function should be defined like ({context, request}, cb) => { ... }", - "DEP_WEBPACK_EXTERNALS_FUNCTION_PARAMETERS" -); - -const cache = new WeakMap(); - -const resolveLayer = (obj, layer) => { - let map = cache.get(obj); - if (map === undefined) { - map = new Map(); - cache.set(obj, map); - } else { - const cacheEntry = map.get(layer); - if (cacheEntry !== undefined) return cacheEntry; - } - const result = resolveByProperty(obj, "byLayer", layer); - map.set(layer, result); - return result; -}; +const DelegatedModule = __webpack_require__(68719); -class ExternalModuleFactoryPlugin { - /** - * @param {string | undefined} type default external type - * @param {Externals} externals externals config - */ - constructor(type, externals) { - this.type = type; - this.externals = externals; +// options.source +// options.type +// options.context +// options.scope +// options.content +// options.associatedObjectForCache +class DelegatedModuleFactoryPlugin { + constructor(options) { + this.options = options; + options.type = options.type || "require"; + options.extensions = options.extensions || ["", ".js", ".json", ".wasm"]; } - /** - * @param {NormalModuleFactory} normalModuleFactory the normal module factory - * @returns {void} - */ apply(normalModuleFactory) { - const globalType = this.type; - normalModuleFactory.hooks.factorize.tapAsync( - "ExternalModuleFactoryPlugin", - (data, callback) => { - const context = data.context; - const contextInfo = data.contextInfo; - const dependency = data.dependencies[0]; - const dependencyType = data.dependencyType; - - /** - * @param {string|string[]|boolean|Record} value the external config - * @param {string|undefined} type type of external - * @param {function(Error=, ExternalModule=): void} callback callback - * @returns {void} - */ - const handleExternal = (value, type, callback) => { - if (value === false) { - // Not externals, fallback to original factory - return callback(); - } - /** @type {string | string[] | Record} */ - let externalConfig; - if (value === true) { - externalConfig = dependency.request; - } else { - externalConfig = value; - } - // When no explicit type is specified, extract it from the externalConfig - if (type === undefined) { - if ( - typeof externalConfig === "string" && - UNSPECIFIED_EXTERNAL_TYPE_REGEXP.test(externalConfig) - ) { - const idx = externalConfig.indexOf(" "); - type = externalConfig.substr(0, idx); - externalConfig = externalConfig.substr(idx + 1); - } else if ( - Array.isArray(externalConfig) && - externalConfig.length > 0 && - UNSPECIFIED_EXTERNAL_TYPE_REGEXP.test(externalConfig[0]) - ) { - const firstItem = externalConfig[0]; - const idx = firstItem.indexOf(" "); - type = firstItem.substr(0, idx); - externalConfig = [ - firstItem.substr(idx + 1), - ...externalConfig.slice(1) - ]; - } - } - callback( - null, - new ExternalModule( - externalConfig, - type || globalType, - dependency.request - ) - ); - }; - - /** - * @param {Externals} externals externals config - * @param {function(Error=, ExternalModule=): void} callback callback - * @returns {void} - */ - const handleExternals = (externals, callback) => { - if (typeof externals === "string") { - if (externals === dependency.request) { - return handleExternal(dependency.request, undefined, callback); - } - } else if (Array.isArray(externals)) { - let i = 0; - const next = () => { - let asyncFlag; - const handleExternalsAndCallback = (err, module) => { - if (err) return callback(err); - if (!module) { - if (asyncFlag) { - asyncFlag = false; - return; - } - return next(); - } - callback(null, module); - }; - - do { - asyncFlag = true; - if (i >= externals.length) return callback(); - handleExternals(externals[i++], handleExternalsAndCallback); - } while (!asyncFlag); - asyncFlag = false; - }; - - next(); - return; - } else if (externals instanceof RegExp) { - if (externals.test(dependency.request)) { - return handleExternal(dependency.request, undefined, callback); + const scope = this.options.scope; + if (scope) { + normalModuleFactory.hooks.factorize.tapAsync( + "DelegatedModuleFactoryPlugin", + (data, callback) => { + const [dependency] = data.dependencies; + const { request } = dependency; + if (request && request.startsWith(`${scope}/`)) { + const innerRequest = "." + request.substr(scope.length); + let resolved; + if (innerRequest in this.options.content) { + resolved = this.options.content[innerRequest]; + return callback( + null, + new DelegatedModule( + this.options.source, + resolved, + this.options.type, + innerRequest, + request + ) + ); } - } else if (typeof externals === "function") { - const cb = (err, value, type) => { - if (err) return callback(err); - if (value !== undefined) { - handleExternal(value, type, callback); - } else { - callback(); + for (let i = 0; i < this.options.extensions.length; i++) { + const extension = this.options.extensions[i]; + const requestPlusExt = innerRequest + extension; + if (requestPlusExt in this.options.content) { + resolved = this.options.content[requestPlusExt]; + return callback( + null, + new DelegatedModule( + this.options.source, + resolved, + this.options.type, + requestPlusExt, + request + extension + ) + ); } - }; - if (externals.length === 3) { - // TODO webpack 6 remove this - callDeprecatedExternals( - externals, - context, - dependency.request, - cb - ); - } else { - const promise = externals( - { - context, - request: dependency.request, - dependencyType, - contextInfo, - getResolve: options => (context, request, callback) => { - const resolveContext = { - fileDependencies: data.fileDependencies, - missingDependencies: data.missingDependencies, - contextDependencies: data.contextDependencies - }; - let resolver = normalModuleFactory.getResolver( - "normal", - dependencyType - ? cachedSetProperty( - data.resolveOptions || EMPTY_RESOLVE_OPTIONS, - "dependencyType", - dependencyType - ) - : data.resolveOptions - ); - if (options) resolver = resolver.withOptions(options); - if (callback) { - resolver.resolve( - {}, - context, - request, - resolveContext, - callback - ); - } else { - return new Promise((resolve, reject) => { - resolver.resolve( - {}, - context, - request, - resolveContext, - (err, result) => { - if (err) reject(err); - else resolve(result); - } - ); - }); - } - } - }, - cb - ); - if (promise && promise.then) promise.then(r => cb(null, r), cb); } - return; - } else if (typeof externals === "object") { - const resolvedExternals = resolveLayer( - externals, - contextInfo.issuerLayer - ); - if ( - Object.prototype.hasOwnProperty.call( - resolvedExternals, - dependency.request - ) - ) { - return handleExternal( - resolvedExternals[dependency.request], - undefined, - callback + } + return callback(); + } + ); + } else { + normalModuleFactory.hooks.module.tap( + "DelegatedModuleFactoryPlugin", + module => { + const request = module.libIdent(this.options); + if (request) { + if (request in this.options.content) { + const resolved = this.options.content[request]; + return new DelegatedModule( + this.options.source, + resolved, + this.options.type, + request, + module ); } } - callback(); - }; - - handleExternals(this.externals, callback); - } - ); + return module; + } + ); + } } } -module.exports = ExternalModuleFactoryPlugin; +module.exports = DelegatedModuleFactoryPlugin; /***/ }), -/***/ 361: +/***/ 48248: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; @@ -42451,19 +39721,14 @@ module.exports = ExternalModuleFactoryPlugin; -const ExternalModuleFactoryPlugin = __webpack_require__(19364); +const DelegatedModuleFactoryPlugin = __webpack_require__(50756); +const DelegatedSourceDependency = __webpack_require__(82766); -/** @typedef {import("../declarations/WebpackOptions").Externals} Externals */ /** @typedef {import("./Compiler")} Compiler */ -class ExternalsPlugin { - /** - * @param {string | undefined} type default external type - * @param {Externals} externals externals config - */ - constructor(type, externals) { - this.type = type; - this.externals = externals; +class DelegatedPlugin { + constructor(options) { + this.options = options; } /** @@ -42472,20 +39737,31 @@ class ExternalsPlugin { * @returns {void} */ apply(compiler) { - compiler.hooks.compile.tap("ExternalsPlugin", ({ normalModuleFactory }) => { - new ExternalModuleFactoryPlugin(this.type, this.externals).apply( - normalModuleFactory - ); + compiler.hooks.compilation.tap( + "DelegatedPlugin", + (compilation, { normalModuleFactory }) => { + compilation.dependencyFactories.set( + DelegatedSourceDependency, + normalModuleFactory + ); + } + ); + + compiler.hooks.compile.tap("DelegatedPlugin", ({ normalModuleFactory }) => { + new DelegatedModuleFactoryPlugin({ + associatedObjectForCache: compiler.root, + ...this.options + }).apply(normalModuleFactory); }); } } -module.exports = ExternalsPlugin; +module.exports = DelegatedPlugin; /***/ }), -/***/ 13679: +/***/ 21484: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; @@ -42496,3559 +39772,1618 @@ module.exports = ExternalsPlugin; -const { create: createResolver } = __webpack_require__(27480); -const asyncLib = __webpack_require__(36386); -const AsyncQueue = __webpack_require__(55531); -const StackedCacheMap = __webpack_require__(26009); -const createHash = __webpack_require__(24123); -const { join, dirname, relative, lstatReadlinkAbsolute } = __webpack_require__(93204); const makeSerializable = __webpack_require__(26522); -const processAsyncTree = __webpack_require__(76815); - -/** @typedef {import("./WebpackError")} WebpackError */ -/** @typedef {import("./logging/Logger").Logger} Logger */ -/** @typedef {typeof import("./util/Hash")} Hash */ -/** @typedef {import("./util/fs").IStats} IStats */ -/** @typedef {import("./util/fs").InputFileSystem} InputFileSystem */ -const supportsEsm = +process.versions.modules >= 83; +/** @typedef {import("./AsyncDependenciesBlock")} AsyncDependenciesBlock */ +/** @typedef {import("./ChunkGraph")} ChunkGraph */ +/** @typedef {import("./ChunkGroup")} ChunkGroup */ +/** @typedef {import("./Dependency")} Dependency */ +/** @typedef {import("./Dependency").UpdateHashContext} UpdateHashContext */ +/** @typedef {import("./util/Hash")} Hash */ -let FS_ACCURACY = 2000; +/** @typedef {(d: Dependency) => boolean} DependencyFilterFunction */ -const EMPTY_SET = new Set(); +class DependenciesBlock { + constructor() { + /** @type {Dependency[]} */ + this.dependencies = []; + /** @type {AsyncDependenciesBlock[]} */ + this.blocks = []; + /** @type {DependenciesBlock} */ + this.parent = undefined; + } -const RBDT_RESOLVE_CJS = 0; -const RBDT_RESOLVE_ESM = 1; -const RBDT_RESOLVE_DIRECTORY = 2; -const RBDT_RESOLVE_CJS_FILE = 3; -const RBDT_RESOLVE_CJS_FILE_AS_CHILD = 4; -const RBDT_RESOLVE_ESM_FILE = 5; -const RBDT_DIRECTORY = 6; -const RBDT_FILE = 7; -const RBDT_DIRECTORY_DEPENDENCIES = 8; -const RBDT_FILE_DEPENDENCIES = 9; + getRootBlock() { + /** @type {DependenciesBlock} */ + let current = this; + while (current.parent) current = current.parent; + return current; + } -const INVALID = Symbol("invalid"); + /** + * Adds a DependencyBlock to DependencyBlock relationship. + * This is used for when a Module has a AsyncDependencyBlock tie (for code-splitting) + * + * @param {AsyncDependenciesBlock} block block being added + * @returns {void} + */ + addBlock(block) { + this.blocks.push(block); + block.parent = this; + } -/** - * @typedef {Object} FileSystemInfoEntry - * @property {number} safeTime - * @property {number=} timestamp - */ + /** + * @param {Dependency} dependency dependency being tied to block. + * This is an "edge" pointing to another "node" on module graph. + * @returns {void} + */ + addDependency(dependency) { + this.dependencies.push(dependency); + } -/** - * @typedef {Object} ResolvedContextFileSystemInfoEntry - * @property {number} safeTime - * @property {string=} timestampHash - */ + /** + * @param {Dependency} dependency dependency being removed + * @returns {void} + */ + removeDependency(dependency) { + const idx = this.dependencies.indexOf(dependency); + if (idx >= 0) { + this.dependencies.splice(idx, 1); + } + } -/** - * @typedef {Object} ContextFileSystemInfoEntry - * @property {number} safeTime - * @property {string=} timestampHash - * @property {ResolvedContextFileSystemInfoEntry=} resolved - * @property {Set=} symlinks - */ + /** + * Removes all dependencies and blocks + * @returns {void} + */ + clearDependenciesAndBlocks() { + this.dependencies.length = 0; + this.blocks.length = 0; + } -/** - * @typedef {Object} TimestampAndHash - * @property {number} safeTime - * @property {number=} timestamp - * @property {string} hash - */ + /** + * @param {Hash} hash the hash used to track dependencies + * @param {UpdateHashContext} context context + * @returns {void} + */ + updateHash(hash, context) { + for (const dep of this.dependencies) { + dep.updateHash(hash, context); + } + for (const block of this.blocks) { + block.updateHash(hash, context); + } + } -/** - * @typedef {Object} ResolvedContextTimestampAndHash - * @property {number} safeTime - * @property {string=} timestampHash - * @property {string} hash - */ + serialize({ write }) { + write(this.dependencies); + write(this.blocks); + } + + deserialize({ read }) { + this.dependencies = read(); + this.blocks = read(); + for (const block of this.blocks) { + block.parent = this; + } + } +} + +makeSerializable(DependenciesBlock, "webpack/lib/DependenciesBlock"); + +module.exports = DependenciesBlock; + + +/***/ }), + +/***/ 50384: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ + + + +const memoize = __webpack_require__(84297); + +/** @typedef {import("webpack-sources").Source} Source */ +/** @typedef {import("./ChunkGraph")} ChunkGraph */ +/** @typedef {import("./DependenciesBlock")} DependenciesBlock */ +/** @typedef {import("./DependencyTemplates")} DependencyTemplates */ +/** @typedef {import("./Module")} Module */ +/** @typedef {import("./ModuleGraph")} ModuleGraph */ +/** @typedef {import("./ModuleGraphConnection")} ModuleGraphConnection */ +/** @typedef {import("./ModuleGraphConnection").ConnectionState} ConnectionState */ +/** @typedef {import("./RuntimeTemplate")} RuntimeTemplate */ +/** @typedef {import("./WebpackError")} WebpackError */ +/** @typedef {import("./util/Hash")} Hash */ +/** @typedef {import("./util/runtime").RuntimeSpec} RuntimeSpec */ /** - * @typedef {Object} ContextTimestampAndHash - * @property {number} safeTime - * @property {string=} timestampHash - * @property {string} hash - * @property {ResolvedContextTimestampAndHash=} resolved - * @property {Set=} symlinks + * @typedef {Object} UpdateHashContext + * @property {ChunkGraph} chunkGraph + * @property {RuntimeSpec} runtime + * @property {RuntimeTemplate=} runtimeTemplate */ /** - * @typedef {Object} ContextHash - * @property {string} hash - * @property {string=} resolved - * @property {Set=} symlinks + * @typedef {Object} SourcePosition + * @property {number} line + * @property {number=} column */ /** - * @typedef {Object} SnapshotOptimizationEntry - * @property {Snapshot} snapshot - * @property {number} shared - * @property {Set} snapshotContent - * @property {Set} children + * @typedef {Object} RealDependencyLocation + * @property {SourcePosition} start + * @property {SourcePosition=} end + * @property {number=} index */ /** - * @typedef {Object} ResolveBuildDependenciesResult - * @property {Set} files list of files - * @property {Set} directories list of directories - * @property {Set} missing list of missing entries - * @property {Map} resolveResults stored resolve results - * @property {Object} resolveDependencies dependencies of the resolving - * @property {Set} resolveDependencies.files list of files - * @property {Set} resolveDependencies.directories list of directories - * @property {Set} resolveDependencies.missing list of missing entries + * @typedef {Object} SyntheticDependencyLocation + * @property {string} name + * @property {number=} index */ -const DONE_ITERATOR_RESULT = new Set().keys().next(); +/** @typedef {SyntheticDependencyLocation|RealDependencyLocation} DependencyLocation */ -// cspell:word tshs -// Tsh = Timestamp + Hash -// Tshs = Timestamp + Hash combinations +/** + * @typedef {Object} ExportSpec + * @property {string} name the name of the export + * @property {boolean=} canMangle can the export be renamed (defaults to true) + * @property {boolean=} terminalBinding is the export a terminal binding that should be checked for export star conflicts + * @property {(string | ExportSpec)[]=} exports nested exports + * @property {ModuleGraphConnection=} from when reexported: from which module + * @property {string[] | null=} export when reexported: from which export + * @property {number=} priority when reexported: with which priority + * @property {boolean=} hidden export is not visible, because another export blends over it + */ -class SnapshotIterator { - constructor(next) { - this.next = next; - } -} +/** + * @typedef {Object} ExportsSpec + * @property {(string | ExportSpec)[] | true | null} exports exported names, true for unknown exports or null for no exports + * @property {Set=} excludeExports when exports = true, list of unaffected exports + * @property {Set=} hideExports list of maybe prior exposed, but now hidden exports + * @property {ModuleGraphConnection=} from when reexported: from which module + * @property {number=} priority when reexported: with which priority + * @property {boolean=} canMangle can the export be renamed (defaults to true) + * @property {boolean=} terminalBinding are the exports terminal bindings that should be checked for export star conflicts + * @property {Module[]=} dependencies module on which the result depends on + */ -class SnapshotIterable { - constructor(snapshot, getMaps) { - this.snapshot = snapshot; - this.getMaps = getMaps; - } +/** + * @typedef {Object} ReferencedExport + * @property {string[]} name name of the referenced export + * @property {boolean=} canMangle when false, referenced export can not be mangled, defaults to true + */ - [Symbol.iterator]() { - let state = 0; - /** @type {IterableIterator} */ - let it; - /** @type {(Snapshot) => (Map | Set)[]} */ - let getMaps; - /** @type {(Map | Set)[]} */ - let maps; - /** @type {Snapshot} */ - let snapshot; - let queue; - return new SnapshotIterator(() => { - for (;;) { - switch (state) { - case 0: - snapshot = this.snapshot; - getMaps = this.getMaps; - maps = getMaps(snapshot); - state = 1; - /* falls through */ - case 1: - if (maps.length > 0) { - const map = maps.pop(); - if (map !== undefined) { - it = map.keys(); - state = 2; - } else { - break; - } - } else { - state = 3; - break; - } - /* falls through */ - case 2: { - const result = it.next(); - if (!result.done) return result; - state = 1; - break; - } - case 3: { - const children = snapshot.children; - if (children !== undefined) { - if (children.size === 1) { - // shortcut for a single child - // avoids allocation of queue - for (const child of children) snapshot = child; - maps = getMaps(snapshot); - state = 1; - break; - } - if (queue === undefined) queue = []; - for (const child of children) { - queue.push(child); - } - } - if (queue !== undefined && queue.length > 0) { - snapshot = queue.pop(); - maps = getMaps(snapshot); - state = 1; - break; - } else { - state = 4; - } - } - /* falls through */ - case 4: - return DONE_ITERATOR_RESULT; - } - } - }); - } -} +const TRANSITIVE = Symbol("transitive"); -class Snapshot { +const getIgnoredModule = memoize(() => { + const RawModule = __webpack_require__(82329); + return new RawModule("/* (ignored) */", `ignored`, `(ignored)`); +}); + +class Dependency { constructor() { - this._flags = 0; - /** @type {number | undefined} */ - this.startTime = undefined; - /** @type {Map | undefined} */ - this.fileTimestamps = undefined; - /** @type {Map | undefined} */ - this.fileHashes = undefined; - /** @type {Map | undefined} */ - this.fileTshs = undefined; - /** @type {Map | undefined} */ - this.contextTimestamps = undefined; - /** @type {Map | undefined} */ - this.contextHashes = undefined; - /** @type {Map | undefined} */ - this.contextTshs = undefined; - /** @type {Map | undefined} */ - this.missingExistence = undefined; - /** @type {Map | undefined} */ - this.managedItemInfo = undefined; - /** @type {Set | undefined} */ - this.managedFiles = undefined; - /** @type {Set | undefined} */ - this.managedContexts = undefined; - /** @type {Set | undefined} */ - this.managedMissing = undefined; - /** @type {Set | undefined} */ - this.children = undefined; + /** @type {Module} */ + this._parentModule = undefined; + /** @type {DependenciesBlock} */ + this._parentDependenciesBlock = undefined; + /** @type {number} */ + this._parentDependenciesBlockIndex = -1; + // TODO check if this can be moved into ModuleDependency + /** @type {boolean} */ + this.weak = false; + // TODO check if this can be moved into ModuleDependency + /** @type {boolean} */ + this.optional = false; + this._locSL = 0; + this._locSC = 0; + this._locEL = 0; + this._locEC = 0; + this._locI = undefined; + this._locN = undefined; + this._loc = undefined; } - hasStartTime() { - return (this._flags & 1) !== 0; + /** + * @returns {string} a display name for the type of dependency + */ + get type() { + return "unknown"; } - setStartTime(value) { - this._flags = this._flags | 1; - this.startTime = value; + /** + * @returns {string} a dependency category, typical categories are "commonjs", "amd", "esm" + */ + get category() { + return "unknown"; } - setMergedStartTime(value, snapshot) { - if (value) { - if (snapshot.hasStartTime()) { - this.setStartTime(Math.min(value, snapshot.startTime)); - } else { - this.setStartTime(value); - } - } else { - if (snapshot.hasStartTime()) this.setStartTime(snapshot.startTime); + /** + * @returns {DependencyLocation} location + */ + get loc() { + if (this._loc !== undefined) return this._loc; + /** @type {SyntheticDependencyLocation & RealDependencyLocation} */ + const loc = {}; + if (this._locSL > 0) { + loc.start = { line: this._locSL, column: this._locSC }; + } + if (this._locEL > 0) { + loc.end = { line: this._locEL, column: this._locEC }; + } + if (this._locN !== undefined) { + loc.name = this._locN; } + if (this._locI !== undefined) { + loc.index = this._locI; + } + return (this._loc = loc); } - hasFileTimestamps() { - return (this._flags & 2) !== 0; + set loc(loc) { + if ("start" in loc && typeof loc.start === "object") { + this._locSL = loc.start.line || 0; + this._locSC = loc.start.column || 0; + } else { + this._locSL = 0; + this._locSC = 0; + } + if ("end" in loc && typeof loc.end === "object") { + this._locEL = loc.end.line || 0; + this._locEC = loc.end.column || 0; + } else { + this._locEL = 0; + this._locEC = 0; + } + if ("index" in loc) { + this._locI = loc.index; + } else { + this._locI = undefined; + } + if ("name" in loc) { + this._locN = loc.name; + } else { + this._locN = undefined; + } + this._loc = loc; } - setFileTimestamps(value) { - this._flags = this._flags | 2; - this.fileTimestamps = value; + /** + * @returns {string | null} an identifier to merge equal requests + */ + getResourceIdentifier() { + return null; } - hasFileHashes() { - return (this._flags & 4) !== 0; + /** + * @returns {boolean | TRANSITIVE} true, when changes to the referenced module could affect the referencing module; TRANSITIVE, when changes to the referenced module could affect referencing modules of the referencing module + */ + couldAffectReferencingModule() { + return TRANSITIVE; } - setFileHashes(value) { - this._flags = this._flags | 4; - this.fileHashes = value; + /** + * Returns the referenced module and export + * @deprecated + * @param {ModuleGraph} moduleGraph module graph + * @returns {never} throws error + */ + getReference(moduleGraph) { + throw new Error( + "Dependency.getReference was removed in favor of Dependency.getReferencedExports, ModuleGraph.getModule and ModuleGraph.getConnection().active" + ); } - hasFileTshs() { - return (this._flags & 8) !== 0; + /** + * Returns list of exports referenced by this dependency + * @param {ModuleGraph} moduleGraph module graph + * @param {RuntimeSpec} runtime the runtime for which the module is analysed + * @returns {(string[] | ReferencedExport)[]} referenced exports + */ + getReferencedExports(moduleGraph, runtime) { + return Dependency.EXPORTS_OBJECT_REFERENCED; } - setFileTshs(value) { - this._flags = this._flags | 8; - this.fileTshs = value; + /** + * @param {ModuleGraph} moduleGraph module graph + * @returns {null | false | function(ModuleGraphConnection, RuntimeSpec): ConnectionState} function to determine if the connection is active + */ + getCondition(moduleGraph) { + return null; } - hasContextTimestamps() { - return (this._flags & 0x10) !== 0; + /** + * Returns the exported names + * @param {ModuleGraph} moduleGraph module graph + * @returns {ExportsSpec | undefined} export names + */ + getExports(moduleGraph) { + return undefined; } - setContextTimestamps(value) { - this._flags = this._flags | 0x10; - this.contextTimestamps = value; + /** + * Returns warnings + * @param {ModuleGraph} moduleGraph module graph + * @returns {WebpackError[]} warnings + */ + getWarnings(moduleGraph) { + return null; } - hasContextHashes() { - return (this._flags & 0x20) !== 0; + /** + * Returns errors + * @param {ModuleGraph} moduleGraph module graph + * @returns {WebpackError[]} errors + */ + getErrors(moduleGraph) { + return null; } - setContextHashes(value) { - this._flags = this._flags | 0x20; - this.contextHashes = value; - } + /** + * Update the hash + * @param {Hash} hash hash to be updated + * @param {UpdateHashContext} context context + * @returns {void} + */ + updateHash(hash, context) {} - hasContextTshs() { - return (this._flags & 0x40) !== 0; + /** + * implement this method to allow the occurrence order plugin to count correctly + * @returns {number} count how often the id is used in this dependency + */ + getNumberOfIdOccurrences() { + return 1; } - setContextTshs(value) { - this._flags = this._flags | 0x40; - this.contextTshs = value; + /** + * @param {ModuleGraph} moduleGraph the module graph + * @returns {ConnectionState} how this dependency connects the module to referencing modules + */ + getModuleEvaluationSideEffectsState(moduleGraph) { + return true; } - hasMissingExistence() { - return (this._flags & 0x80) !== 0; + /** + * @param {string} context context directory + * @returns {Module} a module + */ + createIgnoredModule(context) { + return getIgnoredModule(); } - setMissingExistence(value) { - this._flags = this._flags | 0x80; - this.missingExistence = value; + serialize({ write }) { + write(this.weak); + write(this.optional); + write(this._locSL); + write(this._locSC); + write(this._locEL); + write(this._locEC); + write(this._locI); + write(this._locN); } - hasManagedItemInfo() { - return (this._flags & 0x100) !== 0; + deserialize({ read }) { + this.weak = read(); + this.optional = read(); + this._locSL = read(); + this._locSC = read(); + this._locEL = read(); + this._locEC = read(); + this._locI = read(); + this._locN = read(); } +} - setManagedItemInfo(value) { - this._flags = this._flags | 0x100; - this.managedItemInfo = value; - } +/** @type {string[][]} */ +Dependency.NO_EXPORTS_REFERENCED = []; +/** @type {string[][]} */ +Dependency.EXPORTS_OBJECT_REFERENCED = [[]]; - hasManagedFiles() { - return (this._flags & 0x200) !== 0; - } +Object.defineProperty(Dependency.prototype, "module", { + /** + * @deprecated + * @returns {never} throws + */ + get() { + throw new Error( + "module property was removed from Dependency (use compilation.moduleGraph.getModule(dependency) instead)" + ); + }, - setManagedFiles(value) { - this._flags = this._flags | 0x200; - this.managedFiles = value; + /** + * @deprecated + * @returns {never} throws + */ + set() { + throw new Error( + "module property was removed from Dependency (use compilation.moduleGraph.updateModule(dependency, module) instead)" + ); } +}); - hasManagedContexts() { - return (this._flags & 0x400) !== 0; +Object.defineProperty(Dependency.prototype, "disconnect", { + get() { + throw new Error( + "disconnect was removed from Dependency (Dependency no longer carries graph specific information)" + ); } +}); - setManagedContexts(value) { - this._flags = this._flags | 0x400; - this.managedContexts = value; - } +Dependency.TRANSITIVE = TRANSITIVE; - hasManagedMissing() { - return (this._flags & 0x800) !== 0; - } +module.exports = Dependency; - setManagedMissing(value) { - this._flags = this._flags | 0x800; - this.managedMissing = value; - } - hasChildren() { - return (this._flags & 0x1000) !== 0; - } +/***/ }), - setChildren(value) { - this._flags = this._flags | 0x1000; - this.children = value; - } +/***/ 17600: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - addChild(child) { - if (!this.hasChildren()) { - this.setChildren(new Set()); - } - this.children.add(child); - } +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ - serialize({ write }) { - write(this._flags); - if (this.hasStartTime()) write(this.startTime); - if (this.hasFileTimestamps()) write(this.fileTimestamps); - if (this.hasFileHashes()) write(this.fileHashes); - if (this.hasFileTshs()) write(this.fileTshs); - if (this.hasContextTimestamps()) write(this.contextTimestamps); - if (this.hasContextHashes()) write(this.contextHashes); - if (this.hasContextTshs()) write(this.contextTshs); - if (this.hasMissingExistence()) write(this.missingExistence); - if (this.hasManagedItemInfo()) write(this.managedItemInfo); - if (this.hasManagedFiles()) write(this.managedFiles); - if (this.hasManagedContexts()) write(this.managedContexts); - if (this.hasManagedMissing()) write(this.managedMissing); - if (this.hasChildren()) write(this.children); - } - deserialize({ read }) { - this._flags = read(); - if (this.hasStartTime()) this.startTime = read(); - if (this.hasFileTimestamps()) this.fileTimestamps = read(); - if (this.hasFileHashes()) this.fileHashes = read(); - if (this.hasFileTshs()) this.fileTshs = read(); - if (this.hasContextTimestamps()) this.contextTimestamps = read(); - if (this.hasContextHashes()) this.contextHashes = read(); - if (this.hasContextTshs()) this.contextTshs = read(); - if (this.hasMissingExistence()) this.missingExistence = read(); - if (this.hasManagedItemInfo()) this.managedItemInfo = read(); - if (this.hasManagedFiles()) this.managedFiles = read(); - if (this.hasManagedContexts()) this.managedContexts = read(); - if (this.hasManagedMissing()) this.managedMissing = read(); - if (this.hasChildren()) this.children = read(); - } +/** @typedef {import("webpack-sources").ReplaceSource} ReplaceSource */ +/** @typedef {import("./ChunkGraph")} ChunkGraph */ +/** @typedef {import("./ConcatenationScope")} ConcatenationScope */ +/** @typedef {import("./Dependency")} Dependency */ +/** @typedef {import("./Dependency").RuntimeSpec} RuntimeSpec */ +/** @typedef {import("./DependencyTemplates")} DependencyTemplates */ +/** @typedef {import("./Generator").GenerateContext} GenerateContext */ +/** @template T @typedef {import("./InitFragment")} InitFragment */ +/** @typedef {import("./Module")} Module */ +/** @typedef {import("./ModuleGraph")} ModuleGraph */ +/** @typedef {import("./RuntimeTemplate")} RuntimeTemplate */ + +/** + * @typedef {Object} DependencyTemplateContext + * @property {RuntimeTemplate} runtimeTemplate the runtime template + * @property {DependencyTemplates} dependencyTemplates the dependency templates + * @property {ModuleGraph} moduleGraph the module graph + * @property {ChunkGraph} chunkGraph the chunk graph + * @property {Set} runtimeRequirements the requirements for runtime + * @property {Module} module current module + * @property {RuntimeSpec} runtime current runtimes, for which code is generated + * @property {InitFragment[]} initFragments mutable array of init fragments for the current module + * @property {ConcatenationScope=} concatenationScope when in a concatenated module, information about other concatenated modules + */ + +class DependencyTemplate { + /* istanbul ignore next */ /** - * @param {function(Snapshot): (ReadonlyMap | ReadonlySet)[]} getMaps first - * @returns {Iterable} iterable + * @abstract + * @param {Dependency} dependency the dependency for which the template should be applied + * @param {ReplaceSource} source the current replace source which can be modified + * @param {DependencyTemplateContext} templateContext the context object + * @returns {void} */ - _createIterable(getMaps) { - return new SnapshotIterable(this, getMaps); + apply(dependency, source, templateContext) { + const AbstractMethodError = __webpack_require__(570); + throw new AbstractMethodError(); } +} + +module.exports = DependencyTemplate; + + +/***/ }), + +/***/ 31002: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ + + + +const createHash = __webpack_require__(24123); + +/** @typedef {import("./Dependency")} Dependency */ +/** @typedef {import("./DependencyTemplate")} DependencyTemplate */ +/** @typedef {typeof import("./util/Hash")} Hash */ +/** @typedef {new (...args: any[]) => Dependency} DependencyConstructor */ + +class DependencyTemplates { /** - * @returns {Iterable} iterable + * @param {string | Hash} hashFunction the hash function to use */ - getFileIterable() { - return this._createIterable(s => [ - s.fileTimestamps, - s.fileHashes, - s.fileTshs, - s.managedFiles - ]); + constructor(hashFunction = "md4") { + /** @type {Map} */ + this._map = new Map(); + /** @type {string} */ + this._hash = "31d6cfe0d16ae931b73c59d7e0c089c0"; + this._hashFunction = hashFunction; } /** - * @returns {Iterable} iterable + * @param {DependencyConstructor} dependency Constructor of Dependency + * @returns {DependencyTemplate} template for this dependency */ - getContextIterable() { - return this._createIterable(s => [ - s.contextTimestamps, - s.contextHashes, - s.contextTshs, - s.managedContexts - ]); + get(dependency) { + return this._map.get(dependency); } /** - * @returns {Iterable} iterable + * @param {DependencyConstructor} dependency Constructor of Dependency + * @param {DependencyTemplate} dependencyTemplate template for this dependency + * @returns {void} */ - getMissingIterable() { - return this._createIterable(s => [s.missingExistence, s.managedMissing]); + set(dependency, dependencyTemplate) { + this._map.set(dependency, dependencyTemplate); } -} - -makeSerializable(Snapshot, "webpack/lib/FileSystemInfo", "Snapshot"); - -const MIN_COMMON_SNAPSHOT_SIZE = 3; -/** - * @template T - */ -class SnapshotOptimization { /** - * @param {function(Snapshot): boolean} has has value - * @param {function(Snapshot): Map | Set} get get value - * @param {function(Snapshot, Map | Set): void} set set value - * @param {boolean=} useStartTime use the start time of snapshots - * @param {boolean=} isSet value is an Set instead of a Map + * @param {string} part additional hash contributor + * @returns {void} */ - constructor(has, get, set, useStartTime = true, isSet = false) { - this._has = has; - this._get = get; - this._set = set; - this._useStartTime = useStartTime; - this._isSet = isSet; - /** @type {Map} */ - this._map = new Map(); - this._statItemsShared = 0; - this._statItemsUnshared = 0; - this._statSharedSnapshots = 0; - this._statReusedSharedSnapshots = 0; + updateHash(part) { + const hash = createHash(this._hashFunction); + hash.update(`${this._hash}${part}`); + this._hash = /** @type {string} */ (hash.digest("hex")); } - getStatisticMessage() { - const total = this._statItemsShared + this._statItemsUnshared; - if (total === 0) return undefined; - return `${ - this._statItemsShared && Math.round((this._statItemsShared * 100) / total) - }% (${this._statItemsShared}/${total}) entries shared via ${ - this._statSharedSnapshots - } shared snapshots (${ - this._statReusedSharedSnapshots + this._statSharedSnapshots - } times referenced)`; + getHash() { + return this._hash; } - clear() { - this._map.clear(); - this._statItemsShared = 0; - this._statItemsUnshared = 0; - this._statSharedSnapshots = 0; - this._statReusedSharedSnapshots = 0; + clone() { + const newInstance = new DependencyTemplates(); + newInstance._map = new Map(this._map); + newInstance._hash = this._hash; + return newInstance; } +} - /** - * @param {Snapshot} newSnapshot snapshot - * @param {Set} capturedFiles files to snapshot/share - * @returns {void} - */ - optimize(newSnapshot, capturedFiles) { - /** - * @param {SnapshotOptimizationEntry} entry optimization entry - * @returns {void} - */ - const increaseSharedAndStoreOptimizationEntry = entry => { - if (entry.children !== undefined) { - entry.children.forEach(increaseSharedAndStoreOptimizationEntry); - } - entry.shared++; - storeOptimizationEntry(entry); - }; - /** - * @param {SnapshotOptimizationEntry} entry optimization entry - * @returns {void} - */ - const storeOptimizationEntry = entry => { - for (const path of entry.snapshotContent) { - const old = this._map.get(path); - if (old.shared < entry.shared) { - this._map.set(path, entry); - } - capturedFiles.delete(path); - } - }; +module.exports = DependencyTemplates; - /** @type {SnapshotOptimizationEntry} */ - let newOptimizationEntry = undefined; - const capturedFilesSize = capturedFiles.size; +/***/ }), - /** @type {Set | undefined} */ - const optimizationEntries = new Set(); +/***/ 28766: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - for (const path of capturedFiles) { - const optimizationEntry = this._map.get(path); - if (optimizationEntry === undefined) { - if (newOptimizationEntry === undefined) { - newOptimizationEntry = { - snapshot: newSnapshot, - shared: 0, - snapshotContent: undefined, - children: undefined - }; - } - this._map.set(path, newOptimizationEntry); - continue; - } else { - optimizationEntries.add(optimizationEntry); - } - } +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ - optimizationEntries: for (const optimizationEntry of optimizationEntries) { - const snapshot = optimizationEntry.snapshot; - if (optimizationEntry.shared > 0) { - // It's a shared snapshot - // We can't change it, so we can only use it when all files match - // and startTime is compatible - if ( - this._useStartTime && - newSnapshot.startTime && - (!snapshot.startTime || snapshot.startTime > newSnapshot.startTime) - ) { - continue; - } - const nonSharedFiles = new Set(); - const snapshotContent = optimizationEntry.snapshotContent; - const snapshotEntries = this._get(snapshot); - for (const path of snapshotContent) { - if (!capturedFiles.has(path)) { - if (!snapshotEntries.has(path)) { - // File is not shared and can't be removed from the snapshot - // because it's in a child of the snapshot - continue optimizationEntries; - } - nonSharedFiles.add(path); - continue; - } - } - if (nonSharedFiles.size === 0) { - // The complete snapshot is shared - // add it as child - newSnapshot.addChild(snapshot); - increaseSharedAndStoreOptimizationEntry(optimizationEntry); - this._statReusedSharedSnapshots++; - } else { - // Only a part of the snapshot is shared - const sharedCount = snapshotContent.size - nonSharedFiles.size; - if (sharedCount < MIN_COMMON_SNAPSHOT_SIZE) { - // Common part it too small - continue optimizationEntries; - } - // Extract common timestamps from both snapshots - let commonMap; - if (this._isSet) { - commonMap = new Set(); - for (const path of /** @type {Set} */ (snapshotEntries)) { - if (nonSharedFiles.has(path)) continue; - commonMap.add(path); - snapshotEntries.delete(path); - } - } else { - commonMap = new Map(); - const map = /** @type {Map} */ (snapshotEntries); - for (const [path, value] of map) { - if (nonSharedFiles.has(path)) continue; - commonMap.set(path, value); - snapshotEntries.delete(path); - } - } - // Create and attach snapshot - const commonSnapshot = new Snapshot(); - if (this._useStartTime) { - commonSnapshot.setMergedStartTime(newSnapshot.startTime, snapshot); - } - this._set(commonSnapshot, commonMap); - newSnapshot.addChild(commonSnapshot); - snapshot.addChild(commonSnapshot); - // Create optimization entry - const newEntry = { - snapshot: commonSnapshot, - shared: optimizationEntry.shared + 1, - snapshotContent: new Set(commonMap.keys()), - children: undefined - }; - if (optimizationEntry.children === undefined) - optimizationEntry.children = new Set(); - optimizationEntry.children.add(newEntry); - storeOptimizationEntry(newEntry); - this._statSharedSnapshots++; - } - } else { - // It's a unshared snapshot - // We can extract a common shared snapshot - // with all common files - const snapshotEntries = this._get(snapshot); - if (snapshotEntries === undefined) { - // Incomplete snapshot, that can't be used - continue optimizationEntries; - } - let commonMap; - if (this._isSet) { - commonMap = new Set(); - const set = /** @type {Set} */ (snapshotEntries); - if (capturedFiles.size < set.size) { - for (const path of capturedFiles) { - if (set.has(path)) commonMap.add(path); - } - } else { - for (const path of set) { - if (capturedFiles.has(path)) commonMap.add(path); - } - } - } else { - commonMap = new Map(); - const map = /** @type {Map} */ (snapshotEntries); - for (const path of capturedFiles) { - const ts = map.get(path); - if (ts === undefined) continue; - commonMap.set(path, ts); - } - } - if (commonMap.size < MIN_COMMON_SNAPSHOT_SIZE) { - // Common part it too small - continue optimizationEntries; - } - // Create and attach snapshot - const commonSnapshot = new Snapshot(); - if (this._useStartTime) { - commonSnapshot.setMergedStartTime(newSnapshot.startTime, snapshot); - } - this._set(commonSnapshot, commonMap); - newSnapshot.addChild(commonSnapshot); - snapshot.addChild(commonSnapshot); - // Remove files from snapshot - for (const path of commonMap.keys()) snapshotEntries.delete(path); - const sharedCount = commonMap.size; - this._statItemsUnshared -= sharedCount; - this._statItemsShared += sharedCount; - // Create optimization entry - storeOptimizationEntry({ - snapshot: commonSnapshot, - shared: 2, - snapshotContent: new Set(commonMap.keys()), - children: undefined - }); - this._statSharedSnapshots++; + +const DllModuleFactory = __webpack_require__(77885); +const DllEntryDependency = __webpack_require__(57839); +const EntryDependency = __webpack_require__(41075); + +class DllEntryPlugin { + constructor(context, entries, options) { + this.context = context; + this.entries = entries; + this.options = options; + } + + apply(compiler) { + compiler.hooks.compilation.tap( + "DllEntryPlugin", + (compilation, { normalModuleFactory }) => { + const dllModuleFactory = new DllModuleFactory(); + compilation.dependencyFactories.set( + DllEntryDependency, + dllModuleFactory + ); + compilation.dependencyFactories.set( + EntryDependency, + normalModuleFactory + ); } - } - const unshared = capturedFiles.size; - this._statItemsUnshared += unshared; - this._statItemsShared += capturedFilesSize - unshared; + ); + compiler.hooks.make.tapAsync("DllEntryPlugin", (compilation, callback) => { + compilation.addEntry( + this.context, + new DllEntryDependency( + this.entries.map((e, idx) => { + const dep = new EntryDependency(e); + dep.loc = { + name: this.options.name, + index: idx + }; + return dep; + }), + this.options.name + ), + this.options, + callback + ); + }); } } -const parseString = str => { - if (str[0] === "'") str = `"${str.slice(1, -1).replace(/"/g, '\\"')}"`; - return JSON.parse(str); -}; +module.exports = DllEntryPlugin; -/* istanbul ignore next */ -/** - * @param {number} mtime mtime - */ -const applyMtime = mtime => { - if (FS_ACCURACY > 1 && mtime % 2 !== 0) FS_ACCURACY = 1; - else if (FS_ACCURACY > 10 && mtime % 20 !== 0) FS_ACCURACY = 10; - else if (FS_ACCURACY > 100 && mtime % 200 !== 0) FS_ACCURACY = 100; - else if (FS_ACCURACY > 1000 && mtime % 2000 !== 0) FS_ACCURACY = 1000; -}; -/** - * @template T - * @template K - * @param {Map} a source map - * @param {Map} b joining map - * @returns {Map} joined map - */ -const mergeMaps = (a, b) => { - if (!b || b.size === 0) return a; - if (!a || a.size === 0) return b; - const map = new Map(a); - for (const [key, value] of b) { - map.set(key, value); - } - return map; -}; +/***/ }), -/** - * @template T - * @template K - * @param {Set} a source map - * @param {Set} b joining map - * @returns {Set} joined map - */ -const mergeSets = (a, b) => { - if (!b || b.size === 0) return a; - if (!a || a.size === 0) return b; - const map = new Set(a); - for (const item of b) { - map.add(item); - } - return map; -}; +/***/ 52692: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { -/** - * Finding file or directory to manage - * @param {string} managedPath path that is managing by {@link FileSystemInfo} - * @param {string} path path to file or directory - * @returns {string|null} managed item - * @example - * getManagedItem( - * '/Users/user/my-project/node_modules/', - * '/Users/user/my-project/node_modules/package/index.js' - * ) === '/Users/user/my-project/node_modules/package' - * getManagedItem( - * '/Users/user/my-project/node_modules/', - * '/Users/user/my-project/node_modules/package1/node_modules/package2' - * ) === '/Users/user/my-project/node_modules/package1/node_modules/package2' - * getManagedItem( - * '/Users/user/my-project/node_modules/', - * '/Users/user/my-project/node_modules/.bin/script.js' - * ) === null // hidden files are disallowed as managed items - * getManagedItem( - * '/Users/user/my-project/node_modules/', - * '/Users/user/my-project/node_modules/package' - * ) === '/Users/user/my-project/node_modules/package' - */ -const getManagedItem = (managedPath, path) => { - let i = managedPath.length; - let slashes = 1; - let startingPosition = true; - loop: while (i < path.length) { - switch (path.charCodeAt(i)) { - case 47: // slash - case 92: // backslash - if (--slashes === 0) break loop; - startingPosition = true; - break; - case 46: // . - // hidden files are disallowed as managed items - // it's probably .yarn-integrity or .cache - if (startingPosition) return null; - break; - case 64: // @ - if (!startingPosition) return null; - slashes++; - break; - default: - startingPosition = false; - break; - } - i++; - } - if (i === path.length) slashes--; - // return null when path is incomplete - if (slashes !== 0) return null; - // if (path.slice(i + 1, i + 13) === "node_modules") - if ( - path.length >= i + 13 && - path.charCodeAt(i + 1) === 110 && - path.charCodeAt(i + 2) === 111 && - path.charCodeAt(i + 3) === 100 && - path.charCodeAt(i + 4) === 101 && - path.charCodeAt(i + 5) === 95 && - path.charCodeAt(i + 6) === 109 && - path.charCodeAt(i + 7) === 111 && - path.charCodeAt(i + 8) === 100 && - path.charCodeAt(i + 9) === 117 && - path.charCodeAt(i + 10) === 108 && - path.charCodeAt(i + 11) === 101 && - path.charCodeAt(i + 12) === 115 - ) { - // if this is the end of the path - if (path.length === i + 13) { - // return the node_modules directory - // it's special - return path; - } - const c = path.charCodeAt(i + 13); - // if next symbol is slash or backslash - if (c === 47 || c === 92) { - // Managed subpath - return getManagedItem(path.slice(0, i + 14), path); - } - } - return path.slice(0, i); -}; - -/** - * @template {ContextFileSystemInfoEntry | ContextTimestampAndHash} T - * @param {T} entry entry - * @returns {T["resolved"] | undefined} the resolved entry - */ -const getResolvedTimestamp = entry => { - if (entry === null) return null; - if (entry.resolved !== undefined) return entry.resolved; - return entry.symlinks === undefined ? entry : undefined; -}; - -/** - * @param {ContextHash} entry entry - * @returns {string | undefined} the resolved entry - */ -const getResolvedHash = entry => { - if (entry === null) return null; - if (entry.resolved !== undefined) return entry.resolved; - return entry.symlinks === undefined ? entry.hash : undefined; -}; - -const addAll = (source, target) => { - for (const key of source) target.add(key); -}; +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ -/** - * Used to access information about the filesystem in a cached way - */ -class FileSystemInfo { - /** - * @param {InputFileSystem} fs file system - * @param {Object} options options - * @param {Iterable=} options.managedPaths paths that are only managed by a package manager - * @param {Iterable=} options.immutablePaths paths that are immutable - * @param {Logger=} options.logger logger used to log invalid snapshots - * @param {string | Hash=} options.hashFunction the hash function to use - */ - constructor( - fs, - { - managedPaths = [], - immutablePaths = [], - logger, - hashFunction = "md4" - } = {} - ) { - this.fs = fs; - this.logger = logger; - this._remainingLogs = logger ? 40 : 0; - this._loggedPaths = logger ? new Set() : undefined; - this._hashFunction = hashFunction; - /** @type {WeakMap} */ - this._snapshotCache = new WeakMap(); - this._fileTimestampsOptimization = new SnapshotOptimization( - s => s.hasFileTimestamps(), - s => s.fileTimestamps, - (s, v) => s.setFileTimestamps(v) - ); - this._fileHashesOptimization = new SnapshotOptimization( - s => s.hasFileHashes(), - s => s.fileHashes, - (s, v) => s.setFileHashes(v), - false - ); - this._fileTshsOptimization = new SnapshotOptimization( - s => s.hasFileTshs(), - s => s.fileTshs, - (s, v) => s.setFileTshs(v) - ); - this._contextTimestampsOptimization = new SnapshotOptimization( - s => s.hasContextTimestamps(), - s => s.contextTimestamps, - (s, v) => s.setContextTimestamps(v) - ); - this._contextHashesOptimization = new SnapshotOptimization( - s => s.hasContextHashes(), - s => s.contextHashes, - (s, v) => s.setContextHashes(v), - false - ); - this._contextTshsOptimization = new SnapshotOptimization( - s => s.hasContextTshs(), - s => s.contextTshs, - (s, v) => s.setContextTshs(v) - ); - this._missingExistenceOptimization = new SnapshotOptimization( - s => s.hasMissingExistence(), - s => s.missingExistence, - (s, v) => s.setMissingExistence(v), - false - ); - this._managedItemInfoOptimization = new SnapshotOptimization( - s => s.hasManagedItemInfo(), - s => s.managedItemInfo, - (s, v) => s.setManagedItemInfo(v), - false - ); - this._managedFilesOptimization = new SnapshotOptimization( - s => s.hasManagedFiles(), - s => s.managedFiles, - (s, v) => s.setManagedFiles(v), - false, - true - ); - this._managedContextsOptimization = new SnapshotOptimization( - s => s.hasManagedContexts(), - s => s.managedContexts, - (s, v) => s.setManagedContexts(v), - false, - true - ); - this._managedMissingOptimization = new SnapshotOptimization( - s => s.hasManagedMissing(), - s => s.managedMissing, - (s, v) => s.setManagedMissing(v), - false, - true - ); - /** @type {StackedCacheMap} */ - this._fileTimestamps = new StackedCacheMap(); - /** @type {Map} */ - this._fileHashes = new Map(); - /** @type {Map} */ - this._fileTshs = new Map(); - /** @type {StackedCacheMap} */ - this._contextTimestamps = new StackedCacheMap(); - /** @type {Map} */ - this._contextHashes = new Map(); - /** @type {Map} */ - this._contextTshs = new Map(); - /** @type {Map} */ - this._managedItems = new Map(); - /** @type {AsyncQueue} */ - this.fileTimestampQueue = new AsyncQueue({ - name: "file timestamp", - parallelism: 30, - processor: this._readFileTimestamp.bind(this) - }); - /** @type {AsyncQueue} */ - this.fileHashQueue = new AsyncQueue({ - name: "file hash", - parallelism: 10, - processor: this._readFileHash.bind(this) - }); - /** @type {AsyncQueue} */ - this.contextTimestampQueue = new AsyncQueue({ - name: "context timestamp", - parallelism: 2, - processor: this._readContextTimestamp.bind(this) - }); - /** @type {AsyncQueue} */ - this.contextHashQueue = new AsyncQueue({ - name: "context hash", - parallelism: 2, - processor: this._readContextHash.bind(this) - }); - /** @type {AsyncQueue} */ - this.contextTshQueue = new AsyncQueue({ - name: "context hash and timestamp", - parallelism: 2, - processor: this._readContextTimestampAndHash.bind(this) - }); - /** @type {AsyncQueue} */ - this.managedItemQueue = new AsyncQueue({ - name: "managed item info", - parallelism: 10, - processor: this._getManagedItemInfo.bind(this) - }); - /** @type {AsyncQueue>} */ - this.managedItemDirectoryQueue = new AsyncQueue({ - name: "managed item directory info", - parallelism: 10, - processor: this._getManagedItemDirectoryInfo.bind(this) - }); - this.managedPaths = Array.from(managedPaths); - this.managedPathsWithSlash = /** @type {string[]} */ ( - this.managedPaths.filter(p => typeof p === "string") - ).map(p => join(fs, p, "_").slice(0, -1)); - this.managedPathsRegExps = /** @type {RegExp[]} */ ( - this.managedPaths.filter(p => typeof p !== "string") - ); - this.immutablePaths = Array.from(immutablePaths); - this.immutablePathsWithSlash = /** @type {string[]} */ ( - this.immutablePaths.filter(p => typeof p === "string") - ).map(p => join(fs, p, "_").slice(0, -1)); - this.immutablePathsRegExps = /** @type {RegExp[]} */ ( - this.immutablePaths.filter(p => typeof p !== "string") - ); - this._cachedDeprecatedFileTimestamps = undefined; - this._cachedDeprecatedContextTimestamps = undefined; +const { RawSource } = __webpack_require__(96192); +const Module = __webpack_require__(85887); +const RuntimeGlobals = __webpack_require__(49404); +const makeSerializable = __webpack_require__(26522); - this._warnAboutExperimentalEsmTracking = false; +/** @typedef {import("webpack-sources").Source} Source */ +/** @typedef {import("../declarations/WebpackOptions").WebpackOptionsNormalized} WebpackOptions */ +/** @typedef {import("./ChunkGraph")} ChunkGraph */ +/** @typedef {import("./Compilation")} Compilation */ +/** @typedef {import("./Dependency").UpdateHashContext} UpdateHashContext */ +/** @typedef {import("./DependencyTemplates")} DependencyTemplates */ +/** @typedef {import("./Module").CodeGenerationContext} CodeGenerationContext */ +/** @typedef {import("./Module").CodeGenerationResult} CodeGenerationResult */ +/** @typedef {import("./Module").NeedBuildContext} NeedBuildContext */ +/** @typedef {import("./Module").SourceContext} SourceContext */ +/** @typedef {import("./RequestShortener")} RequestShortener */ +/** @typedef {import("./ResolverFactory").ResolverWithOptions} ResolverWithOptions */ +/** @typedef {import("./RuntimeTemplate")} RuntimeTemplate */ +/** @typedef {import("./WebpackError")} WebpackError */ +/** @typedef {import("./util/Hash")} Hash */ +/** @typedef {import("./util/fs").InputFileSystem} InputFileSystem */ - this._statCreatedSnapshots = 0; - this._statTestedSnapshotsCached = 0; - this._statTestedSnapshotsNotCached = 0; - this._statTestedChildrenCached = 0; - this._statTestedChildrenNotCached = 0; - this._statTestedEntries = 0; - } +const TYPES = new Set(["javascript"]); +const RUNTIME_REQUIREMENTS = new Set([ + RuntimeGlobals.require, + RuntimeGlobals.module +]); - logStatistics() { - const logWhenMessage = (header, message) => { - if (message) { - this.logger.log(`${header}: ${message}`); - } - }; - this.logger.log(`${this._statCreatedSnapshots} new snapshots created`); - this.logger.log( - `${ - this._statTestedSnapshotsNotCached && - Math.round( - (this._statTestedSnapshotsNotCached * 100) / - (this._statTestedSnapshotsCached + - this._statTestedSnapshotsNotCached) - ) - }% root snapshot uncached (${this._statTestedSnapshotsNotCached} / ${ - this._statTestedSnapshotsCached + this._statTestedSnapshotsNotCached - })` - ); - this.logger.log( - `${ - this._statTestedChildrenNotCached && - Math.round( - (this._statTestedChildrenNotCached * 100) / - (this._statTestedChildrenCached + this._statTestedChildrenNotCached) - ) - }% children snapshot uncached (${this._statTestedChildrenNotCached} / ${ - this._statTestedChildrenCached + this._statTestedChildrenNotCached - })` - ); - this.logger.log(`${this._statTestedEntries} entries tested`); - this.logger.log( - `File info in cache: ${this._fileTimestamps.size} timestamps ${this._fileHashes.size} hashes ${this._fileTshs.size} timestamp hash combinations` - ); - logWhenMessage( - `File timestamp snapshot optimization`, - this._fileTimestampsOptimization.getStatisticMessage() - ); - logWhenMessage( - `File hash snapshot optimization`, - this._fileHashesOptimization.getStatisticMessage() - ); - logWhenMessage( - `File timestamp hash combination snapshot optimization`, - this._fileTshsOptimization.getStatisticMessage() - ); - this.logger.log( - `Directory info in cache: ${this._contextTimestamps.size} timestamps ${this._contextHashes.size} hashes ${this._contextTshs.size} timestamp hash combinations` - ); - logWhenMessage( - `Directory timestamp snapshot optimization`, - this._contextTimestampsOptimization.getStatisticMessage() - ); - logWhenMessage( - `Directory hash snapshot optimization`, - this._contextHashesOptimization.getStatisticMessage() - ); - logWhenMessage( - `Directory timestamp hash combination snapshot optimization`, - this._contextTshsOptimization.getStatisticMessage() - ); - logWhenMessage( - `Missing items snapshot optimization`, - this._missingExistenceOptimization.getStatisticMessage() - ); - this.logger.log( - `Managed items info in cache: ${this._managedItems.size} items` - ); - logWhenMessage( - `Managed items snapshot optimization`, - this._managedItemInfoOptimization.getStatisticMessage() - ); - logWhenMessage( - `Managed files snapshot optimization`, - this._managedFilesOptimization.getStatisticMessage() - ); - logWhenMessage( - `Managed contexts snapshot optimization`, - this._managedContextsOptimization.getStatisticMessage() - ); - logWhenMessage( - `Managed missing snapshot optimization`, - this._managedMissingOptimization.getStatisticMessage() - ); - } +class DllModule extends Module { + constructor(context, dependencies, name) { + super("javascript/dynamic", context); - _log(path, reason, ...args) { - const key = path + reason; - if (this._loggedPaths.has(key)) return; - this._loggedPaths.add(key); - this.logger.debug(`${path} invalidated because ${reason}`, ...args); - if (--this._remainingLogs === 0) { - this.logger.debug( - "Logging limit has been reached and no further logging will be emitted by FileSystemInfo" - ); - } + // Info from Factory + this.dependencies = dependencies; + this.name = name; } - clear() { - this._remainingLogs = this.logger ? 40 : 0; - if (this._loggedPaths !== undefined) this._loggedPaths.clear(); - - this._snapshotCache = new WeakMap(); - this._fileTimestampsOptimization.clear(); - this._fileHashesOptimization.clear(); - this._fileTshsOptimization.clear(); - this._contextTimestampsOptimization.clear(); - this._contextHashesOptimization.clear(); - this._contextTshsOptimization.clear(); - this._missingExistenceOptimization.clear(); - this._managedItemInfoOptimization.clear(); - this._managedFilesOptimization.clear(); - this._managedContextsOptimization.clear(); - this._managedMissingOptimization.clear(); - this._fileTimestamps.clear(); - this._fileHashes.clear(); - this._fileTshs.clear(); - this._contextTimestamps.clear(); - this._contextHashes.clear(); - this._contextTshs.clear(); - this._managedItems.clear(); - this._managedItems.clear(); - - this._cachedDeprecatedFileTimestamps = undefined; - this._cachedDeprecatedContextTimestamps = undefined; - - this._statCreatedSnapshots = 0; - this._statTestedSnapshotsCached = 0; - this._statTestedSnapshotsNotCached = 0; - this._statTestedChildrenCached = 0; - this._statTestedChildrenNotCached = 0; - this._statTestedEntries = 0; + /** + * @returns {Set} types available (do not mutate) + */ + getSourceTypes() { + return TYPES; } /** - * @param {ReadonlyMap} map timestamps - * @param {boolean=} immutable if 'map' is immutable and FileSystemInfo can keep referencing it - * @returns {void} + * @returns {string} a unique identifier of the module */ - addFileTimestamps(map, immutable) { - this._fileTimestamps.addAll(map, immutable); - this._cachedDeprecatedFileTimestamps = undefined; + identifier() { + return `dll ${this.name}`; } /** - * @param {ReadonlyMap} map timestamps - * @param {boolean=} immutable if 'map' is immutable and FileSystemInfo can keep referencing it - * @returns {void} + * @param {RequestShortener} requestShortener the request shortener + * @returns {string} a user readable identifier of the module */ - addContextTimestamps(map, immutable) { - this._contextTimestamps.addAll(map, immutable); - this._cachedDeprecatedContextTimestamps = undefined; + readableIdentifier(requestShortener) { + return `dll ${this.name}`; } /** - * @param {string} path file path - * @param {function(WebpackError=, (FileSystemInfoEntry | "ignore" | null)=): void} callback callback function + * @param {WebpackOptions} options webpack options + * @param {Compilation} compilation the compilation + * @param {ResolverWithOptions} resolver the resolver + * @param {InputFileSystem} fs the file system + * @param {function(WebpackError=): void} callback callback function * @returns {void} */ - getFileTimestamp(path, callback) { - const cache = this._fileTimestamps.get(path); - if (cache !== undefined) return callback(null, cache); - this.fileTimestampQueue.add(path, callback); + build(options, compilation, resolver, fs, callback) { + this.buildMeta = {}; + this.buildInfo = {}; + return callback(); } /** - * @param {string} path context path - * @param {function(WebpackError=, (ResolvedContextFileSystemInfoEntry | "ignore" | null)=): void} callback callback function - * @returns {void} + * @param {CodeGenerationContext} context context for code generation + * @returns {CodeGenerationResult} result */ - getContextTimestamp(path, callback) { - const cache = this._contextTimestamps.get(path); - if (cache !== undefined) { - if (cache === "ignore") return callback(null, "ignore"); - const resolved = getResolvedTimestamp(cache); - if (resolved !== undefined) return callback(null, resolved); - return this._resolveContextTimestamp(cache, callback); - } - this.contextTimestampQueue.add(path, (err, entry) => { - if (err) return callback(err); - const resolved = getResolvedTimestamp(entry); - if (resolved !== undefined) return callback(null, resolved); - this._resolveContextTimestamp(entry, callback); - }); + codeGeneration(context) { + const sources = new Map(); + sources.set( + "javascript", + new RawSource("module.exports = __webpack_require__;") + ); + return { + sources, + runtimeRequirements: RUNTIME_REQUIREMENTS + }; } /** - * @param {string} path context path - * @param {function(WebpackError=, (ContextFileSystemInfoEntry | "ignore" | null)=): void} callback callback function + * @param {NeedBuildContext} context context info + * @param {function(WebpackError=, boolean=): void} callback callback function, returns true, if the module needs a rebuild * @returns {void} */ - _getUnresolvedContextTimestamp(path, callback) { - const cache = this._contextTimestamps.get(path); - if (cache !== undefined) return callback(null, cache); - this.contextTimestampQueue.add(path, callback); + needBuild(context, callback) { + return callback(null, !this.buildMeta); } /** - * @param {string} path file path - * @param {function(WebpackError=, string=): void} callback callback function - * @returns {void} + * @param {string=} type the source type for which the size should be estimated + * @returns {number} the estimated size of the module (must be non-zero) */ - getFileHash(path, callback) { - const cache = this._fileHashes.get(path); - if (cache !== undefined) return callback(null, cache); - this.fileHashQueue.add(path, callback); + size(type) { + return 12; } /** - * @param {string} path context path - * @param {function(WebpackError=, string=): void} callback callback function + * @param {Hash} hash the hash used to track dependencies + * @param {UpdateHashContext} context context * @returns {void} */ - getContextHash(path, callback) { - const cache = this._contextHashes.get(path); - if (cache !== undefined) { - const resolved = getResolvedHash(cache); - if (resolved !== undefined) return callback(null, resolved); - return this._resolveContextHash(cache, callback); - } - this.contextHashQueue.add(path, (err, entry) => { - if (err) return callback(err); - const resolved = getResolvedHash(entry); - if (resolved !== undefined) return callback(null, resolved); - this._resolveContextHash(entry, callback); - }); + updateHash(hash, context) { + hash.update(`dll module${this.name || ""}`); + super.updateHash(hash, context); + } + + serialize(context) { + context.write(this.name); + super.serialize(context); + } + + deserialize(context) { + this.name = context.read(); + super.deserialize(context); } /** - * @param {string} path context path - * @param {function(WebpackError=, ContextHash=): void} callback callback function + * Assuming this module is in the cache. Update the (cached) module with + * the fresh module from the factory. Usually updates internal references + * and properties. + * @param {Module} module fresh module * @returns {void} */ - _getUnresolvedContextHash(path, callback) { - const cache = this._contextHashes.get(path); - if (cache !== undefined) return callback(null, cache); - this.contextHashQueue.add(path, callback); + updateCacheModule(module) { + super.updateCacheModule(module); + this.dependencies = module.dependencies; } /** - * @param {string} path context path - * @param {function(WebpackError=, ResolvedContextTimestampAndHash=): void} callback callback function + * Assuming this module is in the cache. Remove internal references to allow freeing some memory. + */ + cleanupForCache() { + super.cleanupForCache(); + this.dependencies = undefined; + } +} + +makeSerializable(DllModule, "webpack/lib/DllModule"); + +module.exports = DllModule; + + +/***/ }), + +/***/ 77885: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ + + + +const DllModule = __webpack_require__(52692); +const ModuleFactory = __webpack_require__(61574); + +/** @typedef {import("./ModuleFactory").ModuleFactoryCreateData} ModuleFactoryCreateData */ +/** @typedef {import("./ModuleFactory").ModuleFactoryResult} ModuleFactoryResult */ +/** @typedef {import("./dependencies/DllEntryDependency")} DllEntryDependency */ + +class DllModuleFactory extends ModuleFactory { + constructor() { + super(); + this.hooks = Object.freeze({}); + } + /** + * @param {ModuleFactoryCreateData} data data object + * @param {function(Error=, ModuleFactoryResult=): void} callback callback * @returns {void} */ - getContextTsh(path, callback) { - const cache = this._contextTshs.get(path); - if (cache !== undefined) { - const resolved = getResolvedTimestamp(cache); - if (resolved !== undefined) return callback(null, resolved); - return this._resolveContextTsh(cache, callback); - } - this.contextTshQueue.add(path, (err, entry) => { - if (err) return callback(err); - const resolved = getResolvedTimestamp(entry); - if (resolved !== undefined) return callback(null, resolved); - this._resolveContextTsh(entry, callback); + create(data, callback) { + const dependency = /** @type {DllEntryDependency} */ (data.dependencies[0]); + callback(null, { + module: new DllModule( + data.context, + dependency.dependencies, + dependency.name + ) }); } +} + +module.exports = DllModuleFactory; + + +/***/ }), + +/***/ 15232: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ + + + +const DllEntryPlugin = __webpack_require__(28766); +const FlagAllModulesAsUsedPlugin = __webpack_require__(85310); +const LibManifestPlugin = __webpack_require__(30711); +const createSchemaValidation = __webpack_require__(77695); + +/** @typedef {import("../declarations/plugins/DllPlugin").DllPluginOptions} DllPluginOptions */ +/** @typedef {import("./Compiler")} Compiler */ + +const validate = createSchemaValidation( + __webpack_require__(9145), + () => __webpack_require__(7754), + { + name: "Dll Plugin", + baseDataPath: "options" + } +); +class DllPlugin { /** - * @param {string} path context path - * @param {function(WebpackError=, ContextTimestampAndHash=): void} callback callback function - * @returns {void} + * @param {DllPluginOptions} options options object */ - _getUnresolvedContextTsh(path, callback) { - const cache = this._contextTshs.get(path); - if (cache !== undefined) return callback(null, cache); - this.contextTshQueue.add(path, callback); + constructor(options) { + validate(options); + this.options = { + ...options, + entryOnly: options.entryOnly !== false + }; } - _createBuildDependenciesResolvers() { - const resolveContext = createResolver({ - resolveToContext: true, - exportsFields: [], - fileSystem: this.fs - }); - const resolveCjs = createResolver({ - extensions: [".js", ".json", ".node"], - conditionNames: ["require", "node"], - exportsFields: ["exports"], - fileSystem: this.fs - }); - const resolveCjsAsChild = createResolver({ - extensions: [".js", ".json", ".node"], - conditionNames: ["require", "node"], - exportsFields: [], - fileSystem: this.fs - }); - const resolveEsm = createResolver({ - extensions: [".js", ".json", ".node"], - fullySpecified: true, - conditionNames: ["import", "node"], - exportsFields: ["exports"], - fileSystem: this.fs + /** + * Apply the plugin + * @param {Compiler} compiler the compiler instance + * @returns {void} + */ + apply(compiler) { + compiler.hooks.entryOption.tap("DllPlugin", (context, entry) => { + if (typeof entry !== "function") { + for (const name of Object.keys(entry)) { + const options = { + name, + filename: entry.filename + }; + new DllEntryPlugin(context, entry[name].import, options).apply( + compiler + ); + } + } else { + throw new Error( + "DllPlugin doesn't support dynamic entry (function) yet" + ); + } + return true; }); - return { resolveContext, resolveEsm, resolveCjs, resolveCjsAsChild }; + new LibManifestPlugin(this.options).apply(compiler); + if (!this.options.entryOnly) { + new FlagAllModulesAsUsedPlugin("DllPlugin").apply(compiler); + } + } +} + +module.exports = DllPlugin; + + +/***/ }), + +/***/ 8904: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ + + + +const parseJson = __webpack_require__(48335); +const DelegatedModuleFactoryPlugin = __webpack_require__(50756); +const ExternalModuleFactoryPlugin = __webpack_require__(19364); +const WebpackError = __webpack_require__(68422); +const DelegatedSourceDependency = __webpack_require__(82766); +const createSchemaValidation = __webpack_require__(77695); +const makePathsRelative = __webpack_require__(96236).makePathsRelative; + +/** @typedef {import("../declarations/WebpackOptions").Externals} Externals */ +/** @typedef {import("../declarations/plugins/DllReferencePlugin").DllReferencePluginOptions} DllReferencePluginOptions */ +/** @typedef {import("../declarations/plugins/DllReferencePlugin").DllReferencePluginOptionsManifest} DllReferencePluginOptionsManifest */ + +const validate = createSchemaValidation( + __webpack_require__(15909), + () => __webpack_require__(15766), + { + name: "Dll Reference Plugin", + baseDataPath: "options" } +); +class DllReferencePlugin { /** - * @param {string} context context directory - * @param {Iterable} deps dependencies - * @param {function(Error=, ResolveBuildDependenciesResult=): void} callback callback function - * @returns {void} + * @param {DllReferencePluginOptions} options options object */ - resolveBuildDependencies(context, deps, callback) { - const { resolveContext, resolveEsm, resolveCjs, resolveCjsAsChild } = - this._createBuildDependenciesResolvers(); + constructor(options) { + validate(options); + this.options = options; + /** @type {WeakMap} */ + this._compilationData = new WeakMap(); + } - /** @type {Set} */ - const files = new Set(); - /** @type {Set} */ - const fileSymlinks = new Set(); - /** @type {Set} */ - const directories = new Set(); - /** @type {Set} */ - const directorySymlinks = new Set(); - /** @type {Set} */ - const missing = new Set(); - /** @type {Set} */ - const resolveFiles = new Set(); - /** @type {Set} */ - const resolveDirectories = new Set(); - /** @type {Set} */ - const resolveMissing = new Set(); - /** @type {Map} */ - const resolveResults = new Map(); - const invalidResolveResults = new Set(); - const resolverContext = { - fileDependencies: resolveFiles, - contextDependencies: resolveDirectories, - missingDependencies: resolveMissing - }; - const expectedToString = expected => { - return expected ? ` (expected ${expected})` : ""; - }; - const jobToString = job => { - switch (job.type) { - case RBDT_RESOLVE_CJS: - return `resolve commonjs ${job.path}${expectedToString( - job.expected - )}`; - case RBDT_RESOLVE_ESM: - return `resolve esm ${job.path}${expectedToString(job.expected)}`; - case RBDT_RESOLVE_DIRECTORY: - return `resolve directory ${job.path}`; - case RBDT_RESOLVE_CJS_FILE: - return `resolve commonjs file ${job.path}${expectedToString( - job.expected - )}`; - case RBDT_RESOLVE_ESM_FILE: - return `resolve esm file ${job.path}${expectedToString( - job.expected - )}`; - case RBDT_DIRECTORY: - return `directory ${job.path}`; - case RBDT_FILE: - return `file ${job.path}`; - case RBDT_DIRECTORY_DEPENDENCIES: - return `directory dependencies ${job.path}`; - case RBDT_FILE_DEPENDENCIES: - return `file dependencies ${job.path}`; - } - return `unknown ${job.type} ${job.path}`; - }; - const pathToString = job => { - let result = ` at ${jobToString(job)}`; - job = job.issuer; - while (job !== undefined) { - result += `\n at ${jobToString(job)}`; - job = job.issuer; + apply(compiler) { + compiler.hooks.compilation.tap( + "DllReferencePlugin", + (compilation, { normalModuleFactory }) => { + compilation.dependencyFactories.set( + DelegatedSourceDependency, + normalModuleFactory + ); } - return result; - }; - processAsyncTree( - Array.from(deps, dep => ({ - type: RBDT_RESOLVE_CJS, - context, - path: dep, - expected: undefined, - issuer: undefined - })), - 20, - (job, push, callback) => { - const { type, context, path, expected } = job; - const resolveDirectory = path => { - const key = `d\n${context}\n${path}`; - if (resolveResults.has(key)) { - return callback(); - } - resolveResults.set(key, undefined); - resolveContext(context, path, resolverContext, (err, _, result) => { - if (err) { - if (expected === false) { - resolveResults.set(key, false); - return callback(); - } - invalidResolveResults.add(key); - err.message += `\nwhile resolving '${path}' in ${context} to a directory`; - return callback(err); - } - const resultPath = result.path; - resolveResults.set(key, resultPath); - push({ - type: RBDT_DIRECTORY, - context: undefined, - path: resultPath, - expected: undefined, - issuer: job - }); - callback(); - }); - }; - const resolveFile = (path, symbol, resolve) => { - const key = `${symbol}\n${context}\n${path}`; - if (resolveResults.has(key)) { - return callback(); - } - resolveResults.set(key, undefined); - resolve(context, path, resolverContext, (err, _, result) => { - if (typeof expected === "string") { - if (!err && result && result.path === expected) { - resolveResults.set(key, result.path); - } else { - invalidResolveResults.add(key); - this.logger.warn( - `Resolving '${path}' in ${context} for build dependencies doesn't lead to expected result '${expected}', but to '${ - err || (result && result.path) - }' instead. Resolving dependencies are ignored for this path.\n${pathToString( - job - )}` + ); + + compiler.hooks.beforeCompile.tapAsync( + "DllReferencePlugin", + (params, callback) => { + if ("manifest" in this.options) { + const manifest = this.options.manifest; + if (typeof manifest === "string") { + compiler.inputFileSystem.readFile(manifest, (err, result) => { + if (err) return callback(err); + const data = { + path: manifest, + data: undefined, + error: undefined + }; + // Catch errors parsing the manifest so that blank + // or malformed manifest files don't kill the process. + try { + data.data = parseJson(result.toString("utf-8")); + } catch (e) { + // Store the error in the params so that it can + // be added as a compilation error later on. + const manifestPath = makePathsRelative( + compiler.options.context, + manifest, + compiler.root ); + data.error = new DllManifestError(manifestPath, e.message); } - } else { - if (err) { - if (expected === false) { - resolveResults.set(key, false); - return callback(); - } - invalidResolveResults.add(key); - err.message += `\nwhile resolving '${path}' in ${context} as file\n${pathToString( - job - )}`; - return callback(err); - } - const resultPath = result.path; - resolveResults.set(key, resultPath); - push({ - type: RBDT_FILE, - context: undefined, - path: resultPath, - expected: undefined, - issuer: job - }); - } - callback(); - }); - }; - switch (type) { - case RBDT_RESOLVE_CJS: { - const isDirectory = /[\\/]$/.test(path); - if (isDirectory) { - resolveDirectory(path.slice(0, path.length - 1)); - } else { - resolveFile(path, "f", resolveCjs); - } - break; - } - case RBDT_RESOLVE_ESM: { - const isDirectory = /[\\/]$/.test(path); - if (isDirectory) { - resolveDirectory(path.slice(0, path.length - 1)); - } else { - resolveFile(path); - } - break; - } - case RBDT_RESOLVE_DIRECTORY: { - resolveDirectory(path); - break; - } - case RBDT_RESOLVE_CJS_FILE: { - resolveFile(path, "f", resolveCjs); - break; - } - case RBDT_RESOLVE_CJS_FILE_AS_CHILD: { - resolveFile(path, "c", resolveCjsAsChild); - break; + this._compilationData.set(params, data); + return callback(); + }); + return; } - case RBDT_RESOLVE_ESM_FILE: { - resolveFile(path, "e", resolveEsm); - break; + } + return callback(); + } + ); + + compiler.hooks.compile.tap("DllReferencePlugin", params => { + let name = this.options.name; + let sourceType = this.options.sourceType; + let content = + "content" in this.options ? this.options.content : undefined; + if ("manifest" in this.options) { + let manifestParameter = this.options.manifest; + let manifest; + if (typeof manifestParameter === "string") { + const data = this._compilationData.get(params); + // If there was an error parsing the manifest + // file, exit now because the error will be added + // as a compilation error in the "compilation" hook. + if (data.error) { + return; } - case RBDT_FILE: { - if (files.has(path)) { - callback(); - break; - } - files.add(path); - this.fs.realpath(path, (err, _realPath) => { - if (err) return callback(err); - const realPath = /** @type {string} */ (_realPath); - if (realPath !== path) { - fileSymlinks.add(path); - resolveFiles.add(path); - if (files.has(realPath)) return callback(); - files.add(realPath); - } - push({ - type: RBDT_FILE_DEPENDENCIES, - context: undefined, - path: realPath, - expected: undefined, - issuer: job - }); - callback(); - }); - break; - } - case RBDT_DIRECTORY: { - if (directories.has(path)) { - callback(); - break; - } - directories.add(path); - this.fs.realpath(path, (err, _realPath) => { - if (err) return callback(err); - const realPath = /** @type {string} */ (_realPath); - if (realPath !== path) { - directorySymlinks.add(path); - resolveFiles.add(path); - if (directories.has(realPath)) return callback(); - directories.add(realPath); - } - push({ - type: RBDT_DIRECTORY_DEPENDENCIES, - context: undefined, - path: realPath, - expected: undefined, - issuer: job - }); - callback(); - }); - break; - } - case RBDT_FILE_DEPENDENCIES: { - // Check for known files without dependencies - if (/\.json5?$|\.yarn-integrity$|yarn\.lock$|\.ya?ml/.test(path)) { - process.nextTick(callback); - break; - } - // Check commonjs cache for the module - /** @type {NodeModule} */ - const module = require.cache[path]; - if (module && Array.isArray(module.children)) { - children: for (const child of module.children) { - let childPath = child.filename; - if (childPath) { - push({ - type: RBDT_FILE, - context: undefined, - path: childPath, - expected: undefined, - issuer: job - }); - const context = dirname(this.fs, path); - for (const modulePath of module.paths) { - if (childPath.startsWith(modulePath)) { - let subPath = childPath.slice(modulePath.length + 1); - const packageMatch = /^(@[^\\/]+[\\/])[^\\/]+/.exec( - subPath - ); - if (packageMatch) { - push({ - type: RBDT_FILE, - context: undefined, - path: - modulePath + - childPath[modulePath.length] + - packageMatch[0] + - childPath[modulePath.length] + - "package.json", - expected: false, - issuer: job - }); - } - let request = subPath.replace(/\\/g, "/"); - if (request.endsWith(".js")) - request = request.slice(0, -3); - push({ - type: RBDT_RESOLVE_CJS_FILE_AS_CHILD, - context, - path: request, - expected: child.filename, - issuer: job - }); - continue children; - } - } - let request = relative(this.fs, context, childPath); - if (request.endsWith(".js")) request = request.slice(0, -3); - request = request.replace(/\\/g, "/"); - if (!request.startsWith("../")) request = `./${request}`; - push({ - type: RBDT_RESOLVE_CJS_FILE, - context, - path: request, - expected: child.filename, - issuer: job - }); - } - } - } else if (supportsEsm && /\.m?js$/.test(path)) { - if (!this._warnAboutExperimentalEsmTracking) { - this.logger.log( - "Node.js doesn't offer a (nice) way to introspect the ESM dependency graph yet.\n" + - "Until a full solution is available webpack uses an experimental ESM tracking based on parsing.\n" + - "As best effort webpack parses the ESM files to guess dependencies. But this can lead to expensive and incorrect tracking." - ); - this._warnAboutExperimentalEsmTracking = true; - } - const lexer = __webpack_require__(79366); - lexer.init.then(() => { - this.fs.readFile(path, (err, content) => { - if (err) return callback(err); - try { - const context = dirname(this.fs, path); - const source = content.toString(); - const [imports] = lexer.parse(source); - for (const imp of imports) { - try { - let dependency; - if (imp.d === -1) { - // import ... from "..." - dependency = parseString( - source.substring(imp.s - 1, imp.e + 1) - ); - } else if (imp.d > -1) { - // import() - let expr = source.substring(imp.s, imp.e).trim(); - dependency = parseString(expr); - } else { - // e.g. import.meta - continue; - } - push({ - type: RBDT_RESOLVE_ESM_FILE, - context, - path: dependency, - expected: undefined, - issuer: job - }); - } catch (e) { - this.logger.warn( - `Parsing of ${path} for build dependencies failed at 'import(${source.substring( - imp.s, - imp.e - )})'.\n` + - "Build dependencies behind this expression are ignored and might cause incorrect cache invalidation." - ); - this.logger.debug(pathToString(job)); - this.logger.debug(e.stack); - } - } - } catch (e) { - this.logger.warn( - `Parsing of ${path} for build dependencies failed and all dependencies of this file are ignored, which might cause incorrect cache invalidation..` - ); - this.logger.debug(pathToString(job)); - this.logger.debug(e.stack); - } - process.nextTick(callback); - }); - }, callback); - break; - } else { - this.logger.log( - `Assuming ${path} has no dependencies as we were unable to assign it to any module system.` - ); - this.logger.debug(pathToString(job)); + manifest = data.data; + } else { + manifest = manifestParameter; + } + if (manifest) { + if (!name) name = manifest.name; + if (!sourceType) sourceType = manifest.type; + if (!content) content = manifest.content; + } + } + /** @type {Externals} */ + const externals = {}; + const source = "dll-reference " + name; + externals[source] = name; + const normalModuleFactory = params.normalModuleFactory; + new ExternalModuleFactoryPlugin(sourceType || "var", externals).apply( + normalModuleFactory + ); + new DelegatedModuleFactoryPlugin({ + source: source, + type: this.options.type, + scope: this.options.scope, + context: this.options.context || compiler.options.context, + content, + extensions: this.options.extensions, + associatedObjectForCache: compiler.root + }).apply(normalModuleFactory); + }); + + compiler.hooks.compilation.tap( + "DllReferencePlugin", + (compilation, params) => { + if ("manifest" in this.options) { + let manifest = this.options.manifest; + if (typeof manifest === "string") { + const data = this._compilationData.get(params); + // If there was an error parsing the manifest file, add the + // error as a compilation error to make the compilation fail. + if (data.error) { + compilation.errors.push(data.error); } - process.nextTick(callback); - break; - } - case RBDT_DIRECTORY_DEPENDENCIES: { - const match = - /(^.+[\\/]node_modules[\\/](?:@[^\\/]+[\\/])?[^\\/]+)/.exec(path); - const packagePath = match ? match[1] : path; - const packageJson = join(this.fs, packagePath, "package.json"); - this.fs.readFile(packageJson, (err, content) => { - if (err) { - if (err.code === "ENOENT") { - resolveMissing.add(packageJson); - const parent = dirname(this.fs, packagePath); - if (parent !== packagePath) { - push({ - type: RBDT_DIRECTORY_DEPENDENCIES, - context: undefined, - path: parent, - expected: undefined, - issuer: job - }); - } - callback(); - return; - } - return callback(err); - } - resolveFiles.add(packageJson); - let packageData; - try { - packageData = JSON.parse(content.toString("utf-8")); - } catch (e) { - return callback(e); - } - const depsObject = packageData.dependencies; - const optionalDepsObject = packageData.optionalDependencies; - const allDeps = new Set(); - const optionalDeps = new Set(); - if (typeof depsObject === "object" && depsObject) { - for (const dep of Object.keys(depsObject)) { - allDeps.add(dep); - } - } - if ( - typeof optionalDepsObject === "object" && - optionalDepsObject - ) { - for (const dep of Object.keys(optionalDepsObject)) { - allDeps.add(dep); - optionalDeps.add(dep); - } - } - for (const dep of allDeps) { - push({ - type: RBDT_RESOLVE_DIRECTORY, - context: packagePath, - path: dep, - expected: !optionalDeps.has(dep), - issuer: job - }); - } - callback(); - }); - break; + compilation.fileDependencies.add(manifest); } } - }, - err => { - if (err) return callback(err); - for (const l of fileSymlinks) files.delete(l); - for (const l of directorySymlinks) directories.delete(l); - for (const k of invalidResolveResults) resolveResults.delete(k); - callback(null, { - files, - directories, - missing, - resolveResults, - resolveDependencies: { - files: resolveFiles, - directories: resolveDirectories, - missing: resolveMissing - } - }); } ); } +} + +class DllManifestError extends WebpackError { + constructor(filename, message) { + super(); + + this.name = "DllManifestError"; + this.message = `Dll manifest ${filename}\n${message}`; + } +} + +module.exports = DllReferencePlugin; + + +/***/ }), + +/***/ 60670: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Naoyuki Kanezawa @nkzawa +*/ + + + +const EntryOptionPlugin = __webpack_require__(59526); +const EntryPlugin = __webpack_require__(82430); +const EntryDependency = __webpack_require__(41075); +/** @typedef {import("../declarations/WebpackOptions").EntryDynamicNormalized} EntryDynamic */ +/** @typedef {import("../declarations/WebpackOptions").EntryItem} EntryItem */ +/** @typedef {import("../declarations/WebpackOptions").EntryStaticNormalized} EntryStatic */ +/** @typedef {import("./Compiler")} Compiler */ + +class DynamicEntryPlugin { /** - * @param {Map} resolveResults results from resolving - * @param {function(Error=, boolean=): void} callback callback with true when resolveResults resolve the same way - * @returns {void} + * @param {string} context the context path + * @param {EntryDynamic} entry the entry value */ - checkResolveResultsValid(resolveResults, callback) { - const { resolveCjs, resolveCjsAsChild, resolveEsm, resolveContext } = - this._createBuildDependenciesResolvers(); - asyncLib.eachLimit( - resolveResults, - 20, - ([key, expectedResult], callback) => { - const [type, context, path] = key.split("\n"); - switch (type) { - case "d": - resolveContext(context, path, {}, (err, _, result) => { - if (expectedResult === false) - return callback(err ? undefined : INVALID); - if (err) return callback(err); - const resultPath = result.path; - if (resultPath !== expectedResult) return callback(INVALID); - callback(); - }); - break; - case "f": - resolveCjs(context, path, {}, (err, _, result) => { - if (expectedResult === false) - return callback(err ? undefined : INVALID); - if (err) return callback(err); - const resultPath = result.path; - if (resultPath !== expectedResult) return callback(INVALID); - callback(); - }); - break; - case "c": - resolveCjsAsChild(context, path, {}, (err, _, result) => { - if (expectedResult === false) - return callback(err ? undefined : INVALID); - if (err) return callback(err); - const resultPath = result.path; - if (resultPath !== expectedResult) return callback(INVALID); - callback(); - }); - break; - case "e": - resolveEsm(context, path, {}, (err, _, result) => { - if (expectedResult === false) - return callback(err ? undefined : INVALID); - if (err) return callback(err); - const resultPath = result.path; - if (resultPath !== expectedResult) return callback(INVALID); - callback(); - }); - break; - default: - callback(new Error("Unexpected type in resolve result key")); - break; - } - }, - /** - * @param {Error | typeof INVALID=} err error or invalid flag - * @returns {void} - */ - err => { - if (err === INVALID) { - return callback(null, false); - } - if (err) { - return callback(err); - } - return callback(null, true); - } - ); + constructor(context, entry) { + this.context = context; + this.entry = entry; } /** - * - * @param {number} startTime when processing the files has started - * @param {Iterable} files all files - * @param {Iterable} directories all directories - * @param {Iterable} missing all missing files or directories - * @param {Object} options options object (for future extensions) - * @param {boolean=} options.hash should use hash to snapshot - * @param {boolean=} options.timestamp should use timestamp to snapshot - * @param {function(WebpackError=, Snapshot=): void} callback callback function + * Apply the plugin + * @param {Compiler} compiler the compiler instance * @returns {void} */ - createSnapshot(startTime, files, directories, missing, options, callback) { - /** @type {Map} */ - const fileTimestamps = new Map(); - /** @type {Map} */ - const fileHashes = new Map(); - /** @type {Map} */ - const fileTshs = new Map(); - /** @type {Map} */ - const contextTimestamps = new Map(); - /** @type {Map} */ - const contextHashes = new Map(); - /** @type {Map} */ - const contextTshs = new Map(); - /** @type {Map} */ - const missingExistence = new Map(); - /** @type {Map} */ - const managedItemInfo = new Map(); - /** @type {Set} */ - const managedFiles = new Set(); - /** @type {Set} */ - const managedContexts = new Set(); - /** @type {Set} */ - const managedMissing = new Set(); - /** @type {Set} */ - const children = new Set(); + apply(compiler) { + compiler.hooks.compilation.tap( + "DynamicEntryPlugin", + (compilation, { normalModuleFactory }) => { + compilation.dependencyFactories.set( + EntryDependency, + normalModuleFactory + ); + } + ); - const snapshot = new Snapshot(); - if (startTime) snapshot.setStartTime(startTime); + compiler.hooks.make.tapPromise( + "DynamicEntryPlugin", + (compilation, callback) => + Promise.resolve(this.entry()) + .then(entry => { + const promises = []; + for (const name of Object.keys(entry)) { + const desc = entry[name]; + const options = EntryOptionPlugin.entryDescriptionToOptions( + compiler, + name, + desc + ); + for (const entry of desc.import) { + promises.push( + new Promise((resolve, reject) => { + compilation.addEntry( + this.context, + EntryPlugin.createDependency(entry, options), + options, + err => { + if (err) return reject(err); + resolve(); + } + ); + }) + ); + } + } + return Promise.all(promises); + }) + .then(x => {}) + ); + } +} - /** @type {Set} */ - const managedItems = new Set(); +module.exports = DynamicEntryPlugin; - /** 1 = timestamp, 2 = hash, 3 = timestamp + hash */ - const mode = options && options.hash ? (options.timestamp ? 3 : 2) : 1; - let jobs = 1; - const jobDone = () => { - if (--jobs === 0) { - if (fileTimestamps.size !== 0) { - snapshot.setFileTimestamps(fileTimestamps); - } - if (fileHashes.size !== 0) { - snapshot.setFileHashes(fileHashes); - } - if (fileTshs.size !== 0) { - snapshot.setFileTshs(fileTshs); - } - if (contextTimestamps.size !== 0) { - snapshot.setContextTimestamps(contextTimestamps); - } - if (contextHashes.size !== 0) { - snapshot.setContextHashes(contextHashes); - } - if (contextTshs.size !== 0) { - snapshot.setContextTshs(contextTshs); - } - if (missingExistence.size !== 0) { - snapshot.setMissingExistence(missingExistence); - } - if (managedItemInfo.size !== 0) { - snapshot.setManagedItemInfo(managedItemInfo); - } - this._managedFilesOptimization.optimize(snapshot, managedFiles); - if (managedFiles.size !== 0) { - snapshot.setManagedFiles(managedFiles); - } - this._managedContextsOptimization.optimize(snapshot, managedContexts); - if (managedContexts.size !== 0) { - snapshot.setManagedContexts(managedContexts); - } - this._managedMissingOptimization.optimize(snapshot, managedMissing); - if (managedMissing.size !== 0) { - snapshot.setManagedMissing(managedMissing); - } - if (children.size !== 0) { - snapshot.setChildren(children); - } - this._snapshotCache.set(snapshot, true); - this._statCreatedSnapshots++; +/***/ }), - callback(null, snapshot); - } - }; - const jobError = () => { - if (jobs > 0) { - // large negative number instead of NaN or something else to keep jobs to stay a SMI (v8) - jobs = -100000000; - callback(null, null); - } - }; - const checkManaged = (path, managedSet) => { - for (const immutablePath of this.immutablePathsRegExps) { - if (immutablePath.test(path)) { - managedSet.add(path); - return true; - } - } - for (const immutablePath of this.immutablePathsWithSlash) { - if (path.startsWith(immutablePath)) { - managedSet.add(path); - return true; - } - } - for (const managedPath of this.managedPathsRegExps) { - const match = managedPath.exec(path); - if (match) { - const managedItem = getManagedItem(match[1], path); - if (managedItem) { - managedItems.add(managedItem); - managedSet.add(path); - return true; - } - } - } - for (const managedPath of this.managedPathsWithSlash) { - if (path.startsWith(managedPath)) { - const managedItem = getManagedItem(managedPath, path); - if (managedItem) { - managedItems.add(managedItem); - managedSet.add(path); - return true; - } - } - } - return false; - }; - const captureNonManaged = (items, managedSet) => { - const capturedItems = new Set(); - for (const path of items) { - if (!checkManaged(path, managedSet)) capturedItems.add(path); - } - return capturedItems; - }; - const processCapturedFiles = capturedFiles => { - switch (mode) { - case 3: - this._fileTshsOptimization.optimize(snapshot, capturedFiles); - for (const path of capturedFiles) { - const cache = this._fileTshs.get(path); - if (cache !== undefined) { - fileTshs.set(path, cache); - } else { - jobs++; - this._getFileTimestampAndHash(path, (err, entry) => { - if (err) { - if (this.logger) { - this.logger.debug( - `Error snapshotting file timestamp hash combination of ${path}: ${err.stack}` - ); - } - jobError(); - } else { - fileTshs.set(path, entry); - jobDone(); - } - }); - } - } - break; - case 2: - this._fileHashesOptimization.optimize(snapshot, capturedFiles); - for (const path of capturedFiles) { - const cache = this._fileHashes.get(path); - if (cache !== undefined) { - fileHashes.set(path, cache); - } else { - jobs++; - this.fileHashQueue.add(path, (err, entry) => { - if (err) { - if (this.logger) { - this.logger.debug( - `Error snapshotting file hash of ${path}: ${err.stack}` - ); - } - jobError(); - } else { - fileHashes.set(path, entry); - jobDone(); - } - }); - } - } - break; - case 1: - this._fileTimestampsOptimization.optimize(snapshot, capturedFiles); - for (const path of capturedFiles) { - const cache = this._fileTimestamps.get(path); - if (cache !== undefined) { - if (cache !== "ignore") { - fileTimestamps.set(path, cache); - } - } else { - jobs++; - this.fileTimestampQueue.add(path, (err, entry) => { - if (err) { - if (this.logger) { - this.logger.debug( - `Error snapshotting file timestamp of ${path}: ${err.stack}` - ); - } - jobError(); - } else { - fileTimestamps.set(path, entry); - jobDone(); - } - }); - } - } - break; - } - }; - if (files) { - processCapturedFiles(captureNonManaged(files, managedFiles)); - } - const processCapturedDirectories = capturedDirectories => { - switch (mode) { - case 3: - this._contextTshsOptimization.optimize(snapshot, capturedDirectories); - for (const path of capturedDirectories) { - const cache = this._contextTshs.get(path); - /** @type {ResolvedContextTimestampAndHash} */ - let resolved; - if ( - cache !== undefined && - (resolved = getResolvedTimestamp(cache)) !== undefined - ) { - contextTshs.set(path, resolved); - } else { - jobs++; - /** - * @param {Error=} err error - * @param {ResolvedContextTimestampAndHash=} entry entry - * @returns {void} - */ - const callback = (err, entry) => { - if (err) { - if (this.logger) { - this.logger.debug( - `Error snapshotting context timestamp hash combination of ${path}: ${err.stack}` - ); - } - jobError(); - } else { - contextTshs.set(path, entry); - jobDone(); - } - }; - if (cache !== undefined) { - this._resolveContextTsh(cache, callback); - } else { - this.getContextTsh(path, callback); - } - } - } - break; - case 2: - this._contextHashesOptimization.optimize( - snapshot, - capturedDirectories - ); - for (const path of capturedDirectories) { - const cache = this._contextHashes.get(path); - let resolved; - if ( - cache !== undefined && - (resolved = getResolvedHash(cache)) !== undefined - ) { - contextHashes.set(path, resolved); - } else { - jobs++; - const callback = (err, entry) => { - if (err) { - if (this.logger) { - this.logger.debug( - `Error snapshotting context hash of ${path}: ${err.stack}` - ); - } - jobError(); - } else { - contextHashes.set(path, entry); - jobDone(); - } - }; - if (cache !== undefined) { - this._resolveContextHash(cache, callback); - } else { - this.getContextHash(path, callback); - } - } - } - break; - case 1: - this._contextTimestampsOptimization.optimize( - snapshot, - capturedDirectories - ); - for (const path of capturedDirectories) { - const cache = this._contextTimestamps.get(path); - if (cache === "ignore") continue; - let resolved; - if ( - cache !== undefined && - (resolved = getResolvedTimestamp(cache)) !== undefined - ) { - contextTimestamps.set(path, resolved); - } else { - jobs++; - /** - * @param {Error=} err error - * @param {ResolvedContextFileSystemInfoEntry=} entry entry - * @returns {void} - */ - const callback = (err, entry) => { - if (err) { - if (this.logger) { - this.logger.debug( - `Error snapshotting context timestamp of ${path}: ${err.stack}` - ); - } - jobError(); - } else { - contextTimestamps.set(path, entry); - jobDone(); - } - }; - if (cache !== undefined) { - this._resolveContextTimestamp(cache, callback); - } else { - this.getContextTimestamp(path, callback); - } - } - } - break; - } - }; - if (directories) { - processCapturedDirectories( - captureNonManaged(directories, managedContexts) - ); - } - const processCapturedMissing = capturedMissing => { - this._missingExistenceOptimization.optimize(snapshot, capturedMissing); - for (const path of capturedMissing) { - const cache = this._fileTimestamps.get(path); - if (cache !== undefined) { - if (cache !== "ignore") { - missingExistence.set(path, Boolean(cache)); - } - } else { - jobs++; - this.fileTimestampQueue.add(path, (err, entry) => { - if (err) { - if (this.logger) { - this.logger.debug( - `Error snapshotting missing timestamp of ${path}: ${err.stack}` - ); - } - jobError(); - } else { - missingExistence.set(path, Boolean(entry)); - jobDone(); - } - }); - } - } - }; - if (missing) { - processCapturedMissing(captureNonManaged(missing, managedMissing)); - } - this._managedItemInfoOptimization.optimize(snapshot, managedItems); - for (const path of managedItems) { - const cache = this._managedItems.get(path); - if (cache !== undefined) { - if (cache !== "missing") { - managedFiles.add(join(this.fs, path, "package.json")); - } - managedItemInfo.set(path, cache); - } else { - jobs++; - this.managedItemQueue.add(path, (err, entry) => { - if (err) { - if (this.logger) { - this.logger.debug( - `Error snapshotting managed item ${path}: ${err.stack}` - ); - } - jobError(); - } else if (entry) { - if (entry !== "missing") { - managedFiles.add(join(this.fs, path, "package.json")); - } - managedItemInfo.set(path, entry); - jobDone(); - } else { - // Fallback to normal snapshotting - const process = (set, fn) => { - if (set.size === 0) return; - const captured = new Set(); - for (const file of set) { - if (file.startsWith(path)) captured.add(file); - } - if (captured.size > 0) fn(captured); - }; - process(managedFiles, processCapturedFiles); - process(managedContexts, processCapturedDirectories); - process(managedMissing, processCapturedMissing); - jobDone(); - } - }); - } - } - jobDone(); - } +/***/ 59526: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ + + + +/** @typedef {import("../declarations/WebpackOptions").EntryDescriptionNormalized} EntryDescription */ +/** @typedef {import("../declarations/WebpackOptions").EntryNormalized} Entry */ +/** @typedef {import("./Compiler")} Compiler */ +/** @typedef {import("./Entrypoint").EntryOptions} EntryOptions */ +class EntryOptionPlugin { /** - * @param {Snapshot} snapshot1 a snapshot - * @param {Snapshot} snapshot2 a snapshot - * @returns {Snapshot} merged snapshot + * @param {Compiler} compiler the compiler instance one is tapping into + * @returns {void} */ - mergeSnapshots(snapshot1, snapshot2) { - const snapshot = new Snapshot(); - if (snapshot1.hasStartTime() && snapshot2.hasStartTime()) - snapshot.setStartTime(Math.min(snapshot1.startTime, snapshot2.startTime)); - else if (snapshot2.hasStartTime()) snapshot.startTime = snapshot2.startTime; - else if (snapshot1.hasStartTime()) snapshot.startTime = snapshot1.startTime; - if (snapshot1.hasFileTimestamps() || snapshot2.hasFileTimestamps()) { - snapshot.setFileTimestamps( - mergeMaps(snapshot1.fileTimestamps, snapshot2.fileTimestamps) - ); - } - if (snapshot1.hasFileHashes() || snapshot2.hasFileHashes()) { - snapshot.setFileHashes( - mergeMaps(snapshot1.fileHashes, snapshot2.fileHashes) - ); - } - if (snapshot1.hasFileTshs() || snapshot2.hasFileTshs()) { - snapshot.setFileTshs(mergeMaps(snapshot1.fileTshs, snapshot2.fileTshs)); - } - if (snapshot1.hasContextTimestamps() || snapshot2.hasContextTimestamps()) { - snapshot.setContextTimestamps( - mergeMaps(snapshot1.contextTimestamps, snapshot2.contextTimestamps) - ); - } - if (snapshot1.hasContextHashes() || snapshot2.hasContextHashes()) { - snapshot.setContextHashes( - mergeMaps(snapshot1.contextHashes, snapshot2.contextHashes) - ); - } - if (snapshot1.hasContextTshs() || snapshot2.hasContextTshs()) { - snapshot.setContextTshs( - mergeMaps(snapshot1.contextTshs, snapshot2.contextTshs) - ); - } - if (snapshot1.hasMissingExistence() || snapshot2.hasMissingExistence()) { - snapshot.setMissingExistence( - mergeMaps(snapshot1.missingExistence, snapshot2.missingExistence) - ); - } - if (snapshot1.hasManagedItemInfo() || snapshot2.hasManagedItemInfo()) { - snapshot.setManagedItemInfo( - mergeMaps(snapshot1.managedItemInfo, snapshot2.managedItemInfo) - ); - } - if (snapshot1.hasManagedFiles() || snapshot2.hasManagedFiles()) { - snapshot.setManagedFiles( - mergeSets(snapshot1.managedFiles, snapshot2.managedFiles) - ); - } - if (snapshot1.hasManagedContexts() || snapshot2.hasManagedContexts()) { - snapshot.setManagedContexts( - mergeSets(snapshot1.managedContexts, snapshot2.managedContexts) - ); - } - if (snapshot1.hasManagedMissing() || snapshot2.hasManagedMissing()) { - snapshot.setManagedMissing( - mergeSets(snapshot1.managedMissing, snapshot2.managedMissing) - ); - } - if (snapshot1.hasChildren() || snapshot2.hasChildren()) { - snapshot.setChildren(mergeSets(snapshot1.children, snapshot2.children)); - } - if ( - this._snapshotCache.get(snapshot1) === true && - this._snapshotCache.get(snapshot2) === true - ) { - this._snapshotCache.set(snapshot, true); - } - return snapshot; + apply(compiler) { + compiler.hooks.entryOption.tap("EntryOptionPlugin", (context, entry) => { + EntryOptionPlugin.applyEntryOption(compiler, context, entry); + return true; + }); } /** - * @param {Snapshot} snapshot the snapshot made - * @param {function(WebpackError=, boolean=): void} callback callback function + * @param {Compiler} compiler the compiler + * @param {string} context context directory + * @param {Entry} entry request * @returns {void} */ - checkSnapshotValid(snapshot, callback) { - const cachedResult = this._snapshotCache.get(snapshot); - if (cachedResult !== undefined) { - this._statTestedSnapshotsCached++; - if (typeof cachedResult === "boolean") { - callback(null, cachedResult); - } else { - cachedResult.push(callback); + static applyEntryOption(compiler, context, entry) { + if (typeof entry === "function") { + const DynamicEntryPlugin = __webpack_require__(60670); + new DynamicEntryPlugin(context, entry).apply(compiler); + } else { + const EntryPlugin = __webpack_require__(82430); + for (const name of Object.keys(entry)) { + const desc = entry[name]; + const options = EntryOptionPlugin.entryDescriptionToOptions( + compiler, + name, + desc + ); + for (const entry of desc.import) { + new EntryPlugin(context, entry, options).apply(compiler); + } } - return; } - this._statTestedSnapshotsNotCached++; - this._checkSnapshotValidNoCache(snapshot, callback); } /** - * @param {Snapshot} snapshot the snapshot made - * @param {function(WebpackError=, boolean=): void} callback callback function - * @returns {void} + * @param {Compiler} compiler the compiler + * @param {string} name entry name + * @param {EntryDescription} desc entry description + * @returns {EntryOptions} options for the entry */ - _checkSnapshotValidNoCache(snapshot, callback) { - /** @type {number | undefined} */ - let startTime = undefined; - if (snapshot.hasStartTime()) { - startTime = snapshot.startTime; - } - let jobs = 1; - const jobDone = () => { - if (--jobs === 0) { - this._snapshotCache.set(snapshot, true); - callback(null, true); - } - }; - const invalid = () => { - if (jobs > 0) { - // large negative number instead of NaN or something else to keep jobs to stay a SMI (v8) - jobs = -100000000; - this._snapshotCache.set(snapshot, false); - callback(null, false); - } - }; - const invalidWithError = (path, err) => { - if (this._remainingLogs > 0) { - this._log(path, `error occurred: %s`, err); - } - invalid(); - }; - /** - * @param {string} path file path - * @param {string} current current hash - * @param {string} snap snapshot hash - * @returns {boolean} true, if ok - */ - const checkHash = (path, current, snap) => { - if (current !== snap) { - // If hash differ it's invalid - if (this._remainingLogs > 0) { - this._log(path, `hashes differ (%s != %s)`, current, snap); - } - return false; - } - return true; - }; - /** - * @param {string} path file path - * @param {boolean} current current entry - * @param {boolean} snap entry from snapshot - * @returns {boolean} true, if ok - */ - const checkExistence = (path, current, snap) => { - if (!current !== !snap) { - // If existence of item differs - // it's invalid - if (this._remainingLogs > 0) { - this._log( - path, - current ? "it didn't exist before" : "it does no longer exist" - ); - } - return false; - } - return true; - }; - /** - * @param {string} path file path - * @param {FileSystemInfoEntry} current current entry - * @param {FileSystemInfoEntry} snap entry from snapshot - * @param {boolean} log log reason - * @returns {boolean} true, if ok - */ - const checkFile = (path, current, snap, log = true) => { - if (current === snap) return true; - if (!checkExistence(path, Boolean(current), Boolean(snap))) return false; - if (current) { - // For existing items only - if (typeof startTime === "number" && current.safeTime > startTime) { - // If a change happened after starting reading the item - // this may no longer be valid - if (log && this._remainingLogs > 0) { - this._log( - path, - `it may have changed (%d) after the start time of the snapshot (%d)`, - current.safeTime, - startTime - ); - } - return false; - } - if ( - snap.timestamp !== undefined && - current.timestamp !== snap.timestamp - ) { - // If we have a timestamp (it was a file or symlink) and it differs from current timestamp - // it's invalid - if (log && this._remainingLogs > 0) { - this._log( - path, - `timestamps differ (%d != %d)`, - current.timestamp, - snap.timestamp - ); - } - return false; - } - } - return true; - }; - /** - * @param {string} path file path - * @param {ResolvedContextFileSystemInfoEntry} current current entry - * @param {ResolvedContextFileSystemInfoEntry} snap entry from snapshot - * @param {boolean} log log reason - * @returns {boolean} true, if ok - */ - const checkContext = (path, current, snap, log = true) => { - if (current === snap) return true; - if (!checkExistence(path, Boolean(current), Boolean(snap))) return false; - if (current) { - // For existing items only - if (typeof startTime === "number" && current.safeTime > startTime) { - // If a change happened after starting reading the item - // this may no longer be valid - if (log && this._remainingLogs > 0) { - this._log( - path, - `it may have changed (%d) after the start time of the snapshot (%d)`, - current.safeTime, - startTime - ); - } - return false; - } - if ( - snap.timestampHash !== undefined && - current.timestampHash !== snap.timestampHash - ) { - // If we have a timestampHash (it was a directory) and it differs from current timestampHash - // it's invalid - if (log && this._remainingLogs > 0) { - this._log( - path, - `timestamps hashes differ (%s != %s)`, - current.timestampHash, - snap.timestampHash - ); - } - return false; - } - } - return true; - }; - if (snapshot.hasChildren()) { - const childCallback = (err, result) => { - if (err || !result) return invalid(); - else jobDone(); - }; - for (const child of snapshot.children) { - const cache = this._snapshotCache.get(child); - if (cache !== undefined) { - this._statTestedChildrenCached++; - /* istanbul ignore else */ - if (typeof cache === "boolean") { - if (cache === false) { - invalid(); - return; - } - } else { - jobs++; - cache.push(childCallback); - } - } else { - this._statTestedChildrenNotCached++; - jobs++; - this._checkSnapshotValidNoCache(child, childCallback); - } - } - } - if (snapshot.hasFileTimestamps()) { - const { fileTimestamps } = snapshot; - this._statTestedEntries += fileTimestamps.size; - for (const [path, ts] of fileTimestamps) { - const cache = this._fileTimestamps.get(path); - if (cache !== undefined) { - if (cache !== "ignore" && !checkFile(path, cache, ts)) { - invalid(); - return; - } - } else { - jobs++; - this.fileTimestampQueue.add(path, (err, entry) => { - if (err) return invalidWithError(path, err); - if (!checkFile(path, entry, ts)) { - invalid(); - } else { - jobDone(); - } - }); - } - } - } - const processFileHashSnapshot = (path, hash) => { - const cache = this._fileHashes.get(path); - if (cache !== undefined) { - if (cache !== "ignore" && !checkHash(path, cache, hash)) { - invalid(); - return; - } - } else { - jobs++; - this.fileHashQueue.add(path, (err, entry) => { - if (err) return invalidWithError(path, err); - if (!checkHash(path, entry, hash)) { - invalid(); - } else { - jobDone(); - } - }); - } - }; - if (snapshot.hasFileHashes()) { - const { fileHashes } = snapshot; - this._statTestedEntries += fileHashes.size; - for (const [path, hash] of fileHashes) { - processFileHashSnapshot(path, hash); - } - } - if (snapshot.hasFileTshs()) { - const { fileTshs } = snapshot; - this._statTestedEntries += fileTshs.size; - for (const [path, tsh] of fileTshs) { - if (typeof tsh === "string") { - processFileHashSnapshot(path, tsh); - } else { - const cache = this._fileTimestamps.get(path); - if (cache !== undefined) { - if (cache === "ignore" || !checkFile(path, cache, tsh, false)) { - processFileHashSnapshot(path, tsh && tsh.hash); - } - } else { - jobs++; - this.fileTimestampQueue.add(path, (err, entry) => { - if (err) return invalidWithError(path, err); - if (!checkFile(path, entry, tsh, false)) { - processFileHashSnapshot(path, tsh && tsh.hash); - } - jobDone(); - }); - } - } - } - } - if (snapshot.hasContextTimestamps()) { - const { contextTimestamps } = snapshot; - this._statTestedEntries += contextTimestamps.size; - for (const [path, ts] of contextTimestamps) { - const cache = this._contextTimestamps.get(path); - if (cache === "ignore") continue; - let resolved; - if ( - cache !== undefined && - (resolved = getResolvedTimestamp(cache)) !== undefined - ) { - if (!checkContext(path, resolved, ts)) { - invalid(); - return; - } - } else { - jobs++; - /** - * @param {Error=} err error - * @param {ResolvedContextFileSystemInfoEntry=} entry entry - * @returns {void} - */ - const callback = (err, entry) => { - if (err) return invalidWithError(path, err); - if (!checkContext(path, entry, ts)) { - invalid(); - } else { - jobDone(); - } - }; - if (cache !== undefined) { - this._resolveContextTimestamp(cache, callback); - } else { - this.getContextTimestamp(path, callback); - } - } - } - } - const processContextHashSnapshot = (path, hash) => { - const cache = this._contextHashes.get(path); - let resolved; - if ( - cache !== undefined && - (resolved = getResolvedHash(cache)) !== undefined - ) { - if (!checkHash(path, resolved, hash)) { - invalid(); - return; - } - } else { - jobs++; - const callback = (err, entry) => { - if (err) return invalidWithError(path, err); - if (!checkHash(path, entry, hash)) { - invalid(); - } else { - jobDone(); - } - }; - if (cache !== undefined) { - this._resolveContextHash(cache, callback); - } else { - this.getContextHash(path, callback); - } - } + static entryDescriptionToOptions(compiler, name, desc) { + /** @type {EntryOptions} */ + const options = { + name, + filename: desc.filename, + runtime: desc.runtime, + layer: desc.layer, + dependOn: desc.dependOn, + publicPath: desc.publicPath, + chunkLoading: desc.chunkLoading, + asyncChunks: desc.asyncChunks, + wasmLoading: desc.wasmLoading, + library: desc.library }; - if (snapshot.hasContextHashes()) { - const { contextHashes } = snapshot; - this._statTestedEntries += contextHashes.size; - for (const [path, hash] of contextHashes) { - processContextHashSnapshot(path, hash); - } - } - if (snapshot.hasContextTshs()) { - const { contextTshs } = snapshot; - this._statTestedEntries += contextTshs.size; - for (const [path, tsh] of contextTshs) { - if (typeof tsh === "string") { - processContextHashSnapshot(path, tsh); - } else { - const cache = this._contextTimestamps.get(path); - if (cache === "ignore") continue; - let resolved; - if ( - cache !== undefined && - (resolved = getResolvedTimestamp(cache)) !== undefined - ) { - if (!checkContext(path, resolved, tsh, false)) { - processContextHashSnapshot(path, tsh && tsh.hash); - } - } else { - jobs++; - /** - * @param {Error=} err error - * @param {ResolvedContextFileSystemInfoEntry=} entry entry - * @returns {void} - */ - const callback = (err, entry) => { - if (err) return invalidWithError(path, err); - if (!checkContext(path, entry, tsh, false)) { - processContextHashSnapshot(path, tsh && tsh.hash); - } - jobDone(); - }; - if (cache !== undefined) { - this._resolveContextTimestamp(cache, callback); - } else { - this.getContextTimestamp(path, callback); - } - } - } - } + if (desc.layer !== undefined && !compiler.options.experiments.layers) { + throw new Error( + "'entryOptions.layer' is only allowed when 'experiments.layers' is enabled" + ); } - if (snapshot.hasMissingExistence()) { - const { missingExistence } = snapshot; - this._statTestedEntries += missingExistence.size; - for (const [path, existence] of missingExistence) { - const cache = this._fileTimestamps.get(path); - if (cache !== undefined) { - if ( - cache !== "ignore" && - !checkExistence(path, Boolean(cache), Boolean(existence)) - ) { - invalid(); - return; - } - } else { - jobs++; - this.fileTimestampQueue.add(path, (err, entry) => { - if (err) return invalidWithError(path, err); - if (!checkExistence(path, Boolean(entry), Boolean(existence))) { - invalid(); - } else { - jobDone(); - } - }); - } - } + if (desc.chunkLoading) { + const EnableChunkLoadingPlugin = __webpack_require__(34726); + EnableChunkLoadingPlugin.checkEnabled(compiler, desc.chunkLoading); } - if (snapshot.hasManagedItemInfo()) { - const { managedItemInfo } = snapshot; - this._statTestedEntries += managedItemInfo.size; - for (const [path, info] of managedItemInfo) { - const cache = this._managedItems.get(path); - if (cache !== undefined) { - if (!checkHash(path, cache, info)) { - invalid(); - return; - } - } else { - jobs++; - this.managedItemQueue.add(path, (err, entry) => { - if (err) return invalidWithError(path, err); - if (!checkHash(path, entry, info)) { - invalid(); - } else { - jobDone(); - } - }); - } - } + if (desc.wasmLoading) { + const EnableWasmLoadingPlugin = __webpack_require__(93943); + EnableWasmLoadingPlugin.checkEnabled(compiler, desc.wasmLoading); } - jobDone(); - - // if there was an async action - // try to join multiple concurrent request for this snapshot - if (jobs > 0) { - const callbacks = [callback]; - callback = (err, result) => { - for (const callback of callbacks) callback(err, result); - }; - this._snapshotCache.set(snapshot, callbacks); + if (desc.library) { + const EnableLibraryPlugin = __webpack_require__(35613); + EnableLibraryPlugin.checkEnabled(compiler, desc.library.type); } + return options; } +} - _readFileTimestamp(path, callback) { - this.fs.stat(path, (err, stat) => { - if (err) { - if (err.code === "ENOENT") { - this._fileTimestamps.set(path, null); - this._cachedDeprecatedFileTimestamps = undefined; - return callback(null, null); - } - return callback(err); - } - - let ts; - if (stat.isDirectory()) { - ts = { - safeTime: 0, - timestamp: undefined - }; - } else { - const mtime = +stat.mtime; - - if (mtime) applyMtime(mtime); - - ts = { - safeTime: mtime ? mtime + FS_ACCURACY : Infinity, - timestamp: mtime - }; - } +module.exports = EntryOptionPlugin; - this._fileTimestamps.set(path, ts); - this._cachedDeprecatedFileTimestamps = undefined; - callback(null, ts); - }); - } +/***/ }), - _readFileHash(path, callback) { - this.fs.readFile(path, (err, content) => { - if (err) { - if (err.code === "EISDIR") { - this._fileHashes.set(path, "directory"); - return callback(null, "directory"); - } - if (err.code === "ENOENT") { - this._fileHashes.set(path, null); - return callback(null, null); - } - if (err.code === "ERR_FS_FILE_TOO_LARGE") { - this.logger.warn(`Ignoring ${path} for hashing as it's very large`); - this._fileHashes.set(path, "too large"); - return callback(null, "too large"); - } - return callback(err); - } +/***/ 82430: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - const hash = createHash(this._hashFunction); +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ - hash.update(content); - const digest = /** @type {string} */ (hash.digest("hex")); - this._fileHashes.set(path, digest); +const EntryDependency = __webpack_require__(41075); - callback(null, digest); - }); - } +/** @typedef {import("./Compiler")} Compiler */ +/** @typedef {import("./Entrypoint").EntryOptions} EntryOptions */ - _getFileTimestampAndHash(path, callback) { - const continueWithHash = hash => { - const cache = this._fileTimestamps.get(path); - if (cache !== undefined) { - if (cache !== "ignore") { - const result = { - ...cache, - hash - }; - this._fileTshs.set(path, result); - return callback(null, result); - } else { - this._fileTshs.set(path, hash); - return callback(null, hash); - } - } else { - this.fileTimestampQueue.add(path, (err, entry) => { - if (err) { - return callback(err); - } - const result = { - ...entry, - hash - }; - this._fileTshs.set(path, result); - return callback(null, result); - }); - } - }; - - const cache = this._fileHashes.get(path); - if (cache !== undefined) { - continueWithHash(cache); - } else { - this.fileHashQueue.add(path, (err, entry) => { - if (err) { - return callback(err); - } - continueWithHash(entry); - }); - } +class EntryPlugin { + /** + * An entry plugin which will handle + * creation of the EntryDependency + * + * @param {string} context context path + * @param {string} entry entry path + * @param {EntryOptions | string=} options entry options (passing a string is deprecated) + */ + constructor(context, entry, options) { + this.context = context; + this.entry = entry; + this.options = options || ""; } /** - * @template T - * @template ItemType - * @param {Object} options options - * @param {string} options.path path - * @param {function(string): ItemType} options.fromImmutablePath called when context item is an immutable path - * @param {function(string): ItemType} options.fromManagedItem called when context item is a managed path - * @param {function(string, string, function(Error=, ItemType=): void): void} options.fromSymlink called when context item is a symlink - * @param {function(string, IStats, function(Error=, ItemType=): void): void} options.fromFile called when context item is a file - * @param {function(string, IStats, function(Error=, ItemType=): void): void} options.fromDirectory called when context item is a directory - * @param {function(string[], ItemType[]): T} options.reduce called from all context items - * @param {function(Error=, (T)=): void} callback callback + * Apply the plugin + * @param {Compiler} compiler the compiler instance + * @returns {void} */ - _readContext( - { - path, - fromImmutablePath, - fromManagedItem, - fromSymlink, - fromFile, - fromDirectory, - reduce - }, - callback - ) { - this.fs.readdir(path, (err, _files) => { - if (err) { - if (err.code === "ENOENT") { - return callback(null, null); - } - return callback(err); + apply(compiler) { + compiler.hooks.compilation.tap( + "EntryPlugin", + (compilation, { normalModuleFactory }) => { + compilation.dependencyFactories.set( + EntryDependency, + normalModuleFactory + ); } - const files = /** @type {string[]} */ (_files) - .map(file => file.normalize("NFC")) - .filter(file => !/^\./.test(file)) - .sort(); - asyncLib.map( - files, - (file, callback) => { - const child = join(this.fs, path, file); - for (const immutablePath of this.immutablePathsRegExps) { - if (immutablePath.test(path)) { - // ignore any immutable path for timestamping - return callback(null, fromImmutablePath(path)); - } - } - for (const immutablePath of this.immutablePathsWithSlash) { - if (path.startsWith(immutablePath)) { - // ignore any immutable path for timestamping - return callback(null, fromImmutablePath(path)); - } - } - for (const managedPath of this.managedPathsRegExps) { - const match = managedPath.exec(path); - if (match) { - const managedItem = getManagedItem(match[1], path); - if (managedItem) { - // construct timestampHash from managed info - return this.managedItemQueue.add(managedItem, (err, info) => { - if (err) return callback(err); - return callback(null, fromManagedItem(info)); - }); - } - } - } - for (const managedPath of this.managedPathsWithSlash) { - if (path.startsWith(managedPath)) { - const managedItem = getManagedItem(managedPath, child); - if (managedItem) { - // construct timestampHash from managed info - return this.managedItemQueue.add(managedItem, (err, info) => { - if (err) return callback(err); - return callback(null, fromManagedItem(info)); - }); - } - } - } - - lstatReadlinkAbsolute(this.fs, child, (err, stat) => { - if (err) return callback(err); + ); - if (typeof stat === "string") { - return fromSymlink(child, stat, callback); - } + const { entry, options, context } = this; + const dep = EntryPlugin.createDependency(entry, options); - if (stat.isFile()) { - return fromFile(child, stat, callback); - } - if (stat.isDirectory()) { - return fromDirectory(child, stat, callback); - } - callback(null, null); - }); - }, - (err, results) => { - if (err) return callback(err); - const result = reduce(files, results); - callback(null, result); - } - ); + compiler.hooks.make.tapAsync("EntryPlugin", (compilation, callback) => { + compilation.addEntry(context, dep, options, err => { + callback(err); + }); }); } - _readContextTimestamp(path, callback) { - this._readContext( - { - path, - fromImmutablePath: () => null, - fromManagedItem: info => ({ - safeTime: 0, - timestampHash: info - }), - fromSymlink: (file, target, callback) => { - callback(null, { - timestampHash: target, - symlinks: new Set([target]) - }); - }, - fromFile: (file, stat, callback) => { - // Prefer the cached value over our new stat to report consistent results - const cache = this._fileTimestamps.get(file); - if (cache !== undefined) - return callback(null, cache === "ignore" ? null : cache); + /** + * @param {string} entry entry request + * @param {EntryOptions | string} options entry options (passing string is deprecated) + * @returns {EntryDependency} the dependency + */ + static createDependency(entry, options) { + const dep = new EntryDependency(entry); + // TODO webpack 6 remove string option + dep.loc = { name: typeof options === "object" ? options.name : options }; + return dep; + } +} - const mtime = +stat.mtime; +module.exports = EntryPlugin; - if (mtime) applyMtime(mtime); - const ts = { - safeTime: mtime ? mtime + FS_ACCURACY : Infinity, - timestamp: mtime - }; +/***/ }), - this._fileTimestamps.set(file, ts); - this._cachedDeprecatedFileTimestamps = undefined; - callback(null, ts); - }, - fromDirectory: (directory, stat, callback) => { - this.contextTimestampQueue.increaseParallelism(); - this._getUnresolvedContextTimestamp(directory, (err, tsEntry) => { - this.contextTimestampQueue.decreaseParallelism(); - callback(err, tsEntry); - }); - }, - reduce: (files, tsEntries) => { - let symlinks = undefined; +/***/ 86695: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - const hash = createHash(this._hashFunction); +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ - for (const file of files) hash.update(file); - let safeTime = 0; - for (const entry of tsEntries) { - if (!entry) { - hash.update("n"); - continue; - } - if (entry.timestamp) { - hash.update("f"); - hash.update(`${entry.timestamp}`); - } else if (entry.timestampHash) { - hash.update("d"); - hash.update(`${entry.timestampHash}`); - } - if (entry.symlinks !== undefined) { - if (symlinks === undefined) symlinks = new Set(); - addAll(entry.symlinks, symlinks); - } - if (entry.safeTime) { - safeTime = Math.max(safeTime, entry.safeTime); - } - } - const digest = /** @type {string} */ (hash.digest("hex")); - const result = { - safeTime, - timestampHash: digest - }; - if (symlinks) result.symlinks = symlinks; - return result; - } - }, - (err, result) => { - if (err) return callback(err); - this._contextTimestamps.set(path, result); - this._cachedDeprecatedContextTimestamps = undefined; +const ChunkGroup = __webpack_require__(96975); - callback(null, result); - } - ); +/** @typedef {import("../declarations/WebpackOptions").EntryDescriptionNormalized} EntryDescription */ +/** @typedef {import("./Chunk")} Chunk */ + +/** @typedef {{ name?: string } & Omit} EntryOptions */ + +/** + * Entrypoint serves as an encapsulation primitive for chunks that are + * a part of a single ChunkGroup. They represent all bundles that need to be loaded for a + * single instance of a page. Multi-page application architectures will typically yield multiple Entrypoint objects + * inside of the compilation, whereas a Single Page App may only contain one with many lazy-loaded chunks. + */ +class Entrypoint extends ChunkGroup { + /** + * Creates an instance of Entrypoint. + * @param {EntryOptions | string} entryOptions the options for the entrypoint (or name) + * @param {boolean=} initial false, when the entrypoint is not initial loaded + */ + constructor(entryOptions, initial = true) { + if (typeof entryOptions === "string") { + entryOptions = { name: entryOptions }; + } + super({ + name: entryOptions.name + }); + this.options = entryOptions; + /** @type {Chunk=} */ + this._runtimeChunk = undefined; + /** @type {Chunk=} */ + this._entrypointChunk = undefined; + /** @type {boolean} */ + this._initial = initial; } /** - * @param {ContextFileSystemInfoEntry} entry entry - * @param {function(Error=, ResolvedContextFileSystemInfoEntry=): void} callback callback + * @returns {boolean} true, when this chunk group will be loaded on initial page load + */ + isInitial() { + return this._initial; + } + + /** + * Sets the runtimeChunk for an entrypoint. + * @param {Chunk} chunk the chunk being set as the runtime chunk. * @returns {void} */ - _resolveContextTimestamp(entry, callback) { - const hashes = []; - let safeTime = 0; - processAsyncTree( - entry.symlinks, - 10, - (target, push, callback) => { - this._getUnresolvedContextTimestamp(target, (err, entry) => { - if (err) return callback(err); - if (entry && entry !== "ignore") { - hashes.push(entry.timestampHash); - if (entry.safeTime) { - safeTime = Math.max(safeTime, entry.safeTime); - } - if (entry.symlinks !== undefined) { - for (const target of entry.symlinks) push(target); - } - } - callback(); - }); - }, - err => { - if (err) return callback(err); - const hash = createHash(this._hashFunction); - hash.update(entry.timestampHash); - if (entry.safeTime) { - safeTime = Math.max(safeTime, entry.safeTime); - } - hashes.sort(); - for (const h of hashes) { - hash.update(h); - } - callback( - null, - (entry.resolved = { - safeTime, - timestampHash: /** @type {string} */ (hash.digest("hex")) - }) - ); - } - ); + setRuntimeChunk(chunk) { + this._runtimeChunk = chunk; } - _readContextHash(path, callback) { - this._readContext( - { - path, - fromImmutablePath: () => "", - fromManagedItem: info => info || "", - fromSymlink: (file, target, callback) => { - callback(null, { - hash: target, - symlinks: new Set([target]) - }); - }, - fromFile: (file, stat, callback) => - this.getFileHash(file, (err, hash) => { - callback(err, hash || ""); - }), - fromDirectory: (directory, stat, callback) => { - this.contextHashQueue.increaseParallelism(); - this._getUnresolvedContextHash(directory, (err, hash) => { - this.contextHashQueue.decreaseParallelism(); - callback(err, hash || ""); - }); - }, - /** - * @param {string[]} files files - * @param {(string | ContextHash)[]} fileHashes hashes - * @returns {ContextHash} reduced hash - */ - reduce: (files, fileHashes) => { - let symlinks = undefined; - const hash = createHash(this._hashFunction); + /** + * Fetches the chunk reference containing the webpack bootstrap code + * @returns {Chunk | null} returns the runtime chunk or null if there is none + */ + getRuntimeChunk() { + if (this._runtimeChunk) return this._runtimeChunk; + for (const parent of this.parentsIterable) { + if (parent instanceof Entrypoint) return parent.getRuntimeChunk(); + } + return null; + } - for (const file of files) hash.update(file); - for (const entry of fileHashes) { - if (typeof entry === "string") { - hash.update(entry); - } else { - hash.update(entry.hash); - if (entry.symlinks) { - if (symlinks === undefined) symlinks = new Set(); - addAll(entry.symlinks, symlinks); - } - } - } + /** + * Sets the chunk with the entrypoint modules for an entrypoint. + * @param {Chunk} chunk the chunk being set as the entrypoint chunk. + * @returns {void} + */ + setEntrypointChunk(chunk) { + this._entrypointChunk = chunk; + } - const result = { - hash: /** @type {string} */ (hash.digest("hex")) - }; - if (symlinks) result.symlinks = symlinks; - return result; - } - }, - (err, result) => { - if (err) return callback(err); - this._contextHashes.set(path, result); - return callback(null, result); - } - ); + /** + * Returns the chunk which contains the entrypoint modules + * (or at least the execution of them) + * @returns {Chunk} chunk + */ + getEntrypointChunk() { + return this._entrypointChunk; } /** - * @param {ContextHash} entry context hash - * @param {function(Error=, string=): void} callback callback - * @returns {void} + * @param {Chunk} oldChunk chunk to be replaced + * @param {Chunk} newChunk New chunk that will be replaced with + * @returns {boolean} returns true if the replacement was successful */ - _resolveContextHash(entry, callback) { - const hashes = []; - processAsyncTree( - entry.symlinks, - 10, - (target, push, callback) => { - this._getUnresolvedContextHash(target, (err, hash) => { - if (err) return callback(err); - if (hash) { - hashes.push(hash.hash); - if (hash.symlinks !== undefined) { - for (const target of hash.symlinks) push(target); - } - } - callback(); - }); - }, - err => { - if (err) return callback(err); - const hash = createHash(this._hashFunction); - hash.update(entry.hash); - hashes.sort(); - for (const h of hashes) { - hash.update(h); - } - callback( - null, - (entry.resolved = /** @type {string} */ (hash.digest("hex"))) - ); - } - ); + replaceChunk(oldChunk, newChunk) { + if (this._runtimeChunk === oldChunk) this._runtimeChunk = newChunk; + if (this._entrypointChunk === oldChunk) this._entrypointChunk = newChunk; + return super.replaceChunk(oldChunk, newChunk); } +} - _readContextTimestampAndHash(path, callback) { - const finalize = (timestamp, hash) => { - const result = - timestamp === "ignore" - ? hash - : { - ...timestamp, - ...hash - }; - this._contextTshs.set(path, result); - callback(null, result); - }; - const cachedHash = this._contextHashes.get(path); - const cachedTimestamp = this._contextTimestamps.get(path); - if (cachedHash !== undefined) { - if (cachedTimestamp !== undefined) { - finalize(cachedTimestamp, cachedHash); - } else { - this.contextTimestampQueue.add(path, (err, entry) => { - if (err) return callback(err); - finalize(entry, cachedHash); - }); - } - } else { - if (cachedTimestamp !== undefined) { - this.contextHashQueue.add(path, (err, entry) => { - if (err) return callback(err); - finalize(cachedTimestamp, entry); - }); - } else { - this._readContext( - { - path, - fromImmutablePath: () => null, - fromManagedItem: info => ({ - safeTime: 0, - timestampHash: info, - hash: info || "" - }), - fromSymlink: (fle, target, callback) => { - callback(null, { - timestampHash: target, - hash: target, - symlinks: new Set([target]) - }); - }, - fromFile: (file, stat, callback) => { - this._getFileTimestampAndHash(file, callback); - }, - fromDirectory: (directory, stat, callback) => { - this.contextTshQueue.increaseParallelism(); - this.contextTshQueue.add(directory, (err, result) => { - this.contextTshQueue.decreaseParallelism(); - callback(err, result); - }); - }, - /** - * @param {string[]} files files - * @param {(Partial & Partial | string | null)[]} results results - * @returns {ContextTimestampAndHash} tsh - */ - reduce: (files, results) => { - let symlinks = undefined; +module.exports = Entrypoint; - const tsHash = createHash(this._hashFunction); - const hash = createHash(this._hashFunction); - for (const file of files) { - tsHash.update(file); - hash.update(file); - } - let safeTime = 0; - for (const entry of results) { - if (!entry) { - tsHash.update("n"); - continue; - } - if (typeof entry === "string") { - tsHash.update("n"); - hash.update(entry); - continue; - } - if (entry.timestamp) { - tsHash.update("f"); - tsHash.update(`${entry.timestamp}`); - } else if (entry.timestampHash) { - tsHash.update("d"); - tsHash.update(`${entry.timestampHash}`); - } - if (entry.symlinks !== undefined) { - if (symlinks === undefined) symlinks = new Set(); - addAll(entry.symlinks, symlinks); - } - if (entry.safeTime) { - safeTime = Math.max(safeTime, entry.safeTime); - } - hash.update(entry.hash); - } +/***/ }), - const result = { - safeTime, - timestampHash: /** @type {string} */ (tsHash.digest("hex")), - hash: /** @type {string} */ (hash.digest("hex")) - }; - if (symlinks) result.symlinks = symlinks; - return result; - } - }, - (err, result) => { - if (err) return callback(err); - this._contextTshs.set(path, result); - return callback(null, result); - } - ); - } +/***/ 43755: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Authors Simen Brekken @simenbrekken, Einar Löve @einarlove +*/ + + + +const DefinePlugin = __webpack_require__(46754); +const WebpackError = __webpack_require__(68422); + +/** @typedef {import("./Compiler")} Compiler */ +/** @typedef {import("./DefinePlugin").CodeValue} CodeValue */ + +class EnvironmentPlugin { + constructor(...keys) { + if (keys.length === 1 && Array.isArray(keys[0])) { + this.keys = keys[0]; + this.defaultValues = {}; + } else if (keys.length === 1 && keys[0] && typeof keys[0] === "object") { + this.keys = Object.keys(keys[0]); + this.defaultValues = keys[0]; + } else { + this.keys = keys; + this.defaultValues = {}; } } /** - * @param {ContextTimestampAndHash} entry entry - * @param {function(Error=, ResolvedContextTimestampAndHash=): void} callback callback + * Apply the plugin + * @param {Compiler} compiler the compiler instance * @returns {void} */ - _resolveContextTsh(entry, callback) { - const hashes = []; - const tsHashes = []; - let safeTime = 0; - processAsyncTree( - entry.symlinks, - 10, - (target, push, callback) => { - this._getUnresolvedContextTsh(target, (err, entry) => { - if (err) return callback(err); - if (entry) { - hashes.push(entry.hash); - if (entry.timestampHash) tsHashes.push(entry.timestampHash); - if (entry.safeTime) { - safeTime = Math.max(safeTime, entry.safeTime); - } - if (entry.symlinks !== undefined) { - for (const target of entry.symlinks) push(target); - } - } - callback(); + apply(compiler) { + /** @type {Record} */ + const definitions = {}; + for (const key of this.keys) { + const value = + process.env[key] !== undefined + ? process.env[key] + : this.defaultValues[key]; + + if (value === undefined) { + compiler.hooks.thisCompilation.tap("EnvironmentPlugin", compilation => { + const error = new WebpackError( + `EnvironmentPlugin - ${key} environment variable is undefined.\n\n` + + "You can pass an object with default values to suppress this warning.\n" + + "See https://webpack.js.org/plugins/environment-plugin for example." + ); + + error.name = "EnvVariableNotDefinedError"; + compilation.errors.push(error); }); - }, - err => { - if (err) return callback(err); - const hash = createHash(this._hashFunction); - const tsHash = createHash(this._hashFunction); - hash.update(entry.hash); - if (entry.timestampHash) tsHash.update(entry.timestampHash); - if (entry.safeTime) { - safeTime = Math.max(safeTime, entry.safeTime); - } - hashes.sort(); - for (const h of hashes) { - hash.update(h); - } - tsHashes.sort(); - for (const h of tsHashes) { - tsHash.update(h); - } - callback( - null, - (entry.resolved = { - safeTime, - timestampHash: /** @type {string} */ (tsHash.digest("hex")), - hash: /** @type {string} */ (hash.digest("hex")) - }) - ); } - ); - } - _getManagedItemDirectoryInfo(path, callback) { - this.fs.readdir(path, (err, elements) => { - if (err) { - if (err.code === "ENOENT" || err.code === "ENOTDIR") { - return callback(null, EMPTY_SET); - } - return callback(err); - } - const set = new Set( - /** @type {string[]} */ (elements).map(element => - join(this.fs, path, element) - ) - ); - callback(null, set); - }); + definitions[`process.env.${key}`] = + value === undefined ? "undefined" : JSON.stringify(value); + } + + new DefinePlugin(definitions).apply(compiler); } +} - _getManagedItemInfo(path, callback) { - const dir = dirname(this.fs, path); - this.managedItemDirectoryQueue.add(dir, (err, elements) => { - if (err) { - return callback(err); - } - if (!elements.has(path)) { - // file or directory doesn't exist - this._managedItems.set(path, "missing"); - return callback(null, "missing"); - } - // something exists - // it may be a file or directory - if ( - path.endsWith("node_modules") && - (path.endsWith("/node_modules") || path.endsWith("\\node_modules")) - ) { - // we are only interested in existence of this special directory - this._managedItems.set(path, "exists"); - return callback(null, "exists"); - } +module.exports = EnvironmentPlugin; - // we assume it's a directory, as files shouldn't occur in managed paths - const packageJsonPath = join(this.fs, path, "package.json"); - this.fs.readFile(packageJsonPath, (err, content) => { - if (err) { - if (err.code === "ENOENT" || err.code === "ENOTDIR") { - // no package.json or path is not a directory - this.fs.readdir(path, (err, elements) => { - if ( - !err && - elements.length === 1 && - elements[0] === "node_modules" - ) { - // This is only a grouping folder e. g. used by yarn - // we are only interested in existence of this special directory - this._managedItems.set(path, "nested"); - return callback(null, "nested"); - } - this.logger.warn( - `Managed item ${path} isn't a directory or doesn't contain a package.json (see snapshot.managedPaths option)` - ); - return callback(); - }); - return; - } - return callback(err); - } - let data; - try { - data = JSON.parse(content.toString("utf-8")); - } catch (e) { - return callback(e); - } - if (!data.name) { - this.logger.warn( - `${packageJsonPath} doesn't contain a "name" property (see snapshot.managedPaths option)` - ); - return callback(); - } - const info = `${data.name || ""}@${data.version || ""}`; - this._managedItems.set(path, info); - callback(null, info); - }); - }); - } - getDeprecatedFileTimestamps() { - if (this._cachedDeprecatedFileTimestamps !== undefined) - return this._cachedDeprecatedFileTimestamps; - const map = new Map(); - for (const [path, info] of this._fileTimestamps) { - if (info) map.set(path, typeof info === "object" ? info.safeTime : null); +/***/ }), + +/***/ 22569: +/***/ (function(__unused_webpack_module, exports) { + +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ + + + +const loaderFlag = "LOADER_EXECUTION"; + +const webpackOptionsFlag = "WEBPACK_OPTIONS"; + +exports.cutOffByFlag = (stack, flag) => { + stack = stack.split("\n"); + for (let i = 0; i < stack.length; i++) { + if (stack[i].includes(flag)) { + stack.length = i; } - return (this._cachedDeprecatedFileTimestamps = map); } + return stack.join("\n"); +}; - getDeprecatedContextTimestamps() { - if (this._cachedDeprecatedContextTimestamps !== undefined) - return this._cachedDeprecatedContextTimestamps; - const map = new Map(); - for (const [path, info] of this._contextTimestamps) { - if (info) map.set(path, typeof info === "object" ? info.safeTime : null); - } - return (this._cachedDeprecatedContextTimestamps = map); +exports.cutOffLoaderExecution = stack => + exports.cutOffByFlag(stack, loaderFlag); + +exports.cutOffWebpackOptions = stack => + exports.cutOffByFlag(stack, webpackOptionsFlag); + +exports.cutOffMultilineMessage = (stack, message) => { + stack = stack.split("\n"); + message = message.split("\n"); + + const result = []; + + stack.forEach((line, idx) => { + if (!line.includes(message[idx])) result.push(line); + }); + + return result.join("\n"); +}; + +exports.cutOffMessage = (stack, message) => { + const nextLine = stack.indexOf("\n"); + if (nextLine === -1) { + return stack === message ? "" : stack; + } else { + const firstLine = stack.substr(0, nextLine); + return firstLine === message ? stack.substr(nextLine + 1) : stack; } -} +}; -module.exports = FileSystemInfo; -module.exports.Snapshot = Snapshot; +exports.cleanUp = (stack, message) => { + stack = exports.cutOffLoaderExecution(stack); + stack = exports.cutOffMessage(stack, message); + return stack; +}; + +exports.cleanUpWebpackOptions = (stack, message) => { + stack = exports.cutOffWebpackOptions(stack); + stack = exports.cutOffMultilineMessage(stack, message); + return stack; +}; /***/ }), -/***/ 85310: +/***/ 4125: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; @@ -46059,14 +41394,34 @@ module.exports.Snapshot = Snapshot; -const { getEntryRuntime, mergeRuntimeOwned } = __webpack_require__(19655); +const { ConcatSource, RawSource } = __webpack_require__(96192); +const ExternalModule = __webpack_require__(89805); +const ModuleFilenameHelpers = __webpack_require__(80295); +const JavascriptModulesPlugin = __webpack_require__(76767); +/** @typedef {import("webpack-sources").Source} Source */ /** @typedef {import("./Compiler")} Compiler */ -/** @typedef {import("./util/runtime").RuntimeSpec} RuntimeSpec */ -class FlagAllModulesAsUsedPlugin { - constructor(explanation) { - this.explanation = explanation; +/** @type {WeakMap} */ +const cache = new WeakMap(); + +const devtoolWarning = new RawSource(`/* + * ATTENTION: The "eval" devtool has been used (maybe by default in mode: "development"). + * This devtool is neither made for production nor for readable output files. + * It uses "eval()" calls to create a separate source file in the browser devtools. + * If you are trying to read the output file, select a different devtool (https://webpack.js.org/configuration/devtool/) + * or disable the default devtool with "devtool: false". + * If you are looking for production-ready output files, see mode: "production" (https://webpack.js.org/configuration/mode/). + */ +`); + +class EvalDevToolModulePlugin { + constructor(options) { + this.namespace = options.namespace || ""; + this.sourceUrlComment = options.sourceUrlComment || "\n//# sourceURL=[url]"; + this.moduleFilenameTemplate = + options.moduleFilenameTemplate || + "webpack://[namespace]/[resourcePath]?[loaders]"; } /** @@ -46075,43 +41430,70 @@ class FlagAllModulesAsUsedPlugin { * @returns {void} */ apply(compiler) { - compiler.hooks.compilation.tap( - "FlagAllModulesAsUsedPlugin", - compilation => { - const moduleGraph = compilation.moduleGraph; - compilation.hooks.optimizeDependencies.tap( - "FlagAllModulesAsUsedPlugin", - modules => { - /** @type {RuntimeSpec} */ - let runtime = undefined; - for (const [name, { options }] of compilation.entries) { - runtime = mergeRuntimeOwned( - runtime, - getEntryRuntime(compilation, name, options) - ); - } - for (const module of modules) { - const exportsInfo = moduleGraph.getExportsInfo(module); - exportsInfo.setUsedInUnknownWay(runtime); - moduleGraph.addExtraReason(module, this.explanation); - if (module.factoryMeta === undefined) { - module.factoryMeta = {}; - } - module.factoryMeta.sideEffectFree = false; - } + compiler.hooks.compilation.tap("EvalDevToolModulePlugin", compilation => { + const hooks = JavascriptModulesPlugin.getCompilationHooks(compilation); + hooks.renderModuleContent.tap( + "EvalDevToolModulePlugin", + (source, module, { runtimeTemplate, chunkGraph }) => { + const cacheEntry = cache.get(source); + if (cacheEntry !== undefined) return cacheEntry; + if (module instanceof ExternalModule) { + cache.set(source, source); + return source; } - ); - } - ); + const content = source.source(); + const str = ModuleFilenameHelpers.createFilename( + module, + { + moduleFilenameTemplate: this.moduleFilenameTemplate, + namespace: this.namespace + }, + { + requestShortener: runtimeTemplate.requestShortener, + chunkGraph, + hashFunction: compilation.outputOptions.hashFunction + } + ); + const footer = + "\n" + + this.sourceUrlComment.replace( + /\[url\]/g, + encodeURI(str) + .replace(/%2F/g, "/") + .replace(/%20/g, "_") + .replace(/%5E/g, "^") + .replace(/%5C/g, "\\") + .replace(/^\//, "") + ); + const result = new RawSource( + `eval(${JSON.stringify(content + footer)});` + ); + cache.set(source, result); + return result; + } + ); + hooks.inlineInRuntimeBailout.tap( + "EvalDevToolModulePlugin", + () => "the eval devtool is used." + ); + hooks.render.tap( + "EvalDevToolModulePlugin", + source => new ConcatSource(devtoolWarning, source) + ); + hooks.chunkHash.tap("EvalDevToolModulePlugin", (chunk, hash) => { + hash.update("EvalDevToolModulePlugin"); + hash.update("2"); + }); + }); } } -module.exports = FlagAllModulesAsUsedPlugin; +module.exports = EvalDevToolModulePlugin; /***/ }), -/***/ 395: +/***/ 42053: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; @@ -46122,421 +41504,193 @@ module.exports = FlagAllModulesAsUsedPlugin; -const asyncLib = __webpack_require__(36386); -const Queue = __webpack_require__(65753); +const { ConcatSource, RawSource } = __webpack_require__(96192); +const ModuleFilenameHelpers = __webpack_require__(80295); +const NormalModule = __webpack_require__(11026); +const SourceMapDevToolModuleOptionsPlugin = __webpack_require__(37661); +const JavascriptModulesPlugin = __webpack_require__(76767); +const ConcatenatedModule = __webpack_require__(1881); +const { makePathsAbsolute } = __webpack_require__(96236); +/** @typedef {import("webpack-sources").Source} Source */ +/** @typedef {import("../declarations/WebpackOptions").DevTool} DevToolOptions */ +/** @typedef {import("../declarations/plugins/SourceMapDevToolPlugin").SourceMapDevToolPluginOptions} SourceMapDevToolPluginOptions */ /** @typedef {import("./Compiler")} Compiler */ -/** @typedef {import("./DependenciesBlock")} DependenciesBlock */ -/** @typedef {import("./Dependency")} Dependency */ -/** @typedef {import("./Dependency").ExportSpec} ExportSpec */ -/** @typedef {import("./Dependency").ExportsSpec} ExportsSpec */ -/** @typedef {import("./ExportsInfo")} ExportsInfo */ -/** @typedef {import("./Module")} Module */ -class FlagDependencyExportsPlugin { +/** @type {WeakMap} */ +const cache = new WeakMap(); + +const devtoolWarning = new RawSource(`/* + * ATTENTION: An "eval-source-map" devtool has been used. + * This devtool is neither made for production nor for readable output files. + * It uses "eval()" calls to create a separate source file with attached SourceMaps in the browser devtools. + * If you are trying to read the output file, select a different devtool (https://webpack.js.org/configuration/devtool/) + * or disable the default devtool with "devtool: false". + * If you are looking for production-ready output files, see mode: "production" (https://webpack.js.org/configuration/mode/). + */ +`); + +class EvalSourceMapDevToolPlugin { /** - * Apply the plugin - * @param {Compiler} compiler the compiler instance - * @returns {void} + * @param {SourceMapDevToolPluginOptions|string} inputOptions Options object */ - apply(compiler) { - compiler.hooks.compilation.tap( - "FlagDependencyExportsPlugin", - compilation => { - const moduleGraph = compilation.moduleGraph; - const cache = compilation.getCache("FlagDependencyExportsPlugin"); - compilation.hooks.finishModules.tapAsync( - "FlagDependencyExportsPlugin", - (modules, callback) => { - const logger = compilation.getLogger( - "webpack.FlagDependencyExportsPlugin" - ); - let statRestoredFromMemCache = 0; - let statRestoredFromCache = 0; - let statNoExports = 0; - let statFlaggedUncached = 0; - let statNotCached = 0; - let statQueueItemsProcessed = 0; - - const { moduleMemCaches } = compilation; + constructor(inputOptions) { + /** @type {SourceMapDevToolPluginOptions} */ + let options; + if (typeof inputOptions === "string") { + options = { + append: inputOptions + }; + } else { + options = inputOptions; + } + this.sourceMapComment = + options.append || "//# sourceURL=[module]\n//# sourceMappingURL=[url]"; + this.moduleFilenameTemplate = + options.moduleFilenameTemplate || + "webpack://[namespace]/[resource-path]?[hash]"; + this.namespace = options.namespace || ""; + this.options = options; + } - /** @type {Queue} */ - const queue = new Queue(); + /** + * Apply the plugin + * @param {Compiler} compiler the compiler instance + * @returns {void} + */ + apply(compiler) { + const options = this.options; + compiler.hooks.compilation.tap( + "EvalSourceMapDevToolPlugin", + compilation => { + const hooks = JavascriptModulesPlugin.getCompilationHooks(compilation); + new SourceMapDevToolModuleOptionsPlugin(options).apply(compilation); + const matchModule = ModuleFilenameHelpers.matchObject.bind( + ModuleFilenameHelpers, + options + ); + hooks.renderModuleContent.tap( + "EvalSourceMapDevToolPlugin", + (source, m, { runtimeTemplate, chunkGraph }) => { + const cachedSource = cache.get(source); + if (cachedSource !== undefined) { + return cachedSource; + } - // Step 1: Try to restore cached provided export info from cache - logger.time("restore cached provided exports"); - asyncLib.each( - modules, - (module, callback) => { - const exportsInfo = moduleGraph.getExportsInfo(module); - if (!module.buildMeta || !module.buildMeta.exportsType) { - if (exportsInfo.otherExportsInfo.provided !== null) { - // It's a module without declared exports - statNoExports++; - exportsInfo.setHasProvideInfo(); - exportsInfo.setUnknownExportsProvided(); - return callback(); - } - } - if (typeof module.buildInfo.hash !== "string") { - statFlaggedUncached++; - // Enqueue uncacheable module for determining the exports - queue.enqueue(module); - exportsInfo.setHasProvideInfo(); - return callback(); - } - const memCache = moduleMemCaches && moduleMemCaches.get(module); - const memCacheValue = memCache && memCache.get(this); - if (memCacheValue !== undefined) { - statRestoredFromMemCache++; - exportsInfo.restoreProvided(memCacheValue); - return callback(); - } - cache.get( - module.identifier(), - module.buildInfo.hash, - (err, result) => { - if (err) return callback(err); + const result = r => { + cache.set(source, r); + return r; + }; - if (result !== undefined) { - statRestoredFromCache++; - exportsInfo.restoreProvided(result); - } else { - statNotCached++; - // Without cached info enqueue module for determining the exports - queue.enqueue(module); - exportsInfo.setHasProvideInfo(); - } - callback(); - } + if (m instanceof NormalModule) { + const module = /** @type {NormalModule} */ (m); + if (!matchModule(module.resource)) { + return result(source); + } + } else if (m instanceof ConcatenatedModule) { + const concatModule = /** @type {ConcatenatedModule} */ (m); + if (concatModule.rootModule instanceof NormalModule) { + const module = /** @type {NormalModule} */ ( + concatModule.rootModule ); - }, - err => { - logger.timeEnd("restore cached provided exports"); - if (err) return callback(err); - - /** @type {Set} */ - const modulesToStore = new Set(); - - /** @type {Map>} */ - const dependencies = new Map(); - - /** @type {Module} */ - let module; - - /** @type {ExportsInfo} */ - let exportsInfo; - - /** @type {Map} */ - const exportsSpecsFromDependencies = new Map(); - - let cacheable = true; - let changed = false; - - /** - * @param {DependenciesBlock} depBlock the dependencies block - * @returns {void} - */ - const processDependenciesBlock = depBlock => { - for (const dep of depBlock.dependencies) { - processDependency(dep); - } - for (const block of depBlock.blocks) { - processDependenciesBlock(block); - } - }; - - /** - * @param {Dependency} dep the dependency - * @returns {void} - */ - const processDependency = dep => { - const exportDesc = dep.getExports(moduleGraph); - if (!exportDesc) return; - exportsSpecsFromDependencies.set(dep, exportDesc); - }; - - /** - * @param {Dependency} dep dependency - * @param {ExportsSpec} exportDesc info - * @returns {void} - */ - const processExportsSpec = (dep, exportDesc) => { - const exports = exportDesc.exports; - const globalCanMangle = exportDesc.canMangle; - const globalFrom = exportDesc.from; - const globalPriority = exportDesc.priority; - const globalTerminalBinding = - exportDesc.terminalBinding || false; - const exportDeps = exportDesc.dependencies; - if (exportDesc.hideExports) { - for (const name of exportDesc.hideExports) { - const exportInfo = exportsInfo.getExportInfo(name); - exportInfo.unsetTarget(dep); - } - } - if (exports === true) { - // unknown exports - if ( - exportsInfo.setUnknownExportsProvided( - globalCanMangle, - exportDesc.excludeExports, - globalFrom && dep, - globalFrom, - globalPriority - ) - ) { - changed = true; - } - } else if (Array.isArray(exports)) { - /** - * merge in new exports - * @param {ExportsInfo} exportsInfo own exports info - * @param {(ExportSpec | string)[]} exports list of exports - */ - const mergeExports = (exportsInfo, exports) => { - for (const exportNameOrSpec of exports) { - let name; - let canMangle = globalCanMangle; - let terminalBinding = globalTerminalBinding; - let exports = undefined; - let from = globalFrom; - let fromExport = undefined; - let priority = globalPriority; - let hidden = false; - if (typeof exportNameOrSpec === "string") { - name = exportNameOrSpec; - } else { - name = exportNameOrSpec.name; - if (exportNameOrSpec.canMangle !== undefined) - canMangle = exportNameOrSpec.canMangle; - if (exportNameOrSpec.export !== undefined) - fromExport = exportNameOrSpec.export; - if (exportNameOrSpec.exports !== undefined) - exports = exportNameOrSpec.exports; - if (exportNameOrSpec.from !== undefined) - from = exportNameOrSpec.from; - if (exportNameOrSpec.priority !== undefined) - priority = exportNameOrSpec.priority; - if (exportNameOrSpec.terminalBinding !== undefined) - terminalBinding = exportNameOrSpec.terminalBinding; - if (exportNameOrSpec.hidden !== undefined) - hidden = exportNameOrSpec.hidden; - } - const exportInfo = exportsInfo.getExportInfo(name); - - if ( - exportInfo.provided === false || - exportInfo.provided === null - ) { - exportInfo.provided = true; - changed = true; - } - - if ( - exportInfo.canMangleProvide !== false && - canMangle === false - ) { - exportInfo.canMangleProvide = false; - changed = true; - } - - if (terminalBinding && !exportInfo.terminalBinding) { - exportInfo.terminalBinding = true; - changed = true; - } - - if (exports) { - const nestedExportsInfo = - exportInfo.createNestedExportsInfo(); - mergeExports(nestedExportsInfo, exports); - } - - if ( - from && - (hidden - ? exportInfo.unsetTarget(dep) - : exportInfo.setTarget( - dep, - from, - fromExport === undefined ? [name] : fromExport, - priority - )) - ) { - changed = true; - } - - // Recalculate target exportsInfo - const target = exportInfo.getTarget(moduleGraph); - let targetExportsInfo = undefined; - if (target) { - const targetModuleExportsInfo = - moduleGraph.getExportsInfo(target.module); - targetExportsInfo = - targetModuleExportsInfo.getNestedExportsInfo( - target.export - ); - // add dependency for this module - const set = dependencies.get(target.module); - if (set === undefined) { - dependencies.set(target.module, new Set([module])); - } else { - set.add(module); - } - } - - if (exportInfo.exportsInfoOwned) { - if ( - exportInfo.exportsInfo.setRedirectNamedTo( - targetExportsInfo - ) - ) { - changed = true; - } - } else if ( - exportInfo.exportsInfo !== targetExportsInfo - ) { - exportInfo.exportsInfo = targetExportsInfo; - changed = true; - } - } - }; - mergeExports(exportsInfo, exports); - } - // store dependencies - if (exportDeps) { - cacheable = false; - for (const exportDependency of exportDeps) { - // add dependency for this module - const set = dependencies.get(exportDependency); - if (set === undefined) { - dependencies.set(exportDependency, new Set([module])); - } else { - set.add(module); - } - } - } - }; - - const notifyDependencies = () => { - const deps = dependencies.get(module); - if (deps !== undefined) { - for (const dep of deps) { - queue.enqueue(dep); - } - } - }; - - logger.time("figure out provided exports"); - while (queue.length > 0) { - module = queue.dequeue(); - - statQueueItemsProcessed++; - - exportsInfo = moduleGraph.getExportsInfo(module); - - cacheable = true; - changed = false; - - exportsSpecsFromDependencies.clear(); - moduleGraph.freeze(); - processDependenciesBlock(module); - moduleGraph.unfreeze(); - for (const [ - dep, - exportsSpec - ] of exportsSpecsFromDependencies) { - processExportsSpec(dep, exportsSpec); - } - - if (cacheable) { - modulesToStore.add(module); - } - - if (changed) { - notifyDependencies(); - } + if (!matchModule(module.resource)) { + return result(source); } - logger.timeEnd("figure out provided exports"); + } else { + return result(source); + } + } else { + return result(source); + } - logger.log( - `${Math.round( - (100 * (statFlaggedUncached + statNotCached)) / - (statRestoredFromMemCache + - statRestoredFromCache + - statNotCached + - statFlaggedUncached + - statNoExports) - )}% of exports of modules have been determined (${statNoExports} no declared exports, ${statNotCached} not cached, ${statFlaggedUncached} flagged uncacheable, ${statRestoredFromCache} from cache, ${statRestoredFromMemCache} from mem cache, ${ - statQueueItemsProcessed - - statNotCached - - statFlaggedUncached - } additional calculations due to dependencies)` - ); + /** @type {{ [key: string]: TODO; }} */ + let sourceMap; + let content; + if (source.sourceAndMap) { + const sourceAndMap = source.sourceAndMap(options); + sourceMap = sourceAndMap.map; + content = sourceAndMap.source; + } else { + sourceMap = source.map(options); + content = source.source(); + } + if (!sourceMap) { + return result(source); + } - logger.time("store provided exports into cache"); - asyncLib.each( - modulesToStore, - (module, callback) => { - if (typeof module.buildInfo.hash !== "string") { - // not cacheable - return callback(); - } - const cachedData = moduleGraph - .getExportsInfo(module) - .getRestoreProvidedData(); - const memCache = - moduleMemCaches && moduleMemCaches.get(module); - if (memCache) { - memCache.set(this, cachedData); - } - cache.store( - module.identifier(), - module.buildInfo.hash, - cachedData, - callback - ); - }, - err => { - logger.timeEnd("store provided exports into cache"); - callback(err); - } - ); + // Clone (flat) the sourcemap to ensure that the mutations below do not persist. + sourceMap = { ...sourceMap }; + const context = compiler.options.context; + const root = compiler.root; + const modules = sourceMap.sources.map(source => { + if (!source.startsWith("webpack://")) return source; + source = makePathsAbsolute(context, source.slice(10), root); + const module = compilation.findModule(source); + return module || source; + }); + let moduleFilenames = modules.map(module => { + return ModuleFilenameHelpers.createFilename( + module, + { + moduleFilenameTemplate: this.moduleFilenameTemplate, + namespace: this.namespace + }, + { + requestShortener: runtimeTemplate.requestShortener, + chunkGraph, + hashFunction: compilation.outputOptions.hashFunction + } + ); + }); + moduleFilenames = ModuleFilenameHelpers.replaceDuplicates( + moduleFilenames, + (filename, i, n) => { + for (let j = 0; j < n; j++) filename += "*"; + return filename; } ); - } - ); + sourceMap.sources = moduleFilenames; + sourceMap.sourceRoot = options.sourceRoot || ""; + const moduleId = chunkGraph.getModuleId(m); + sourceMap.file = `${moduleId}.js`; - /** @type {WeakMap} */ - const providedExportsCache = new WeakMap(); - compilation.hooks.rebuildModule.tap( - "FlagDependencyExportsPlugin", - module => { - providedExportsCache.set( - module, - moduleGraph.getExportsInfo(module).getRestoreProvidedData() + const footer = + this.sourceMapComment.replace( + /\[url\]/g, + `data:application/json;charset=utf-8;base64,${Buffer.from( + JSON.stringify(sourceMap), + "utf8" + ).toString("base64")}` + ) + `\n//# sourceURL=webpack-internal:///${moduleId}\n`; // workaround for chrome bug + + return result( + new RawSource(`eval(${JSON.stringify(content + footer)});`) ); } ); - compilation.hooks.finishRebuildingModule.tap( - "FlagDependencyExportsPlugin", - module => { - moduleGraph - .getExportsInfo(module) - .restoreProvided(providedExportsCache.get(module)); - } + hooks.inlineInRuntimeBailout.tap( + "EvalDevToolModulePlugin", + () => "the eval-source-map devtool is used." + ); + hooks.render.tap( + "EvalSourceMapDevToolPlugin", + source => new ConcatSource(devtoolWarning, source) ); + hooks.chunkHash.tap("EvalSourceMapDevToolPlugin", (chunk, hash) => { + hash.update("EvalSourceMapDevToolPlugin"); + hash.update("2"); + }); } ); } } -module.exports = FlagDependencyExportsPlugin; +module.exports = EvalSourceMapDevToolPlugin; /***/ }), -/***/ 13104: +/***/ 4295: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; @@ -46547,1910 +41701,1544 @@ module.exports = FlagDependencyExportsPlugin; -const Dependency = __webpack_require__(50384); -const { UsageState } = __webpack_require__(4295); -const ModuleGraphConnection = __webpack_require__(94144); -const { STAGE_DEFAULT } = __webpack_require__(68145); -const ArrayQueue = __webpack_require__(29704); -const TupleQueue = __webpack_require__(54345); -const { getEntryRuntime, mergeRuntimeOwned } = __webpack_require__(19655); +const { equals } = __webpack_require__(21537); +const SortableSet = __webpack_require__(67563); +const makeSerializable = __webpack_require__(26522); +const { forEachRuntime } = __webpack_require__(19655); -/** @typedef {import("./Chunk")} Chunk */ -/** @typedef {import("./ChunkGroup")} ChunkGroup */ -/** @typedef {import("./Compiler")} Compiler */ -/** @typedef {import("./DependenciesBlock")} DependenciesBlock */ -/** @typedef {import("./Dependency").ReferencedExport} ReferencedExport */ -/** @typedef {import("./ExportsInfo")} ExportsInfo */ +/** @typedef {import("./Dependency").RuntimeSpec} RuntimeSpec */ /** @typedef {import("./Module")} Module */ -/** @typedef {import("./util/runtime").RuntimeSpec} RuntimeSpec */ - -const { NO_EXPORTS_REFERENCED, EXPORTS_OBJECT_REFERENCED } = Dependency; - -class FlagDependencyUsagePlugin { - /** - * @param {boolean} global do a global analysis instead of per runtime - */ - constructor(global) { - this.global = global; - } - - /** - * Apply the plugin - * @param {Compiler} compiler the compiler instance - * @returns {void} - */ - apply(compiler) { - compiler.hooks.compilation.tap("FlagDependencyUsagePlugin", compilation => { - const moduleGraph = compilation.moduleGraph; - compilation.hooks.optimizeDependencies.tap( - { - name: "FlagDependencyUsagePlugin", - stage: STAGE_DEFAULT - }, - modules => { - if (compilation.moduleMemCaches) { - throw new Error( - "optimization.usedExports can't be used with cacheUnaffected as export usage is a global effect" - ); - } - - const logger = compilation.getLogger( - "webpack.FlagDependencyUsagePlugin" - ); - /** @type {Map} */ - const exportInfoToModuleMap = new Map(); - - /** @type {TupleQueue<[Module, RuntimeSpec]>} */ - const queue = new TupleQueue(); - - /** - * @param {Module} module module to process - * @param {(string[] | ReferencedExport)[]} usedExports list of used exports - * @param {RuntimeSpec} runtime part of which runtime - * @param {boolean} forceSideEffects always apply side effects - * @returns {void} - */ - const processReferencedModule = ( - module, - usedExports, - runtime, - forceSideEffects - ) => { - const exportsInfo = moduleGraph.getExportsInfo(module); - if (usedExports.length > 0) { - if (!module.buildMeta || !module.buildMeta.exportsType) { - if (exportsInfo.setUsedWithoutInfo(runtime)) { - queue.enqueue(module, runtime); - } - return; - } - for (const usedExportInfo of usedExports) { - let usedExport; - let canMangle = true; - if (Array.isArray(usedExportInfo)) { - usedExport = usedExportInfo; - } else { - usedExport = usedExportInfo.name; - canMangle = usedExportInfo.canMangle !== false; - } - if (usedExport.length === 0) { - if (exportsInfo.setUsedInUnknownWay(runtime)) { - queue.enqueue(module, runtime); - } - } else { - let currentExportsInfo = exportsInfo; - for (let i = 0; i < usedExport.length; i++) { - const exportInfo = currentExportsInfo.getExportInfo( - usedExport[i] - ); - if (canMangle === false) { - exportInfo.canMangleUse = false; - } - const lastOne = i === usedExport.length - 1; - if (!lastOne) { - const nestedInfo = exportInfo.getNestedExportsInfo(); - if (nestedInfo) { - if ( - exportInfo.setUsedConditionally( - used => used === UsageState.Unused, - UsageState.OnlyPropertiesUsed, - runtime - ) - ) { - const currentModule = - currentExportsInfo === exportsInfo - ? module - : exportInfoToModuleMap.get(currentExportsInfo); - if (currentModule) { - queue.enqueue(currentModule, runtime); - } - } - currentExportsInfo = nestedInfo; - continue; - } - } - if ( - exportInfo.setUsedConditionally( - v => v !== UsageState.Used, - UsageState.Used, - runtime - ) - ) { - const currentModule = - currentExportsInfo === exportsInfo - ? module - : exportInfoToModuleMap.get(currentExportsInfo); - if (currentModule) { - queue.enqueue(currentModule, runtime); - } - } - break; - } - } - } - } else { - // for a module without side effects we stop tracking usage here when no export is used - // This module won't be evaluated in this case - // TODO webpack 6 remove this check - if ( - !forceSideEffects && - module.factoryMeta !== undefined && - module.factoryMeta.sideEffectFree - ) { - return; - } - if (exportsInfo.setUsedForSideEffectsOnly(runtime)) { - queue.enqueue(module, runtime); - } - } - }; +/** @typedef {import("./ModuleGraph")} ModuleGraph */ +/** @typedef {import("./ModuleGraphConnection")} ModuleGraphConnection */ +/** @typedef {import("./util/Hash")} Hash */ - /** - * @param {DependenciesBlock} module the module - * @param {RuntimeSpec} runtime part of which runtime - * @param {boolean} forceSideEffects always apply side effects - * @returns {void} - */ - const processModule = (module, runtime, forceSideEffects) => { - /** @type {Map>} */ - const map = new Map(); +/** @typedef {typeof UsageState.OnlyPropertiesUsed | typeof UsageState.NoInfo | typeof UsageState.Unknown | typeof UsageState.Used} RuntimeUsageStateType */ +/** @typedef {typeof UsageState.Unused | RuntimeUsageStateType} UsageStateType */ - /** @type {ArrayQueue} */ - const queue = new ArrayQueue(); - queue.enqueue(module); - for (;;) { - const block = queue.dequeue(); - if (block === undefined) break; - for (const b of block.blocks) { - if ( - !this.global && - b.groupOptions && - b.groupOptions.entryOptions - ) { - processModule( - b, - b.groupOptions.entryOptions.runtime || undefined, - true - ); - } else { - queue.enqueue(b); - } - } - for (const dep of block.dependencies) { - const connection = moduleGraph.getConnection(dep); - if (!connection || !connection.module) { - continue; - } - const activeState = connection.getActiveState(runtime); - if (activeState === false) continue; - const { module } = connection; - if (activeState === ModuleGraphConnection.TRANSITIVE_ONLY) { - processModule(module, runtime, false); - continue; - } - const oldReferencedExports = map.get(module); - if (oldReferencedExports === EXPORTS_OBJECT_REFERENCED) { - continue; - } - const referencedExports = - compilation.getDependencyReferencedExports(dep, runtime); - if ( - oldReferencedExports === undefined || - oldReferencedExports === NO_EXPORTS_REFERENCED || - referencedExports === EXPORTS_OBJECT_REFERENCED - ) { - map.set(module, referencedExports); - } else if ( - oldReferencedExports !== undefined && - referencedExports === NO_EXPORTS_REFERENCED - ) { - continue; - } else { - let exportsMap; - if (Array.isArray(oldReferencedExports)) { - exportsMap = new Map(); - for (const item of oldReferencedExports) { - if (Array.isArray(item)) { - exportsMap.set(item.join("\n"), item); - } else { - exportsMap.set(item.name.join("\n"), item); - } - } - map.set(module, exportsMap); - } else { - exportsMap = oldReferencedExports; - } - for (const item of referencedExports) { - if (Array.isArray(item)) { - const key = item.join("\n"); - const oldItem = exportsMap.get(key); - if (oldItem === undefined) { - exportsMap.set(key, item); - } - // if oldItem is already an array we have to do nothing - // if oldItem is an ReferencedExport object, we don't have to do anything - // as canMangle defaults to true for arrays - } else { - const key = item.name.join("\n"); - const oldItem = exportsMap.get(key); - if (oldItem === undefined || Array.isArray(oldItem)) { - exportsMap.set(key, item); - } else { - exportsMap.set(key, { - name: item.name, - canMangle: item.canMangle && oldItem.canMangle - }); - } - } - } - } - } - } +const UsageState = Object.freeze({ + Unused: /** @type {0} */ (0), + OnlyPropertiesUsed: /** @type {1} */ (1), + NoInfo: /** @type {2} */ (2), + Unknown: /** @type {3} */ (3), + Used: /** @type {4} */ (4) +}); - for (const [module, referencedExports] of map) { - if (Array.isArray(referencedExports)) { - processReferencedModule( - module, - referencedExports, - runtime, - forceSideEffects - ); - } else { - processReferencedModule( - module, - Array.from(referencedExports.values()), - runtime, - forceSideEffects - ); - } - } - }; +const RETURNS_TRUE = () => true; - logger.time("initialize exports usage"); - for (const module of modules) { - const exportsInfo = moduleGraph.getExportsInfo(module); - exportInfoToModuleMap.set(exportsInfo, module); - exportsInfo.setHasUseInfo(); - } - logger.timeEnd("initialize exports usage"); +const CIRCULAR = Symbol("circular target"); - logger.time("trace exports usage in graph"); +class RestoreProvidedData { + constructor( + exports, + otherProvided, + otherCanMangleProvide, + otherTerminalBinding + ) { + this.exports = exports; + this.otherProvided = otherProvided; + this.otherCanMangleProvide = otherCanMangleProvide; + this.otherTerminalBinding = otherTerminalBinding; + } - /** - * @param {Dependency} dep dependency - * @param {RuntimeSpec} runtime runtime - */ - const processEntryDependency = (dep, runtime) => { - const module = moduleGraph.getModule(dep); - if (module) { - processReferencedModule( - module, - NO_EXPORTS_REFERENCED, - runtime, - true - ); - } - }; - /** @type {RuntimeSpec} */ - let globalRuntime = undefined; - for (const [ - entryName, - { dependencies: deps, includeDependencies: includeDeps, options } - ] of compilation.entries) { - const runtime = this.global - ? undefined - : getEntryRuntime(compilation, entryName, options); - for (const dep of deps) { - processEntryDependency(dep, runtime); - } - for (const dep of includeDeps) { - processEntryDependency(dep, runtime); - } - globalRuntime = mergeRuntimeOwned(globalRuntime, runtime); - } - for (const dep of compilation.globalEntry.dependencies) { - processEntryDependency(dep, globalRuntime); - } - for (const dep of compilation.globalEntry.includeDependencies) { - processEntryDependency(dep, globalRuntime); - } + serialize({ write }) { + write(this.exports); + write(this.otherProvided); + write(this.otherCanMangleProvide); + write(this.otherTerminalBinding); + } - while (queue.length) { - const [module, runtime] = queue.dequeue(); - processModule(module, runtime, false); - } - logger.timeEnd("trace exports usage in graph"); - } - ); - }); + static deserialize({ read }) { + return new RestoreProvidedData(read(), read(), read(), read()); } } -module.exports = FlagDependencyUsagePlugin; - - -/***/ }), - -/***/ 1826: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ - - - -/** @typedef {import("webpack-sources").Source} Source */ -/** @typedef {import("./ChunkGraph")} ChunkGraph */ -/** @typedef {import("./Compilation")} Compilation */ -/** @typedef {import("./ConcatenationScope")} ConcatenationScope */ -/** @typedef {import("./DependencyTemplate")} DependencyTemplate */ -/** @typedef {import("./DependencyTemplates")} DependencyTemplates */ -/** @typedef {import("./Module").ConcatenationBailoutReasonContext} ConcatenationBailoutReasonContext */ -/** @typedef {import("./ModuleGraph")} ModuleGraph */ -/** @typedef {import("./NormalModule")} NormalModule */ -/** @typedef {import("./RuntimeTemplate")} RuntimeTemplate */ -/** @typedef {import("./util/Hash")} Hash */ -/** @typedef {import("./util/runtime").RuntimeSpec} RuntimeSpec */ - -/** - * @typedef {Object} GenerateContext - * @property {DependencyTemplates} dependencyTemplates mapping from dependencies to templates - * @property {RuntimeTemplate} runtimeTemplate the runtime template - * @property {ModuleGraph} moduleGraph the module graph - * @property {ChunkGraph} chunkGraph the chunk graph - * @property {Set} runtimeRequirements the requirements for runtime - * @property {RuntimeSpec} runtime the runtime - * @property {ConcatenationScope=} concatenationScope when in concatenated module, information about other concatenated modules - * @property {string} type which kind of code should be generated - * @property {function(): Map=} getData get access to the code generation data - */ - -/** - * @typedef {Object} UpdateHashContext - * @property {NormalModule} module the module - * @property {ChunkGraph} chunkGraph - * @property {RuntimeSpec} runtime - */ - -/** - * - */ -class Generator { - static byType(map) { - return new ByTypeGenerator(map); - } +makeSerializable( + RestoreProvidedData, + "webpack/lib/ModuleGraph", + "RestoreProvidedData" +); - /* istanbul ignore next */ - /** - * @abstract - * @param {NormalModule} module fresh module - * @returns {Set} available types (do not mutate) - */ - getTypes(module) { - const AbstractMethodError = __webpack_require__(570); - throw new AbstractMethodError(); +class ExportsInfo { + constructor() { + /** @type {Map} */ + this._exports = new Map(); + this._otherExportsInfo = new ExportInfo(null); + this._sideEffectsOnlyInfo = new ExportInfo("*side effects only*"); + this._exportsAreOrdered = false; + /** @type {ExportsInfo=} */ + this._redirectTo = undefined; } - /* istanbul ignore next */ /** - * @abstract - * @param {NormalModule} module the module - * @param {string=} type source type - * @returns {number} estimate size of the module + * @returns {Iterable} all owned exports in any order */ - getSize(module, type) { - const AbstractMethodError = __webpack_require__(570); - throw new AbstractMethodError(); + get ownedExports() { + return this._exports.values(); } - /* istanbul ignore next */ /** - * @abstract - * @param {NormalModule} module module for which the code should be generated - * @param {GenerateContext} generateContext context for generate - * @returns {Source} generated code + * @returns {Iterable} all owned exports in order */ - generate( - module, - { dependencyTemplates, runtimeTemplate, moduleGraph, type } - ) { - const AbstractMethodError = __webpack_require__(570); - throw new AbstractMethodError(); + get orderedOwnedExports() { + if (!this._exportsAreOrdered) { + this._sortExports(); + } + return this._exports.values(); } /** - * @param {NormalModule} module module for which the bailout reason should be determined - * @param {ConcatenationBailoutReasonContext} context context - * @returns {string | undefined} reason why this module can't be concatenated, undefined when it can be concatenated + * @returns {Iterable} all exports in any order */ - getConcatenationBailoutReason(module, context) { - return `Module Concatenation is not implemented for ${this.constructor.name}`; + get exports() { + if (this._redirectTo !== undefined) { + const map = new Map(this._redirectTo._exports); + for (const [key, value] of this._exports) { + map.set(key, value); + } + return map.values(); + } + return this._exports.values(); } /** - * @param {Hash} hash hash that will be modified - * @param {UpdateHashContext} updateHashContext context for updating hash + * @returns {Iterable} all exports in order */ - updateHash(hash, { module, runtime }) { - // no nothing - } -} - -class ByTypeGenerator extends Generator { - constructor(map) { - super(); - this.map = map; - this._types = new Set(Object.keys(map)); + get orderedExports() { + if (!this._exportsAreOrdered) { + this._sortExports(); + } + if (this._redirectTo !== undefined) { + const map = new Map( + Array.from(this._redirectTo.orderedExports, item => [item.name, item]) + ); + for (const [key, value] of this._exports) { + map.set(key, value); + } + // sorting should be pretty fast as map contains + // a lot of presorted items + this._sortExportsMap(map); + return map.values(); + } + return this._exports.values(); } /** - * @param {NormalModule} module fresh module - * @returns {Set} available types (do not mutate) + * @returns {ExportInfo} the export info of unlisted exports */ - getTypes(module) { - return this._types; + get otherExportsInfo() { + if (this._redirectTo !== undefined) + return this._redirectTo.otherExportsInfo; + return this._otherExportsInfo; } - /** - * @param {NormalModule} module the module - * @param {string=} type source type - * @returns {number} estimate size of the module - */ - getSize(module, type) { - const t = type || "javascript"; - const generator = this.map[t]; - return generator ? generator.getSize(module, t) : 0; - } - - /** - * @param {NormalModule} module module for which the code should be generated - * @param {GenerateContext} generateContext context for generate - * @returns {Source} generated code - */ - generate(module, generateContext) { - const type = generateContext.type; - const generator = this.map[type]; - if (!generator) { - throw new Error(`Generator.byType: no generator specified for ${type}`); + _sortExportsMap(exports) { + if (exports.size > 1) { + const namesInOrder = []; + for (const entry of exports.values()) { + namesInOrder.push(entry.name); + } + namesInOrder.sort(); + let i = 0; + for (const entry of exports.values()) { + const name = namesInOrder[i]; + if (entry.name !== name) break; + i++; + } + for (; i < namesInOrder.length; i++) { + const name = namesInOrder[i]; + const correctEntry = exports.get(name); + exports.delete(name); + exports.set(name, correctEntry); + } } - return generator.generate(module, generateContext); } -} - -module.exports = Generator; - - -/***/ }), - -/***/ 76652: -/***/ (function(__unused_webpack_module, exports) { - -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ - - - -/** @typedef {import("./AsyncDependenciesBlock")} AsyncDependenciesBlock */ -/** @typedef {import("./Chunk")} Chunk */ -/** @typedef {import("./ChunkGroup")} ChunkGroup */ -/** @typedef {import("./DependenciesBlock")} DependenciesBlock */ -/** @typedef {import("./Module")} Module */ -/** - * @param {ChunkGroup} chunkGroup the ChunkGroup to connect - * @param {Chunk} chunk chunk to tie to ChunkGroup - * @returns {void} - */ -const connectChunkGroupAndChunk = (chunkGroup, chunk) => { - if (chunkGroup.pushChunk(chunk)) { - chunk.addGroup(chunkGroup); + _sortExports() { + this._sortExportsMap(this._exports); + this._exportsAreOrdered = true; } -}; -/** - * @param {ChunkGroup} parent parent ChunkGroup to connect - * @param {ChunkGroup} child child ChunkGroup to connect - * @returns {void} - */ -const connectChunkGroupParentAndChild = (parent, child) => { - if (parent.addChild(child)) { - child.addParent(parent); + setRedirectNamedTo(exportsInfo) { + if (this._redirectTo === exportsInfo) return false; + this._redirectTo = exportsInfo; + return true; } -}; - -exports.connectChunkGroupAndChunk = connectChunkGroupAndChunk; -exports.connectChunkGroupParentAndChild = connectChunkGroupParentAndChild; - - -/***/ }), - -/***/ 42766: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php -*/ - - - -const WebpackError = __webpack_require__(68422); -module.exports = class HarmonyLinkingError extends WebpackError { - /** @param {string} message Error message */ - constructor(message) { - super(message); - this.name = "HarmonyLinkingError"; - this.hideStack = true; + setHasProvideInfo() { + for (const exportInfo of this._exports.values()) { + if (exportInfo.provided === undefined) { + exportInfo.provided = false; + } + if (exportInfo.canMangleProvide === undefined) { + exportInfo.canMangleProvide = true; + } + } + if (this._redirectTo !== undefined) { + this._redirectTo.setHasProvideInfo(); + } else { + if (this._otherExportsInfo.provided === undefined) { + this._otherExportsInfo.provided = false; + } + if (this._otherExportsInfo.canMangleProvide === undefined) { + this._otherExportsInfo.canMangleProvide = true; + } + } } -}; - - -/***/ }), - -/***/ 89935: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Sean Larkin @thelarkinn -*/ - - -const WebpackError = __webpack_require__(68422); - -/** @typedef {import("./Module")} Module */ - -/** - * @template T - * @callback Callback - * @param {Error=} err - * @param {T=} stats - * @returns {void} - */ + setHasUseInfo() { + for (const exportInfo of this._exports.values()) { + exportInfo.setHasUseInfo(); + } + this._sideEffectsOnlyInfo.setHasUseInfo(); + if (this._redirectTo !== undefined) { + this._redirectTo.setHasUseInfo(); + } else { + this._otherExportsInfo.setHasUseInfo(); + if (this._otherExportsInfo.canMangleUse === undefined) { + this._otherExportsInfo.canMangleUse = true; + } + } + } -class HookWebpackError extends WebpackError { /** - * Creates an instance of HookWebpackError. - * @param {Error} error inner error - * @param {string} hook name of hook + * @param {string} name export name + * @returns {ExportInfo} export info for this name */ - constructor(error, hook) { - super(error.message); + getOwnExportInfo(name) { + const info = this._exports.get(name); + if (info !== undefined) return info; + const newInfo = new ExportInfo(name, this._otherExportsInfo); + this._exports.set(name, newInfo); + this._exportsAreOrdered = false; + return newInfo; + } - this.name = "HookWebpackError"; - this.hook = hook; - this.error = error; - this.hideStack = true; - this.details = `caused by plugins in ${hook}\n${error.stack}`; + /** + * @param {string} name export name + * @returns {ExportInfo} export info for this name + */ + getExportInfo(name) { + const info = this._exports.get(name); + if (info !== undefined) return info; + if (this._redirectTo !== undefined) + return this._redirectTo.getExportInfo(name); + const newInfo = new ExportInfo(name, this._otherExportsInfo); + this._exports.set(name, newInfo); + this._exportsAreOrdered = false; + return newInfo; + } - this.stack += `\n-- inner error --\n${error.stack}`; + /** + * @param {string} name export name + * @returns {ExportInfo} export info for this name + */ + getReadOnlyExportInfo(name) { + const info = this._exports.get(name); + if (info !== undefined) return info; + if (this._redirectTo !== undefined) + return this._redirectTo.getReadOnlyExportInfo(name); + return this._otherExportsInfo; } -} -module.exports = HookWebpackError; + /** + * @param {string[]} name export name + * @returns {ExportInfo | undefined} export info for this name + */ + getReadOnlyExportInfoRecursive(name) { + const exportInfo = this.getReadOnlyExportInfo(name[0]); + if (name.length === 1) return exportInfo; + if (!exportInfo.exportsInfo) return undefined; + return exportInfo.exportsInfo.getReadOnlyExportInfoRecursive(name.slice(1)); + } -/** - * @param {Error} error an error - * @param {string} hook name of the hook - * @returns {WebpackError} a webpack error - */ -const makeWebpackError = (error, hook) => { - if (error instanceof WebpackError) return error; - return new HookWebpackError(error, hook); -}; -module.exports.makeWebpackError = makeWebpackError; + /** + * @param {string[]=} name the export name + * @returns {ExportsInfo | undefined} the nested exports info + */ + getNestedExportsInfo(name) { + if (Array.isArray(name) && name.length > 0) { + const info = this.getReadOnlyExportInfo(name[0]); + if (!info.exportsInfo) return undefined; + return info.exportsInfo.getNestedExportsInfo(name.slice(1)); + } + return this; + } -/** - * @template T - * @param {function(WebpackError=, T=): void} callback webpack error callback - * @param {string} hook name of hook - * @returns {Callback} generic callback - */ -const makeWebpackErrorCallback = (callback, hook) => { - return (err, result) => { - if (err) { - if (err instanceof WebpackError) { - callback(err); - return; + /** + * @param {boolean=} canMangle true, if exports can still be mangled (defaults to false) + * @param {Set=} excludeExports list of unaffected exports + * @param {any=} targetKey use this as key for the target + * @param {ModuleGraphConnection=} targetModule set this module as target + * @param {number=} priority priority + * @returns {boolean} true, if this call changed something + */ + setUnknownExportsProvided( + canMangle, + excludeExports, + targetKey, + targetModule, + priority + ) { + let changed = false; + if (excludeExports) { + for (const name of excludeExports) { + // Make sure these entries exist, so they can get different info + this.getExportInfo(name); } - callback(new HookWebpackError(err, hook)); - return; } - callback(null, result); - }; -}; - -module.exports.makeWebpackErrorCallback = makeWebpackErrorCallback; - -/** - * @template T - * @param {function(): T} fn function which will be wrapping in try catch - * @param {string} hook name of hook - * @returns {T} the result - */ -const tryRunOrWebpackError = (fn, hook) => { - let r; - try { - r = fn(); - } catch (err) { - if (err instanceof WebpackError) { - throw err; + for (const exportInfo of this._exports.values()) { + if (excludeExports && excludeExports.has(exportInfo.name)) continue; + if (exportInfo.provided !== true && exportInfo.provided !== null) { + exportInfo.provided = null; + changed = true; + } + if (!canMangle && exportInfo.canMangleProvide !== false) { + exportInfo.canMangleProvide = false; + changed = true; + } + if (targetKey) { + exportInfo.setTarget(targetKey, targetModule, [exportInfo.name], -1); + } } - throw new HookWebpackError(err, hook); + if (this._redirectTo !== undefined) { + if ( + this._redirectTo.setUnknownExportsProvided( + canMangle, + excludeExports, + targetKey, + targetModule, + priority + ) + ) { + changed = true; + } + } else { + if ( + this._otherExportsInfo.provided !== true && + this._otherExportsInfo.provided !== null + ) { + this._otherExportsInfo.provided = null; + changed = true; + } + if (!canMangle && this._otherExportsInfo.canMangleProvide !== false) { + this._otherExportsInfo.canMangleProvide = false; + changed = true; + } + if (targetKey) { + this._otherExportsInfo.setTarget( + targetKey, + targetModule, + undefined, + priority + ); + } + } + return changed; } - return r; -}; - -module.exports.tryRunOrWebpackError = tryRunOrWebpackError; - - -/***/ }), - -/***/ 616: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ - - - -const { SyncBailHook } = __webpack_require__(34718); -const { RawSource } = __webpack_require__(96192); -const ChunkGraph = __webpack_require__(97860); -const Compilation = __webpack_require__(59622); -const HotUpdateChunk = __webpack_require__(39222); -const NormalModule = __webpack_require__(11026); -const RuntimeGlobals = __webpack_require__(49404); -const WebpackError = __webpack_require__(68422); -const ConstDependency = __webpack_require__(60864); -const ImportMetaHotAcceptDependency = __webpack_require__(58287); -const ImportMetaHotDeclineDependency = __webpack_require__(89911); -const ModuleHotAcceptDependency = __webpack_require__(90200); -const ModuleHotDeclineDependency = __webpack_require__(72986); -const HotModuleReplacementRuntimeModule = __webpack_require__(21978); -const JavascriptParser = __webpack_require__(42060); -const { - evaluateToIdentifier -} = __webpack_require__(28723); -const { find, isSubset } = __webpack_require__(34715); -const TupleSet = __webpack_require__(39322); -const { compareModulesById } = __webpack_require__(26296); -const { - getRuntimeKey, - keyToRuntime, - forEachRuntime, - mergeRuntimeOwned, - subtractRuntime, - intersectRuntime -} = __webpack_require__(19655); - -/** @typedef {import("./Chunk")} Chunk */ -/** @typedef {import("./Compilation").AssetInfo} AssetInfo */ -/** @typedef {import("./Compiler")} Compiler */ -/** @typedef {import("./Module")} Module */ -/** @typedef {import("./RuntimeModule")} RuntimeModule */ -/** @typedef {import("./util/runtime").RuntimeSpec} RuntimeSpec */ - -/** - * @typedef {Object} HMRJavascriptParserHooks - * @property {SyncBailHook<[TODO, string[]], void>} hotAcceptCallback - * @property {SyncBailHook<[TODO, string[]], void>} hotAcceptWithoutCallback - */ - -/** @type {WeakMap} */ -const parserHooksMap = new WeakMap(); -class HotModuleReplacementPlugin { /** - * @param {JavascriptParser} parser the parser - * @returns {HMRJavascriptParserHooks} the attached hooks + * @param {RuntimeSpec} runtime the runtime + * @returns {boolean} true, when something changed */ - static getParserHooks(parser) { - if (!(parser instanceof JavascriptParser)) { - throw new TypeError( - "The 'parser' argument must be an instance of JavascriptParser" - ); + setUsedInUnknownWay(runtime) { + let changed = false; + for (const exportInfo of this._exports.values()) { + if (exportInfo.setUsedInUnknownWay(runtime)) { + changed = true; + } } - let hooks = parserHooksMap.get(parser); - if (hooks === undefined) { - hooks = { - hotAcceptCallback: new SyncBailHook(["expression", "requests"]), - hotAcceptWithoutCallback: new SyncBailHook(["expression", "requests"]) - }; - parserHooksMap.set(parser, hooks); + if (this._redirectTo !== undefined) { + if (this._redirectTo.setUsedInUnknownWay(runtime)) { + changed = true; + } + } else { + if ( + this._otherExportsInfo.setUsedConditionally( + used => used < UsageState.Unknown, + UsageState.Unknown, + runtime + ) + ) { + changed = true; + } + if (this._otherExportsInfo.canMangleUse !== false) { + this._otherExportsInfo.canMangleUse = false; + changed = true; + } } - return hooks; + return changed; } - constructor(options) { - this.options = options || {}; + /** + * @param {RuntimeSpec} runtime the runtime + * @returns {boolean} true, when something changed + */ + setUsedWithoutInfo(runtime) { + let changed = false; + for (const exportInfo of this._exports.values()) { + if (exportInfo.setUsedWithoutInfo(runtime)) { + changed = true; + } + } + if (this._redirectTo !== undefined) { + if (this._redirectTo.setUsedWithoutInfo(runtime)) { + changed = true; + } + } else { + if (this._otherExportsInfo.setUsed(UsageState.NoInfo, runtime)) { + changed = true; + } + if (this._otherExportsInfo.canMangleUse !== false) { + this._otherExportsInfo.canMangleUse = false; + changed = true; + } + } + return changed; } /** - * Apply the plugin - * @param {Compiler} compiler the compiler instance - * @returns {void} + * @param {RuntimeSpec} runtime the runtime + * @returns {boolean} true, when something changed */ - apply(compiler) { - const { _backCompat: backCompat } = compiler; - if (compiler.options.output.strictModuleErrorHandling === undefined) - compiler.options.output.strictModuleErrorHandling = true; - const runtimeRequirements = [RuntimeGlobals.module]; - - const createAcceptHandler = (parser, ParamDependency) => { - const { hotAcceptCallback, hotAcceptWithoutCallback } = - HotModuleReplacementPlugin.getParserHooks(parser); + setAllKnownExportsUsed(runtime) { + let changed = false; + for (const exportInfo of this._exports.values()) { + if (!exportInfo.provided) continue; + if (exportInfo.setUsed(UsageState.Used, runtime)) { + changed = true; + } + } + return changed; + } - return expr => { - const module = parser.state.module; - const dep = new ConstDependency( - `${module.moduleArgument}.hot.accept`, - expr.callee.range, - runtimeRequirements - ); - dep.loc = expr.loc; - module.addPresentationalDependency(dep); - module.buildInfo.moduleConcatenationBailout = "Hot Module Replacement"; - if (expr.arguments.length >= 1) { - const arg = parser.evaluateExpression(expr.arguments[0]); - let params = []; - let requests = []; - if (arg.isString()) { - params = [arg]; - } else if (arg.isArray()) { - params = arg.items.filter(param => param.isString()); - } - if (params.length > 0) { - params.forEach((param, idx) => { - const request = param.string; - const dep = new ParamDependency(request, param.range); - dep.optional = true; - dep.loc = Object.create(expr.loc); - dep.loc.index = idx; - module.addDependency(dep); - requests.push(request); - }); - if (expr.arguments.length > 1) { - hotAcceptCallback.call(expr.arguments[1], requests); - for (let i = 1; i < expr.arguments.length; i++) { - parser.walkExpression(expr.arguments[i]); - } - return true; - } else { - hotAcceptWithoutCallback.call(expr, requests); - return true; - } - } - } - parser.walkExpressions(expr.arguments); - return true; - }; - }; + /** + * @param {RuntimeSpec} runtime the runtime + * @returns {boolean} true, when something changed + */ + setUsedForSideEffectsOnly(runtime) { + return this._sideEffectsOnlyInfo.setUsedConditionally( + used => used === UsageState.Unused, + UsageState.Used, + runtime + ); + } - const createDeclineHandler = (parser, ParamDependency) => expr => { - const module = parser.state.module; - const dep = new ConstDependency( - `${module.moduleArgument}.hot.decline`, - expr.callee.range, - runtimeRequirements - ); - dep.loc = expr.loc; - module.addPresentationalDependency(dep); - module.buildInfo.moduleConcatenationBailout = "Hot Module Replacement"; - if (expr.arguments.length === 1) { - const arg = parser.evaluateExpression(expr.arguments[0]); - let params = []; - if (arg.isString()) { - params = [arg]; - } else if (arg.isArray()) { - params = arg.items.filter(param => param.isString()); - } - params.forEach((param, idx) => { - const dep = new ParamDependency(param.string, param.range); - dep.optional = true; - dep.loc = Object.create(expr.loc); - dep.loc.index = idx; - module.addDependency(dep); - }); + /** + * @param {RuntimeSpec} runtime the runtime + * @returns {boolean} true, when the module exports are used in any way + */ + isUsed(runtime) { + if (this._redirectTo !== undefined) { + if (this._redirectTo.isUsed(runtime)) { + return true; } - return true; - }; + } else { + if (this._otherExportsInfo.getUsed(runtime) !== UsageState.Unused) { + return true; + } + } + for (const exportInfo of this._exports.values()) { + if (exportInfo.getUsed(runtime) !== UsageState.Unused) { + return true; + } + } + return false; + } - const createHMRExpressionHandler = parser => expr => { - const module = parser.state.module; - const dep = new ConstDependency( - `${module.moduleArgument}.hot`, - expr.range, - runtimeRequirements - ); - dep.loc = expr.loc; - module.addPresentationalDependency(dep); - module.buildInfo.moduleConcatenationBailout = "Hot Module Replacement"; + /** + * @param {RuntimeSpec} runtime the runtime + * @returns {boolean} true, when the module is used in any way + */ + isModuleUsed(runtime) { + if (this.isUsed(runtime)) return true; + if (this._sideEffectsOnlyInfo.getUsed(runtime) !== UsageState.Unused) return true; - }; + return false; + } - const applyModuleHot = parser => { - parser.hooks.evaluateIdentifier.for("module.hot").tap( - { - name: "HotModuleReplacementPlugin", - before: "NodeStuffPlugin" - }, - expr => { - return evaluateToIdentifier( - "module.hot", - "module", - () => ["hot"], - true - )(expr); + /** + * @param {RuntimeSpec} runtime the runtime + * @returns {SortableSet | boolean | null} set of used exports, or true (when namespace object is used), or false (when unused), or null (when unknown) + */ + getUsedExports(runtime) { + if (!this._redirectTo !== undefined) { + switch (this._otherExportsInfo.getUsed(runtime)) { + case UsageState.NoInfo: + return null; + case UsageState.Unknown: + case UsageState.OnlyPropertiesUsed: + case UsageState.Used: + return true; + } + } + const array = []; + if (!this._exportsAreOrdered) this._sortExports(); + for (const exportInfo of this._exports.values()) { + switch (exportInfo.getUsed(runtime)) { + case UsageState.NoInfo: + return null; + case UsageState.Unknown: + return true; + case UsageState.OnlyPropertiesUsed: + case UsageState.Used: + array.push(exportInfo.name); + } + } + if (this._redirectTo !== undefined) { + const inner = this._redirectTo.getUsedExports(runtime); + if (inner === null) return null; + if (inner === true) return true; + if (inner !== false) { + for (const item of inner) { + array.push(item); } - ); - parser.hooks.call - .for("module.hot.accept") - .tap( - "HotModuleReplacementPlugin", - createAcceptHandler(parser, ModuleHotAcceptDependency) - ); - parser.hooks.call - .for("module.hot.decline") - .tap( - "HotModuleReplacementPlugin", - createDeclineHandler(parser, ModuleHotDeclineDependency) - ); - parser.hooks.expression - .for("module.hot") - .tap("HotModuleReplacementPlugin", createHMRExpressionHandler(parser)); - }; - - const applyImportMetaHot = parser => { - parser.hooks.evaluateIdentifier - .for("import.meta.webpackHot") - .tap("HotModuleReplacementPlugin", expr => { - return evaluateToIdentifier( - "import.meta.webpackHot", - "import.meta", - () => ["webpackHot"], - true - )(expr); - }); - parser.hooks.call - .for("import.meta.webpackHot.accept") - .tap( - "HotModuleReplacementPlugin", - createAcceptHandler(parser, ImportMetaHotAcceptDependency) - ); - parser.hooks.call - .for("import.meta.webpackHot.decline") - .tap( - "HotModuleReplacementPlugin", - createDeclineHandler(parser, ImportMetaHotDeclineDependency) - ); - parser.hooks.expression - .for("import.meta.webpackHot") - .tap("HotModuleReplacementPlugin", createHMRExpressionHandler(parser)); - }; - - compiler.hooks.compilation.tap( - "HotModuleReplacementPlugin", - (compilation, { normalModuleFactory }) => { - // This applies the HMR plugin only to the targeted compiler - // It should not affect child compilations - if (compilation.compiler !== compiler) return; + } + } + if (array.length === 0) { + switch (this._sideEffectsOnlyInfo.getUsed(runtime)) { + case UsageState.NoInfo: + return null; + case UsageState.Unused: + return false; + } + } + return new SortableSet(array); + } - //#region module.hot.* API - compilation.dependencyFactories.set( - ModuleHotAcceptDependency, - normalModuleFactory - ); - compilation.dependencyTemplates.set( - ModuleHotAcceptDependency, - new ModuleHotAcceptDependency.Template() - ); - compilation.dependencyFactories.set( - ModuleHotDeclineDependency, - normalModuleFactory - ); - compilation.dependencyTemplates.set( - ModuleHotDeclineDependency, - new ModuleHotDeclineDependency.Template() - ); - //#endregion + /** + * @returns {null | true | string[]} list of exports when known + */ + getProvidedExports() { + if (!this._redirectTo !== undefined) { + switch (this._otherExportsInfo.provided) { + case undefined: + return null; + case null: + return true; + case true: + return true; + } + } + const array = []; + if (!this._exportsAreOrdered) this._sortExports(); + for (const exportInfo of this._exports.values()) { + switch (exportInfo.provided) { + case undefined: + return null; + case null: + return true; + case true: + array.push(exportInfo.name); + } + } + if (this._redirectTo !== undefined) { + const inner = this._redirectTo.getProvidedExports(); + if (inner === null) return null; + if (inner === true) return true; + for (const item of inner) { + if (!array.includes(item)) { + array.push(item); + } + } + } + return array; + } - //#region import.meta.webpackHot.* API - compilation.dependencyFactories.set( - ImportMetaHotAcceptDependency, - normalModuleFactory - ); - compilation.dependencyTemplates.set( - ImportMetaHotAcceptDependency, - new ImportMetaHotAcceptDependency.Template() - ); - compilation.dependencyFactories.set( - ImportMetaHotDeclineDependency, - normalModuleFactory - ); - compilation.dependencyTemplates.set( - ImportMetaHotDeclineDependency, - new ImportMetaHotDeclineDependency.Template() - ); - //#endregion + /** + * @param {RuntimeSpec} runtime the runtime + * @returns {ExportInfo[]} exports that are relevant (not unused and potential provided) + */ + getRelevantExports(runtime) { + const list = []; + for (const exportInfo of this._exports.values()) { + const used = exportInfo.getUsed(runtime); + if (used === UsageState.Unused) continue; + if (exportInfo.provided === false) continue; + list.push(exportInfo); + } + if (this._redirectTo !== undefined) { + for (const exportInfo of this._redirectTo.getRelevantExports(runtime)) { + if (!this._exports.has(exportInfo.name)) list.push(exportInfo); + } + } + if ( + this._otherExportsInfo.provided !== false && + this._otherExportsInfo.getUsed(runtime) !== UsageState.Unused + ) { + list.push(this._otherExportsInfo); + } + return list; + } - let hotIndex = 0; - const fullHashChunkModuleHashes = {}; - const chunkModuleHashes = {}; + /** + * @param {string | string[]} name the name of the export + * @returns {boolean | undefined | null} if the export is provided + */ + isExportProvided(name) { + if (Array.isArray(name)) { + const info = this.getReadOnlyExportInfo(name[0]); + if (info.exportsInfo && name.length > 1) { + return info.exportsInfo.isExportProvided(name.slice(1)); + } + return info.provided; + } + const info = this.getReadOnlyExportInfo(name); + return info.provided; + } - compilation.hooks.record.tap( - "HotModuleReplacementPlugin", - (compilation, records) => { - if (records.hash === compilation.hash) return; - const chunkGraph = compilation.chunkGraph; - records.hash = compilation.hash; - records.hotIndex = hotIndex; - records.fullHashChunkModuleHashes = fullHashChunkModuleHashes; - records.chunkModuleHashes = chunkModuleHashes; - records.chunkHashes = {}; - records.chunkRuntime = {}; - for (const chunk of compilation.chunks) { - records.chunkHashes[chunk.id] = chunk.hash; - records.chunkRuntime[chunk.id] = getRuntimeKey(chunk.runtime); - } - records.chunkModuleIds = {}; - for (const chunk of compilation.chunks) { - records.chunkModuleIds[chunk.id] = Array.from( - chunkGraph.getOrderedChunkModulesIterable( - chunk, - compareModulesById(chunkGraph) - ), - m => chunkGraph.getModuleId(m) - ); - } - } - ); - /** @type {TupleSet<[Module, Chunk]>} */ - const updatedModules = new TupleSet(); - /** @type {TupleSet<[Module, Chunk]>} */ - const fullHashModules = new TupleSet(); - /** @type {TupleSet<[Module, RuntimeSpec]>} */ - const nonCodeGeneratedModules = new TupleSet(); - compilation.hooks.fullHash.tap("HotModuleReplacementPlugin", hash => { - const chunkGraph = compilation.chunkGraph; - const records = compilation.records; - for (const chunk of compilation.chunks) { - const getModuleHash = module => { - if ( - compilation.codeGenerationResults.has(module, chunk.runtime) - ) { - return compilation.codeGenerationResults.getHash( - module, - chunk.runtime - ); - } else { - nonCodeGeneratedModules.add(module, chunk.runtime); - return chunkGraph.getModuleHash(module, chunk.runtime); - } - }; - const fullHashModulesInThisChunk = - chunkGraph.getChunkFullHashModulesSet(chunk); - if (fullHashModulesInThisChunk !== undefined) { - for (const module of fullHashModulesInThisChunk) { - fullHashModules.add(module, chunk); - } - } - const modules = chunkGraph.getChunkModulesIterable(chunk); - if (modules !== undefined) { - if (records.chunkModuleHashes) { - if (fullHashModulesInThisChunk !== undefined) { - for (const module of modules) { - const key = `${chunk.id}|${module.identifier()}`; - const hash = getModuleHash(module); - if ( - fullHashModulesInThisChunk.has( - /** @type {RuntimeModule} */ (module) - ) - ) { - if (records.fullHashChunkModuleHashes[key] !== hash) { - updatedModules.add(module, chunk); - } - fullHashChunkModuleHashes[key] = hash; - } else { - if (records.chunkModuleHashes[key] !== hash) { - updatedModules.add(module, chunk); - } - chunkModuleHashes[key] = hash; - } - } - } else { - for (const module of modules) { - const key = `${chunk.id}|${module.identifier()}`; - const hash = getModuleHash(module); - if (records.chunkModuleHashes[key] !== hash) { - updatedModules.add(module, chunk); - } - chunkModuleHashes[key] = hash; - } - } - } else { - if (fullHashModulesInThisChunk !== undefined) { - for (const module of modules) { - const key = `${chunk.id}|${module.identifier()}`; - const hash = getModuleHash(module); - if ( - fullHashModulesInThisChunk.has( - /** @type {RuntimeModule} */ (module) - ) - ) { - fullHashChunkModuleHashes[key] = hash; - } else { - chunkModuleHashes[key] = hash; - } - } - } else { - for (const module of modules) { - const key = `${chunk.id}|${module.identifier()}`; - const hash = getModuleHash(module); - chunkModuleHashes[key] = hash; - } - } - } - } - } + /** + * @param {RuntimeSpec} runtime runtime + * @returns {string} key representing the usage + */ + getUsageKey(runtime) { + const key = []; + if (this._redirectTo !== undefined) { + key.push(this._redirectTo.getUsageKey(runtime)); + } else { + key.push(this._otherExportsInfo.getUsed(runtime)); + } + key.push(this._sideEffectsOnlyInfo.getUsed(runtime)); + for (const exportInfo of this.orderedOwnedExports) { + key.push(exportInfo.getUsed(runtime)); + } + return key.join("|"); + } - hotIndex = records.hotIndex || 0; - if (updatedModules.size > 0) hotIndex++; + /** + * @param {RuntimeSpec} runtimeA first runtime + * @param {RuntimeSpec} runtimeB second runtime + * @returns {boolean} true, when equally used + */ + isEquallyUsed(runtimeA, runtimeB) { + if (this._redirectTo !== undefined) { + if (!this._redirectTo.isEquallyUsed(runtimeA, runtimeB)) return false; + } else { + if ( + this._otherExportsInfo.getUsed(runtimeA) !== + this._otherExportsInfo.getUsed(runtimeB) + ) { + return false; + } + } + if ( + this._sideEffectsOnlyInfo.getUsed(runtimeA) !== + this._sideEffectsOnlyInfo.getUsed(runtimeB) + ) { + return false; + } + for (const exportInfo of this.ownedExports) { + if (exportInfo.getUsed(runtimeA) !== exportInfo.getUsed(runtimeB)) + return false; + } + return true; + } - hash.update(`${hotIndex}`); - }); - compilation.hooks.processAssets.tap( - { - name: "HotModuleReplacementPlugin", - stage: Compilation.PROCESS_ASSETS_STAGE_ADDITIONAL - }, - () => { - const chunkGraph = compilation.chunkGraph; - const records = compilation.records; - if (records.hash === compilation.hash) return; - if ( - !records.chunkModuleHashes || - !records.chunkHashes || - !records.chunkModuleIds - ) { - return; - } - for (const [module, chunk] of fullHashModules) { - const key = `${chunk.id}|${module.identifier()}`; - const hash = nonCodeGeneratedModules.has(module, chunk.runtime) - ? chunkGraph.getModuleHash(module, chunk.runtime) - : compilation.codeGenerationResults.getHash( - module, - chunk.runtime - ); - if (records.chunkModuleHashes[key] !== hash) { - updatedModules.add(module, chunk); - } - chunkModuleHashes[key] = hash; - } - - /** @type {Map, removedChunkIds: Set, removedModules: Set, filename: string, assetInfo: AssetInfo }>} */ - const hotUpdateMainContentByRuntime = new Map(); - let allOldRuntime; - for (const key of Object.keys(records.chunkRuntime)) { - const runtime = keyToRuntime(records.chunkRuntime[key]); - allOldRuntime = mergeRuntimeOwned(allOldRuntime, runtime); - } - forEachRuntime(allOldRuntime, runtime => { - const { path: filename, info: assetInfo } = - compilation.getPathWithInfo( - compilation.outputOptions.hotUpdateMainFilename, - { - hash: records.hash, - runtime - } - ); - hotUpdateMainContentByRuntime.set(runtime, { - updatedChunkIds: new Set(), - removedChunkIds: new Set(), - removedModules: new Set(), - filename, - assetInfo - }); - }); - if (hotUpdateMainContentByRuntime.size === 0) return; - - // Create a list of all active modules to verify which modules are removed completely - /** @type {Map} */ - const allModules = new Map(); - for (const module of compilation.modules) { - const id = chunkGraph.getModuleId(module); - allModules.set(id, module); - } - - // List of completely removed modules - /** @type {Set} */ - const completelyRemovedModules = new Set(); - - for (const key of Object.keys(records.chunkHashes)) { - const oldRuntime = keyToRuntime(records.chunkRuntime[key]); - /** @type {Module[]} */ - const remainingModules = []; - // Check which modules are removed - for (const id of records.chunkModuleIds[key]) { - const module = allModules.get(id); - if (module === undefined) { - completelyRemovedModules.add(id); - } else { - remainingModules.push(module); - } - } - - let chunkId; - let newModules; - let newRuntimeModules; - let newFullHashModules; - let newDependentHashModules; - let newRuntime; - let removedFromRuntime; - const currentChunk = find( - compilation.chunks, - chunk => `${chunk.id}` === key - ); - if (currentChunk) { - chunkId = currentChunk.id; - newRuntime = intersectRuntime( - currentChunk.runtime, - allOldRuntime - ); - if (newRuntime === undefined) continue; - newModules = chunkGraph - .getChunkModules(currentChunk) - .filter(module => updatedModules.has(module, currentChunk)); - newRuntimeModules = Array.from( - chunkGraph.getChunkRuntimeModulesIterable(currentChunk) - ).filter(module => updatedModules.has(module, currentChunk)); - const fullHashModules = - chunkGraph.getChunkFullHashModulesIterable(currentChunk); - newFullHashModules = - fullHashModules && - Array.from(fullHashModules).filter(module => - updatedModules.has(module, currentChunk) - ); - const dependentHashModules = - chunkGraph.getChunkDependentHashModulesIterable(currentChunk); - newDependentHashModules = - dependentHashModules && - Array.from(dependentHashModules).filter(module => - updatedModules.has(module, currentChunk) - ); - removedFromRuntime = subtractRuntime(oldRuntime, newRuntime); - } else { - // chunk has completely removed - chunkId = `${+key}` === key ? +key : key; - removedFromRuntime = oldRuntime; - newRuntime = oldRuntime; - } - if (removedFromRuntime) { - // chunk was removed from some runtimes - forEachRuntime(removedFromRuntime, runtime => { - hotUpdateMainContentByRuntime - .get(runtime) - .removedChunkIds.add(chunkId); - }); - // dispose modules from the chunk in these runtimes - // where they are no longer in this runtime - for (const module of remainingModules) { - const moduleKey = `${key}|${module.identifier()}`; - const oldHash = records.chunkModuleHashes[moduleKey]; - const runtimes = chunkGraph.getModuleRuntimes(module); - if (oldRuntime === newRuntime && runtimes.has(newRuntime)) { - // Module is still in the same runtime combination - const hash = nonCodeGeneratedModules.has(module, newRuntime) - ? chunkGraph.getModuleHash(module, newRuntime) - : compilation.codeGenerationResults.getHash( - module, - newRuntime - ); - if (hash !== oldHash) { - if (module.type === "runtime") { - newRuntimeModules = newRuntimeModules || []; - newRuntimeModules.push( - /** @type {RuntimeModule} */ (module) - ); - } else { - newModules = newModules || []; - newModules.push(module); - } - } - } else { - // module is no longer in this runtime combination - // We (incorrectly) assume that it's not in an overlapping runtime combination - // and dispose it from the main runtimes the chunk was removed from - forEachRuntime(removedFromRuntime, runtime => { - // If the module is still used in this runtime, do not dispose it - // This could create a bad runtime state where the module is still loaded, - // but no chunk which contains it. This means we don't receive further HMR updates - // to this module and that's bad. - // TODO force load one of the chunks which contains the module - for (const moduleRuntime of runtimes) { - if (typeof moduleRuntime === "string") { - if (moduleRuntime === runtime) return; - } else if (moduleRuntime !== undefined) { - if (moduleRuntime.has(runtime)) return; - } - } - hotUpdateMainContentByRuntime - .get(runtime) - .removedModules.add(module); - }); - } - } - } - if ( - (newModules && newModules.length > 0) || - (newRuntimeModules && newRuntimeModules.length > 0) - ) { - const hotUpdateChunk = new HotUpdateChunk(); - if (backCompat) - ChunkGraph.setChunkGraphForChunk(hotUpdateChunk, chunkGraph); - hotUpdateChunk.id = chunkId; - hotUpdateChunk.runtime = newRuntime; - if (currentChunk) { - for (const group of currentChunk.groupsIterable) - hotUpdateChunk.addGroup(group); - } - chunkGraph.attachModules(hotUpdateChunk, newModules || []); - chunkGraph.attachRuntimeModules( - hotUpdateChunk, - newRuntimeModules || [] - ); - if (newFullHashModules) { - chunkGraph.attachFullHashModules( - hotUpdateChunk, - newFullHashModules - ); - } - if (newDependentHashModules) { - chunkGraph.attachDependentHashModules( - hotUpdateChunk, - newDependentHashModules - ); - } - const renderManifest = compilation.getRenderManifest({ - chunk: hotUpdateChunk, - hash: records.hash, - fullHash: records.hash, - outputOptions: compilation.outputOptions, - moduleTemplates: compilation.moduleTemplates, - dependencyTemplates: compilation.dependencyTemplates, - codeGenerationResults: compilation.codeGenerationResults, - runtimeTemplate: compilation.runtimeTemplate, - moduleGraph: compilation.moduleGraph, - chunkGraph - }); - for (const entry of renderManifest) { - /** @type {string} */ - let filename; - /** @type {AssetInfo} */ - let assetInfo; - if ("filename" in entry) { - filename = entry.filename; - assetInfo = entry.info; - } else { - ({ path: filename, info: assetInfo } = - compilation.getPathWithInfo( - entry.filenameTemplate, - entry.pathOptions - )); - } - const source = entry.render(); - compilation.additionalChunkAssets.push(filename); - compilation.emitAsset(filename, source, { - hotModuleReplacement: true, - ...assetInfo - }); - if (currentChunk) { - currentChunk.files.add(filename); - compilation.hooks.chunkAsset.call(currentChunk, filename); - } - } - forEachRuntime(newRuntime, runtime => { - hotUpdateMainContentByRuntime - .get(runtime) - .updatedChunkIds.add(chunkId); - }); - } - } - const completelyRemovedModulesArray = Array.from( - completelyRemovedModules - ); - const hotUpdateMainContentByFilename = new Map(); - for (const { - removedChunkIds, - removedModules, - updatedChunkIds, - filename, - assetInfo - } of hotUpdateMainContentByRuntime.values()) { - const old = hotUpdateMainContentByFilename.get(filename); - if ( - old && - (!isSubset(old.removedChunkIds, removedChunkIds) || - !isSubset(old.removedModules, removedModules) || - !isSubset(old.updatedChunkIds, updatedChunkIds)) - ) { - compilation.warnings.push( - new WebpackError(`HotModuleReplacementPlugin -The configured output.hotUpdateMainFilename doesn't lead to unique filenames per runtime and HMR update differs between runtimes. -This might lead to incorrect runtime behavior of the applied update. -To fix this, make sure to include [runtime] in the output.hotUpdateMainFilename option, or use the default config.`) - ); - for (const chunkId of removedChunkIds) - old.removedChunkIds.add(chunkId); - for (const chunkId of removedModules) - old.removedModules.add(chunkId); - for (const chunkId of updatedChunkIds) - old.updatedChunkIds.add(chunkId); - continue; - } - hotUpdateMainContentByFilename.set(filename, { - removedChunkIds, - removedModules, - updatedChunkIds, - assetInfo - }); - } - for (const [ - filename, - { removedChunkIds, removedModules, updatedChunkIds, assetInfo } - ] of hotUpdateMainContentByFilename) { - const hotUpdateMainJson = { - c: Array.from(updatedChunkIds), - r: Array.from(removedChunkIds), - m: - removedModules.size === 0 - ? completelyRemovedModulesArray - : completelyRemovedModulesArray.concat( - Array.from(removedModules, m => - chunkGraph.getModuleId(m) - ) - ) - }; - - const source = new RawSource(JSON.stringify(hotUpdateMainJson)); - compilation.emitAsset(filename, source, { - hotModuleReplacement: true, - ...assetInfo - }); - } - } - ); - - compilation.hooks.additionalTreeRuntimeRequirements.tap( - "HotModuleReplacementPlugin", - (chunk, runtimeRequirements) => { - runtimeRequirements.add(RuntimeGlobals.hmrDownloadManifest); - runtimeRequirements.add(RuntimeGlobals.hmrDownloadUpdateHandlers); - runtimeRequirements.add(RuntimeGlobals.interceptModuleExecution); - runtimeRequirements.add(RuntimeGlobals.moduleCache); - compilation.addRuntimeModule( - chunk, - new HotModuleReplacementRuntimeModule() - ); - } - ); - - normalModuleFactory.hooks.parser - .for("javascript/auto") - .tap("HotModuleReplacementPlugin", parser => { - applyModuleHot(parser); - applyImportMetaHot(parser); - }); - normalModuleFactory.hooks.parser - .for("javascript/dynamic") - .tap("HotModuleReplacementPlugin", parser => { - applyModuleHot(parser); - }); - normalModuleFactory.hooks.parser - .for("javascript/esm") - .tap("HotModuleReplacementPlugin", parser => { - applyImportMetaHot(parser); - }); - - NormalModule.getCompilationHooks(compilation).loader.tap( - "HotModuleReplacementPlugin", - context => { - context.hot = true; - } - ); + /** + * @param {string | string[]} name export name + * @param {RuntimeSpec} runtime check usage for this runtime only + * @returns {UsageStateType} usage status + */ + getUsed(name, runtime) { + if (Array.isArray(name)) { + if (name.length === 0) return this.otherExportsInfo.getUsed(runtime); + let info = this.getReadOnlyExportInfo(name[0]); + if (info.exportsInfo && name.length > 1) { + return info.exportsInfo.getUsed(name.slice(1), runtime); } - ); + return info.getUsed(runtime); + } + let info = this.getReadOnlyExportInfo(name); + return info.getUsed(runtime); } -} - -module.exports = HotModuleReplacementPlugin; - - -/***/ }), - -/***/ 39222: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ - - -const Chunk = __webpack_require__(65574); - -/** @typedef {import("./ChunkGraph")} ChunkGraph */ -/** @typedef {import("./util/Hash")} Hash */ - -class HotUpdateChunk extends Chunk { - constructor() { - super(); + /** + * @param {string | string[]} name the export name + * @param {RuntimeSpec} runtime check usage for this runtime only + * @returns {string | string[] | false} the used name + */ + getUsedName(name, runtime) { + if (Array.isArray(name)) { + // TODO improve this + if (name.length === 0) { + if (!this.isUsed(runtime)) return false; + return name; + } + let info = this.getReadOnlyExportInfo(name[0]); + const x = info.getUsedName(name[0], runtime); + if (x === false) return false; + const arr = x === name[0] && name.length === 1 ? name : [x]; + if (name.length === 1) { + return arr; + } + if ( + info.exportsInfo && + info.getUsed(runtime) === UsageState.OnlyPropertiesUsed + ) { + const nested = info.exportsInfo.getUsedName(name.slice(1), runtime); + if (!nested) return false; + return arr.concat(nested); + } else { + return arr.concat(name.slice(1)); + } + } else { + let info = this.getReadOnlyExportInfo(name); + const usedName = info.getUsedName(name, runtime); + return usedName; + } } -} - -module.exports = HotUpdateChunk; - - -/***/ }), - -/***/ 91471: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Ivan Kopeykin @vankop -*/ - - - -const ModuleFactory = __webpack_require__(61574); - -/** @typedef {import("./ModuleFactory").ModuleFactoryCreateData} ModuleFactoryCreateData */ -/** @typedef {import("./ModuleFactory").ModuleFactoryResult} ModuleFactoryResult */ -/** @typedef {import("./NormalModuleFactory")} NormalModuleFactory */ -/** - * Ignores error when module is unresolved - */ -class IgnoreErrorModuleFactory extends ModuleFactory { /** - * @param {NormalModuleFactory} normalModuleFactory normalModuleFactory instance + * @param {Hash} hash the hash + * @param {RuntimeSpec} runtime the runtime + * @returns {void} */ - constructor(normalModuleFactory) { - super(); - - this.normalModuleFactory = normalModuleFactory; + updateHash(hash, runtime) { + this._updateHash(hash, runtime, new Set()); } /** - * @param {ModuleFactoryCreateData} data data object - * @param {function(Error=, ModuleFactoryResult=): void} callback callback + * @param {Hash} hash the hash + * @param {RuntimeSpec} runtime the runtime + * @param {Set} alreadyVisitedExportsInfo for circular references * @returns {void} */ - create(data, callback) { - this.normalModuleFactory.create(data, (err, result) => { - return callback(null, result); - }); + _updateHash(hash, runtime, alreadyVisitedExportsInfo) { + const set = new Set(alreadyVisitedExportsInfo); + set.add(this); + for (const exportInfo of this.orderedExports) { + if (exportInfo.hasInfo(this._otherExportsInfo, runtime)) { + exportInfo._updateHash(hash, runtime, set); + } + } + this._sideEffectsOnlyInfo._updateHash(hash, runtime, set); + this._otherExportsInfo._updateHash(hash, runtime, set); + if (this._redirectTo !== undefined) { + this._redirectTo._updateHash(hash, runtime, set); + } } -} - -module.exports = IgnoreErrorModuleFactory; - - -/***/ }), - -/***/ 8098: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ - - -const createSchemaValidation = __webpack_require__(77695); - -/** @typedef {import("../declarations/plugins/IgnorePlugin").IgnorePluginOptions} IgnorePluginOptions */ -/** @typedef {import("./Compiler")} Compiler */ -/** @typedef {import("./NormalModuleFactory").ResolveData} ResolveData */ - -const validate = createSchemaValidation( - __webpack_require__(21420), - () => __webpack_require__(51856), - { - name: "Ignore Plugin", - baseDataPath: "options" - } -); - -class IgnorePlugin { - /** - * @param {IgnorePluginOptions} options IgnorePlugin options - */ - constructor(options) { - validate(options); - this.options = options; - - /** @private @type {Function} */ - this.checkIgnore = this.checkIgnore.bind(this); + getRestoreProvidedData() { + const otherProvided = this._otherExportsInfo.provided; + const otherCanMangleProvide = this._otherExportsInfo.canMangleProvide; + const otherTerminalBinding = this._otherExportsInfo.terminalBinding; + const exports = []; + for (const exportInfo of this.orderedExports) { + if ( + exportInfo.provided !== otherProvided || + exportInfo.canMangleProvide !== otherCanMangleProvide || + exportInfo.terminalBinding !== otherTerminalBinding || + exportInfo.exportsInfoOwned + ) { + exports.push({ + name: exportInfo.name, + provided: exportInfo.provided, + canMangleProvide: exportInfo.canMangleProvide, + terminalBinding: exportInfo.terminalBinding, + exportsInfo: exportInfo.exportsInfoOwned + ? exportInfo.exportsInfo.getRestoreProvidedData() + : undefined + }); + } + } + return new RestoreProvidedData( + exports, + otherProvided, + otherCanMangleProvide, + otherTerminalBinding + ); } - /** - * Note that if "contextRegExp" is given, both the "resourceRegExp" - * and "contextRegExp" have to match. - * - * @param {ResolveData} resolveData resolve data - * @returns {false|undefined} returns false when the request should be ignored, otherwise undefined - */ - checkIgnore(resolveData) { - if ( - "checkResource" in this.options && - this.options.checkResource && - this.options.checkResource(resolveData.request, resolveData.context) - ) { - return false; + restoreProvided({ + otherProvided, + otherCanMangleProvide, + otherTerminalBinding, + exports + }) { + let wasEmpty = true; + for (const exportInfo of this._exports.values()) { + wasEmpty = false; + exportInfo.provided = otherProvided; + exportInfo.canMangleProvide = otherCanMangleProvide; + exportInfo.terminalBinding = otherTerminalBinding; } - - if ( - "resourceRegExp" in this.options && - this.options.resourceRegExp && - this.options.resourceRegExp.test(resolveData.request) - ) { - if ("contextRegExp" in this.options && this.options.contextRegExp) { - // if "contextRegExp" is given, - // both the "resourceRegExp" and "contextRegExp" have to match. - if (this.options.contextRegExp.test(resolveData.context)) { - return false; - } - } else { - return false; + this._otherExportsInfo.provided = otherProvided; + this._otherExportsInfo.canMangleProvide = otherCanMangleProvide; + this._otherExportsInfo.terminalBinding = otherTerminalBinding; + for (const exp of exports) { + const exportInfo = this.getExportInfo(exp.name); + exportInfo.provided = exp.provided; + exportInfo.canMangleProvide = exp.canMangleProvide; + exportInfo.terminalBinding = exp.terminalBinding; + if (exp.exportsInfo) { + const exportsInfo = exportInfo.createNestedExportsInfo(); + exportsInfo.restoreProvided(exp.exportsInfo); } } + if (wasEmpty) this._exportsAreOrdered = true; } +} +class ExportInfo { /** - * Apply the plugin - * @param {Compiler} compiler the compiler instance - * @returns {void} + * @param {string} name the original name of the export + * @param {ExportInfo=} initFrom init values from this ExportInfo */ - apply(compiler) { - compiler.hooks.normalModuleFactory.tap("IgnorePlugin", nmf => { - nmf.hooks.beforeResolve.tap("IgnorePlugin", this.checkIgnore); - }); - compiler.hooks.contextModuleFactory.tap("IgnorePlugin", cmf => { - cmf.hooks.beforeResolve.tap("IgnorePlugin", this.checkIgnore); - }); + constructor(name, initFrom) { + /** @type {string} */ + this.name = name; + /** @private @type {string | null} */ + this._usedName = initFrom ? initFrom._usedName : null; + /** @private @type {UsageStateType} */ + this._globalUsed = initFrom ? initFrom._globalUsed : undefined; + /** @private @type {Map} */ + this._usedInRuntime = + initFrom && initFrom._usedInRuntime + ? new Map(initFrom._usedInRuntime) + : undefined; + /** @private @type {boolean} */ + this._hasUseInRuntimeInfo = initFrom + ? initFrom._hasUseInRuntimeInfo + : false; + /** + * true: it is provided + * false: it is not provided + * null: only the runtime knows if it is provided + * undefined: it was not determined if it is provided + * @type {boolean | null | undefined} + */ + this.provided = initFrom ? initFrom.provided : undefined; + /** + * is the export a terminal binding that should be checked for export star conflicts + * @type {boolean} + */ + this.terminalBinding = initFrom ? initFrom.terminalBinding : false; + /** + * true: it can be mangled + * false: is can not be mangled + * undefined: it was not determined if it can be mangled + * @type {boolean | undefined} + */ + this.canMangleProvide = initFrom ? initFrom.canMangleProvide : undefined; + /** + * true: it can be mangled + * false: is can not be mangled + * undefined: it was not determined if it can be mangled + * @type {boolean | undefined} + */ + this.canMangleUse = initFrom ? initFrom.canMangleUse : undefined; + /** @type {boolean} */ + this.exportsInfoOwned = false; + /** @type {ExportsInfo=} */ + this.exportsInfo = undefined; + /** @type {Map=} */ + this._target = undefined; + if (initFrom && initFrom._target) { + this._target = new Map(); + for (const [key, value] of initFrom._target) { + this._target.set(key, { + connection: value.connection, + export: value.export || [name], + priority: value.priority + }); + } + } + /** @type {Map=} */ + this._maxTarget = undefined; } -} - -module.exports = IgnorePlugin; - - -/***/ }), - -/***/ 18913: -/***/ (function(module) { - -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ - - - -/** @typedef {import("../declarations/WebpackOptions").IgnoreWarningsNormalized} IgnoreWarningsNormalized */ -/** @typedef {import("./Compiler")} Compiler */ -class IgnoreWarningsPlugin { + // TODO webpack 5 remove + /** @private */ + get used() { + throw new Error("REMOVED"); + } + /** @private */ + get usedName() { + throw new Error("REMOVED"); + } /** - * @param {IgnoreWarningsNormalized} ignoreWarnings conditions to ignore warnings + * @private + * @param {*} v v */ - constructor(ignoreWarnings) { - this._ignoreWarnings = ignoreWarnings; + set used(v) { + throw new Error("REMOVED"); } /** - * Apply the plugin - * @param {Compiler} compiler the compiler instance - * @returns {void} + * @private + * @param {*} v v */ - apply(compiler) { - compiler.hooks.compilation.tap("IgnoreWarningsPlugin", compilation => { - compilation.hooks.processWarnings.tap( - "IgnoreWarningsPlugin", - warnings => { - return warnings.filter(warning => { - return !this._ignoreWarnings.some(ignore => - ignore(warning, compilation) - ); - }); - } - ); - }); + set usedName(v) { + throw new Error("REMOVED"); } -} - -module.exports = IgnoreWarningsPlugin; - - -/***/ }), - -/***/ 51739: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Florent Cailhol @ooflorent -*/ - - - -const { ConcatSource } = __webpack_require__(96192); -const makeSerializable = __webpack_require__(26522); - -/** @typedef {import("webpack-sources").Source} Source */ -/** @typedef {import("./Generator").GenerateContext} GenerateContext */ - -/** - * @param {InitFragment} fragment the init fragment - * @param {number} index index - * @returns {[InitFragment, number]} tuple with both - */ -const extractFragmentIndex = (fragment, index) => [fragment, index]; - -/** - * @param {[InitFragment, number]} a first pair - * @param {[InitFragment, number]} b second pair - * @returns {number} sort value - */ -const sortFragmentWithIndex = ([a, i], [b, j]) => { - const stageCmp = a.stage - b.stage; - if (stageCmp !== 0) return stageCmp; - const positionCmp = a.position - b.position; - if (positionCmp !== 0) return positionCmp; - return i - j; -}; -/** - * @template Context - */ -class InitFragment { - /** - * @param {string|Source} content the source code that will be included as initialization code - * @param {number} stage category of initialization code (contribute to order) - * @param {number} position position in the category (contribute to order) - * @param {string=} key unique key to avoid emitting the same initialization code twice - * @param {string|Source=} endContent the source code that will be included at the end of the module - */ - constructor(content, stage, position, key, endContent) { - this.content = content; - this.stage = stage; - this.position = position; - this.key = key; - this.endContent = endContent; + get canMangle() { + switch (this.canMangleProvide) { + case undefined: + return this.canMangleUse === false ? false : undefined; + case false: + return false; + case true: + switch (this.canMangleUse) { + case undefined: + return undefined; + case false: + return false; + case true: + return true; + } + } + throw new Error( + `Unexpected flags for canMangle ${this.canMangleProvide} ${this.canMangleUse}` + ); } /** - * @param {Context} context context - * @returns {string|Source} the source code that will be included as initialization code + * @param {RuntimeSpec} runtime only apply to this runtime + * @returns {boolean} true, when something changed */ - getContent(context) { - return this.content; + setUsedInUnknownWay(runtime) { + let changed = false; + if ( + this.setUsedConditionally( + used => used < UsageState.Unknown, + UsageState.Unknown, + runtime + ) + ) { + changed = true; + } + if (this.canMangleUse !== false) { + this.canMangleUse = false; + changed = true; + } + return changed; } /** - * @param {Context} context context - * @returns {string|Source=} the source code that will be included at the end of the module + * @param {RuntimeSpec} runtime only apply to this runtime + * @returns {boolean} true, when something changed */ - getEndContent(context) { - return this.endContent; + setUsedWithoutInfo(runtime) { + let changed = false; + if (this.setUsed(UsageState.NoInfo, runtime)) { + changed = true; + } + if (this.canMangleUse !== false) { + this.canMangleUse = false; + changed = true; + } + return changed; } - static addToSource(source, initFragments, context) { - if (initFragments.length > 0) { - // Sort fragments by position. If 2 fragments have the same position, - // use their index. - const sortedFragments = initFragments - .map(extractFragmentIndex) - .sort(sortFragmentWithIndex); + setHasUseInfo() { + if (!this._hasUseInRuntimeInfo) { + this._hasUseInRuntimeInfo = true; + } + if (this.canMangleUse === undefined) { + this.canMangleUse = true; + } + if (this.exportsInfoOwned) { + this.exportsInfo.setHasUseInfo(); + } + } - // Deduplicate fragments. If a fragment has no key, it is always included. - const keyedFragments = new Map(); - for (const [fragment] of sortedFragments) { - if (typeof fragment.mergeAll === "function") { - if (!fragment.key) { - throw new Error( - `InitFragment with mergeAll function must have a valid key: ${fragment.constructor.name}` - ); - } - const oldValue = keyedFragments.get(fragment.key); - if (oldValue === undefined) { - keyedFragments.set(fragment.key, fragment); - } else if (Array.isArray(oldValue)) { - oldValue.push(fragment); + /** + * @param {function(UsageStateType): boolean} condition compare with old value + * @param {UsageStateType} newValue set when condition is true + * @param {RuntimeSpec} runtime only apply to this runtime + * @returns {boolean} true when something has changed + */ + setUsedConditionally(condition, newValue, runtime) { + if (runtime === undefined) { + if (this._globalUsed === undefined) { + this._globalUsed = newValue; + return true; + } else { + if (this._globalUsed !== newValue && condition(this._globalUsed)) { + this._globalUsed = newValue; + return true; + } + } + } else if (this._usedInRuntime === undefined) { + if (newValue !== UsageState.Unused && condition(UsageState.Unused)) { + this._usedInRuntime = new Map(); + forEachRuntime(runtime, runtime => + this._usedInRuntime.set(runtime, newValue) + ); + return true; + } + } else { + let changed = false; + forEachRuntime(runtime, runtime => { + /** @type {UsageStateType} */ + let oldValue = this._usedInRuntime.get(runtime); + if (oldValue === undefined) oldValue = UsageState.Unused; + if (newValue !== oldValue && condition(oldValue)) { + if (newValue === UsageState.Unused) { + this._usedInRuntime.delete(runtime); } else { - keyedFragments.set(fragment.key, [oldValue, fragment]); - } - continue; - } else if (typeof fragment.merge === "function") { - const oldValue = keyedFragments.get(fragment.key); - if (oldValue !== undefined) { - keyedFragments.set(fragment.key, fragment.merge(oldValue)); - continue; + this._usedInRuntime.set(runtime, newValue); } + changed = true; } - keyedFragments.set(fragment.key || Symbol(), fragment); + }); + if (changed) { + if (this._usedInRuntime.size === 0) this._usedInRuntime = undefined; + return true; } + } + return false; + } - const concatSource = new ConcatSource(); - const endContents = []; - for (let fragment of keyedFragments.values()) { - if (Array.isArray(fragment)) { - fragment = fragment[0].mergeAll(fragment); - } - concatSource.add(fragment.getContent(context)); - const endContent = fragment.getEndContent(context); - if (endContent) { - endContents.push(endContent); - } + /** + * @param {UsageStateType} newValue new value of the used state + * @param {RuntimeSpec} runtime only apply to this runtime + * @returns {boolean} true when something has changed + */ + setUsed(newValue, runtime) { + if (runtime === undefined) { + if (this._globalUsed !== newValue) { + this._globalUsed = newValue; + return true; } - - concatSource.add(source); - for (const content of endContents.reverse()) { - concatSource.add(content); + } else if (this._usedInRuntime === undefined) { + if (newValue !== UsageState.Unused) { + this._usedInRuntime = new Map(); + forEachRuntime(runtime, runtime => + this._usedInRuntime.set(runtime, newValue) + ); + return true; } - return concatSource; } else { - return source; + let changed = false; + forEachRuntime(runtime, runtime => { + /** @type {UsageStateType} */ + let oldValue = this._usedInRuntime.get(runtime); + if (oldValue === undefined) oldValue = UsageState.Unused; + if (newValue !== oldValue) { + if (newValue === UsageState.Unused) { + this._usedInRuntime.delete(runtime); + } else { + this._usedInRuntime.set(runtime, newValue); + } + changed = true; + } + }); + if (changed) { + if (this._usedInRuntime.size === 0) this._usedInRuntime = undefined; + return true; + } } + return false; } - serialize(context) { - const { write } = context; - - write(this.content); - write(this.stage); - write(this.position); - write(this.key); - write(this.endContent); + /** + * @param {any} key the key + * @returns {boolean} true, if something has changed + */ + unsetTarget(key) { + if (!this._target) return false; + if (this._target.delete(key)) { + this._maxTarget = undefined; + return true; + } + return false; } - deserialize(context) { - const { read } = context; + /** + * @param {any} key the key + * @param {ModuleGraphConnection} connection the target module if a single one + * @param {string[]=} exportName the exported name + * @param {number=} priority priority + * @returns {boolean} true, if something has changed + */ + setTarget(key, connection, exportName, priority = 0) { + if (exportName) exportName = [...exportName]; + if (!this._target) { + this._target = new Map(); + this._target.set(key, { connection, export: exportName, priority }); + return true; + } + const oldTarget = this._target.get(key); + if (!oldTarget) { + if (oldTarget === null && !connection) return false; + this._target.set(key, { connection, export: exportName, priority }); + this._maxTarget = undefined; + return true; + } + if ( + oldTarget.connection !== connection || + oldTarget.priority !== priority || + (exportName + ? !oldTarget.export || !equals(oldTarget.export, exportName) + : oldTarget.export) + ) { + oldTarget.connection = connection; + oldTarget.export = exportName; + oldTarget.priority = priority; + this._maxTarget = undefined; + return true; + } + return false; + } - this.content = read(); - this.stage = read(); - this.position = read(); - this.key = read(); - this.endContent = read(); + /** + * @param {RuntimeSpec} runtime for this runtime + * @returns {UsageStateType} usage state + */ + getUsed(runtime) { + if (!this._hasUseInRuntimeInfo) return UsageState.NoInfo; + if (this._globalUsed !== undefined) return this._globalUsed; + if (this._usedInRuntime === undefined) { + return UsageState.Unused; + } else if (typeof runtime === "string") { + const value = this._usedInRuntime.get(runtime); + return value === undefined ? UsageState.Unused : value; + } else if (runtime === undefined) { + /** @type {UsageStateType} */ + let max = UsageState.Unused; + for (const value of this._usedInRuntime.values()) { + if (value === UsageState.Used) { + return UsageState.Used; + } + if (max < value) max = value; + } + return max; + } else { + /** @type {UsageStateType} */ + let max = UsageState.Unused; + for (const item of runtime) { + const value = this._usedInRuntime.get(item); + if (value !== undefined) { + if (value === UsageState.Used) { + return UsageState.Used; + } + if (max < value) max = value; + } + } + return max; + } } -} -makeSerializable(InitFragment, "webpack/lib/InitFragment"); + /** + * get used name + * @param {string | undefined} fallbackName fallback name for used exports with no name + * @param {RuntimeSpec} runtime check usage for this runtime only + * @returns {string | false} used name + */ + getUsedName(fallbackName, runtime) { + if (this._hasUseInRuntimeInfo) { + if (this._globalUsed !== undefined) { + if (this._globalUsed === UsageState.Unused) return false; + } else { + if (this._usedInRuntime === undefined) return false; + if (typeof runtime === "string") { + if (!this._usedInRuntime.has(runtime)) { + return false; + } + } else if (runtime !== undefined) { + if ( + Array.from(runtime).every( + runtime => !this._usedInRuntime.has(runtime) + ) + ) { + return false; + } + } + } + } + if (this._usedName !== null) return this._usedName; + return this.name || fallbackName; + } -InitFragment.prototype.merge = undefined; + /** + * @returns {boolean} true, when a mangled name of this export is set + */ + hasUsedName() { + return this._usedName !== null; + } -InitFragment.STAGE_CONSTANTS = 10; -InitFragment.STAGE_ASYNC_BOUNDARY = 20; -InitFragment.STAGE_HARMONY_EXPORTS = 30; -InitFragment.STAGE_HARMONY_IMPORTS = 40; -InitFragment.STAGE_PROVIDES = 50; -InitFragment.STAGE_ASYNC_DEPENDENCIES = 60; -InitFragment.STAGE_ASYNC_HARMONY_IMPORTS = 70; + /** + * Sets the mangled name of this export + * @param {string} name the new name + * @returns {void} + */ + setUsedName(name) { + this._usedName = name; + } -module.exports = InitFragment; + /** + * @param {ModuleGraph} moduleGraph the module graph + * @param {function({ module: Module, export: string[] | undefined }): boolean} resolveTargetFilter filter function to further resolve target + * @returns {ExportInfo | ExportsInfo | undefined} the terminal binding export(s) info if known + */ + getTerminalBinding(moduleGraph, resolveTargetFilter = RETURNS_TRUE) { + if (this.terminalBinding) return this; + const target = this.getTarget(moduleGraph, resolveTargetFilter); + if (!target) return undefined; + const exportsInfo = moduleGraph.getExportsInfo(target.module); + if (!target.export) return exportsInfo; + return exportsInfo.getReadOnlyExportInfoRecursive(target.export); + } + isReexport() { + return !this.terminalBinding && this._target && this._target.size > 0; + } -/***/ }), + _getMaxTarget() { + if (this._maxTarget !== undefined) return this._maxTarget; + if (this._target.size <= 1) return (this._maxTarget = this._target); + let maxPriority = -Infinity; + let minPriority = Infinity; + for (const { priority } of this._target.values()) { + if (maxPriority < priority) maxPriority = priority; + if (minPriority > priority) minPriority = priority; + } + // This should be very common + if (maxPriority === minPriority) return (this._maxTarget = this._target); -/***/ 2822: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + // This is an edge case + const map = new Map(); + for (const [key, value] of this._target) { + if (maxPriority === value.priority) { + map.set(key, value); + } + } + this._maxTarget = map; + return map; + } -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ + /** + * @param {ModuleGraph} moduleGraph the module graph + * @param {function(Module): boolean} validTargetModuleFilter a valid target module + * @returns {{ module: Module, export: string[] | undefined } | undefined | false} the target, undefined when there is no target, false when no target is valid + */ + findTarget(moduleGraph, validTargetModuleFilter) { + return this._findTarget(moduleGraph, validTargetModuleFilter, new Set()); + } + /** + * @param {ModuleGraph} moduleGraph the module graph + * @param {function(Module): boolean} validTargetModuleFilter a valid target module + * @param {Set | undefined} alreadyVisited set of already visited export info to avoid circular references + * @returns {{ module: Module, export: string[] | undefined } | undefined | false} the target, undefined when there is no target, false when no target is valid + */ + _findTarget(moduleGraph, validTargetModuleFilter, alreadyVisited) { + if (!this._target || this._target.size === 0) return undefined; + let rawTarget = this._getMaxTarget().values().next().value; + if (!rawTarget) return undefined; + /** @type {{ module: Module, export: string[] | undefined }} */ + let target = { + module: rawTarget.connection.module, + export: rawTarget.export + }; + for (;;) { + if (validTargetModuleFilter(target.module)) return target; + const exportsInfo = moduleGraph.getExportsInfo(target.module); + const exportInfo = exportsInfo.getExportInfo(target.export[0]); + if (alreadyVisited.has(exportInfo)) return null; + const newTarget = exportInfo._findTarget( + moduleGraph, + validTargetModuleFilter, + alreadyVisited + ); + if (!newTarget) return false; + if (target.export.length === 1) { + target = newTarget; + } else { + target = { + module: newTarget.module, + export: newTarget.export + ? newTarget.export.concat(target.export.slice(1)) + : target.export.slice(1) + }; + } + } + } + /** + * @param {ModuleGraph} moduleGraph the module graph + * @param {function({ module: Module, export: string[] | undefined }): boolean} resolveTargetFilter filter function to further resolve target + * @returns {{ module: Module, export: string[] | undefined } | undefined} the target + */ + getTarget(moduleGraph, resolveTargetFilter = RETURNS_TRUE) { + const result = this._getTarget(moduleGraph, resolveTargetFilter, undefined); + if (result === CIRCULAR) return undefined; + return result; + } -const WebpackError = __webpack_require__(68422); -const makeSerializable = __webpack_require__(26522); + /** + * @param {ModuleGraph} moduleGraph the module graph + * @param {function({ module: Module, connection: ModuleGraphConnection, export: string[] | undefined }): boolean} resolveTargetFilter filter function to further resolve target + * @param {Set | undefined} alreadyVisited set of already visited export info to avoid circular references + * @returns {{ module: Module, connection: ModuleGraphConnection, export: string[] | undefined } | CIRCULAR | undefined} the target + */ + _getTarget(moduleGraph, resolveTargetFilter, alreadyVisited) { + /** + * @param {{ connection: ModuleGraphConnection, export: string[] | undefined } | null} inputTarget unresolved target + * @param {Set} alreadyVisited set of already visited export info to avoid circular references + * @returns {{ module: Module, connection: ModuleGraphConnection, export: string[] | undefined } | CIRCULAR | null} resolved target + */ + const resolveTarget = (inputTarget, alreadyVisited) => { + if (!inputTarget) return null; + if (!inputTarget.export) { + return { + module: inputTarget.connection.module, + connection: inputTarget.connection, + export: undefined + }; + } + /** @type {{ module: Module, connection: ModuleGraphConnection, export: string[] | undefined }} */ + let target = { + module: inputTarget.connection.module, + connection: inputTarget.connection, + export: inputTarget.export + }; + if (!resolveTargetFilter(target)) return target; + let alreadyVisitedOwned = false; + for (;;) { + const exportsInfo = moduleGraph.getExportsInfo(target.module); + const exportInfo = exportsInfo.getExportInfo(target.export[0]); + if (!exportInfo) return target; + if (alreadyVisited.has(exportInfo)) return CIRCULAR; + const newTarget = exportInfo._getTarget( + moduleGraph, + resolveTargetFilter, + alreadyVisited + ); + if (newTarget === CIRCULAR) return CIRCULAR; + if (!newTarget) return target; + if (target.export.length === 1) { + target = newTarget; + if (!target.export) return target; + } else { + target = { + module: newTarget.module, + connection: newTarget.connection, + export: newTarget.export + ? newTarget.export.concat(target.export.slice(1)) + : target.export.slice(1) + }; + } + if (!resolveTargetFilter(target)) return target; + if (!alreadyVisitedOwned) { + alreadyVisited = new Set(alreadyVisited); + alreadyVisitedOwned = true; + } + alreadyVisited.add(exportInfo); + } + }; -/** @typedef {import("./Dependency").DependencyLocation} DependencyLocation */ -/** @typedef {import("./Module")} Module */ + if (!this._target || this._target.size === 0) return undefined; + if (alreadyVisited && alreadyVisited.has(this)) return CIRCULAR; + const newAlreadyVisited = new Set(alreadyVisited); + newAlreadyVisited.add(this); + const values = this._getMaxTarget().values(); + const target = resolveTarget(values.next().value, newAlreadyVisited); + if (target === CIRCULAR) return CIRCULAR; + if (target === null) return undefined; + let result = values.next(); + while (!result.done) { + const t = resolveTarget(result.value, newAlreadyVisited); + if (t === CIRCULAR) return CIRCULAR; + if (t === null) return undefined; + if (t.module !== target.module) return undefined; + if (!t.export !== !target.export) return undefined; + if (target.export && !equals(t.export, target.export)) return undefined; + result = values.next(); + } + return target; + } -class InvalidDependenciesModuleWarning extends WebpackError { /** - * @param {Module} module module tied to dependency - * @param {Iterable} deps invalid dependencies + * Move the target forward as long resolveTargetFilter is fulfilled + * @param {ModuleGraph} moduleGraph the module graph + * @param {function({ module: Module, export: string[] | undefined }): boolean} resolveTargetFilter filter function to further resolve target + * @param {function({ module: Module, export: string[] | undefined }): ModuleGraphConnection=} updateOriginalConnection updates the original connection instead of using the target connection + * @returns {{ module: Module, export: string[] | undefined } | undefined} the resolved target when moved */ - constructor(module, deps) { - const orderedDeps = deps ? Array.from(deps).sort() : []; - const depsList = orderedDeps.map(dep => ` * ${JSON.stringify(dep)}`); - super(`Invalid dependencies have been reported by plugins or loaders for this module. All reported dependencies need to be absolute paths. -Invalid dependencies may lead to broken watching and caching. -As best effort we try to convert all invalid values to absolute paths and converting globs into context dependencies, but this is deprecated behavior. -Loaders: Pass absolute paths to this.addDependency (existing files), this.addMissingDependency (not existing files), and this.addContextDependency (directories). -Plugins: Pass absolute paths to fileDependencies (existing files), missingDependencies (not existing files), and contextDependencies (directories). -Globs: They are not supported. Pass absolute path to the directory as context dependencies. -The following invalid values have been reported: -${depsList.slice(0, 3).join("\n")}${ - depsList.length > 3 ? "\n * and more ..." : "" - }`); + moveTarget(moduleGraph, resolveTargetFilter, updateOriginalConnection) { + const target = this._getTarget(moduleGraph, resolveTargetFilter, undefined); + if (target === CIRCULAR) return undefined; + if (!target) return undefined; + const originalTarget = this._getMaxTarget().values().next().value; + if ( + originalTarget.connection === target.connection && + originalTarget.export === target.export + ) { + return undefined; + } + this._target.clear(); + this._target.set(undefined, { + connection: updateOriginalConnection + ? updateOriginalConnection(target) + : target.connection, + export: target.export, + priority: 0 + }); + return target; + } - this.name = "InvalidDependenciesModuleWarning"; - this.details = depsList.slice(3).join("\n"); - this.module = module; + createNestedExportsInfo() { + if (this.exportsInfoOwned) return this.exportsInfo; + this.exportsInfoOwned = true; + const oldExportsInfo = this.exportsInfo; + this.exportsInfo = new ExportsInfo(); + this.exportsInfo.setHasProvideInfo(); + if (oldExportsInfo) { + this.exportsInfo.setRedirectNamedTo(oldExportsInfo); + } + return this.exportsInfo; } -} -makeSerializable( - InvalidDependenciesModuleWarning, - "webpack/lib/InvalidDependenciesModuleWarning" -); + getNestedExportsInfo() { + return this.exportsInfo; + } -module.exports = InvalidDependenciesModuleWarning; + hasInfo(baseInfo, runtime) { + return ( + (this._usedName && this._usedName !== this.name) || + this.provided || + this.terminalBinding || + this.getUsed(runtime) !== baseInfo.getUsed(runtime) + ); + } + + updateHash(hash, runtime) { + this._updateHash(hash, runtime, new Set()); + } + + _updateHash(hash, runtime, alreadyVisitedExportsInfo) { + hash.update( + `${this._usedName || this.name}${this.getUsed(runtime)}${this.provided}${ + this.terminalBinding + }` + ); + if (this.exportsInfo && !alreadyVisitedExportsInfo.has(this.exportsInfo)) { + this.exportsInfo._updateHash(hash, runtime, alreadyVisitedExportsInfo); + } + } + + getUsedInfo() { + if (this._globalUsed !== undefined) { + switch (this._globalUsed) { + case UsageState.Unused: + return "unused"; + case UsageState.NoInfo: + return "no usage info"; + case UsageState.Unknown: + return "maybe used (runtime-defined)"; + case UsageState.Used: + return "used"; + case UsageState.OnlyPropertiesUsed: + return "only properties used"; + } + } else if (this._usedInRuntime !== undefined) { + /** @type {Map} */ + const map = new Map(); + for (const [runtime, used] of this._usedInRuntime) { + const list = map.get(used); + if (list !== undefined) list.push(runtime); + else map.set(used, [runtime]); + } + const specificInfo = Array.from(map, ([used, runtimes]) => { + switch (used) { + case UsageState.NoInfo: + return `no usage info in ${runtimes.join(", ")}`; + case UsageState.Unknown: + return `maybe used in ${runtimes.join(", ")} (runtime-defined)`; + case UsageState.Used: + return `used in ${runtimes.join(", ")}`; + case UsageState.OnlyPropertiesUsed: + return `only properties used in ${runtimes.join(", ")}`; + } + }); + if (specificInfo.length > 0) { + return specificInfo.join("; "); + } + } + return this._hasUseInRuntimeInfo ? "unused" : "no usage info"; + } + + getProvidedInfo() { + switch (this.provided) { + case undefined: + return "no provided info"; + case null: + return "maybe provided (runtime-defined)"; + case true: + return "provided"; + case false: + return "not provided"; + } + } + + getRenameInfo() { + if (this._usedName !== null && this._usedName !== this.name) { + return `renamed to ${JSON.stringify(this._usedName).slice(1, -1)}`; + } + switch (this.canMangleProvide) { + case undefined: + switch (this.canMangleUse) { + case undefined: + return "missing provision and use info prevents renaming"; + case false: + return "usage prevents renaming (no provision info)"; + case true: + return "missing provision info prevents renaming"; + } + break; + case true: + switch (this.canMangleUse) { + case undefined: + return "missing usage info prevents renaming"; + case false: + return "usage prevents renaming"; + case true: + return "could be renamed"; + } + break; + case false: + switch (this.canMangleUse) { + case undefined: + return "provision prevents renaming (no use info)"; + case false: + return "usage and provision prevents renaming"; + case true: + return "provision prevents renaming"; + } + break; + } + throw new Error( + `Unexpected flags for getRenameInfo ${this.canMangleProvide} ${this.canMangleUse}` + ); + } +} + +module.exports = ExportsInfo; +module.exports.ExportInfo = ExportInfo; +module.exports.UsageState = UsageState; /***/ }), -/***/ 38197: +/***/ 75529: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; /* MIT License http://www.opensource.org/licenses/mit-license.php - Author Sergey Melyukov @smelukov + Author Tobias Koppers @sokra */ -const InnerGraph = __webpack_require__(92886); +const ConstDependency = __webpack_require__(60864); +const ExportsInfoDependency = __webpack_require__(30474); /** @typedef {import("./Compiler")} Compiler */ /** @typedef {import("./javascript/JavascriptParser")} JavascriptParser */ -class JavascriptMetaInfoPlugin { +class ExportsInfoApiPlugin { /** * Apply the plugin * @param {Compiler} compiler the compiler instance @@ -48458,59 +43246,61 @@ class JavascriptMetaInfoPlugin { */ apply(compiler) { compiler.hooks.compilation.tap( - "JavascriptMetaInfoPlugin", + "ExportsInfoApiPlugin", (compilation, { normalModuleFactory }) => { + compilation.dependencyTemplates.set( + ExportsInfoDependency, + new ExportsInfoDependency.Template() + ); /** * @param {JavascriptParser} parser the parser * @returns {void} */ const handler = parser => { - parser.hooks.call.for("eval").tap("JavascriptMetaInfoPlugin", () => { - parser.state.module.buildInfo.moduleConcatenationBailout = "eval()"; - parser.state.module.buildInfo.usingEval = true; - const currentSymbol = InnerGraph.getTopLevelSymbol(parser.state); - if (currentSymbol) { - InnerGraph.addUsage(parser.state, null, currentSymbol); - } else { - InnerGraph.bailout(parser.state); - } - }); - parser.hooks.finish.tap("JavascriptMetaInfoPlugin", () => { - let topLevelDeclarations = - parser.state.module.buildInfo.topLevelDeclarations; - if (topLevelDeclarations === undefined) { - topLevelDeclarations = - parser.state.module.buildInfo.topLevelDeclarations = new Set(); - } - for (const name of parser.scope.definitions.asSet()) { - const freeInfo = parser.getFreeInfoFromVariable(name); - if (freeInfo === undefined) { - topLevelDeclarations.add(name); - } - } - }); + parser.hooks.expressionMemberChain + .for("__webpack_exports_info__") + .tap("ExportsInfoApiPlugin", (expr, members) => { + const dep = + members.length >= 2 + ? new ExportsInfoDependency( + expr.range, + members.slice(0, -1), + members[members.length - 1] + ) + : new ExportsInfoDependency(expr.range, null, members[0]); + dep.loc = expr.loc; + parser.state.module.addDependency(dep); + return true; + }); + parser.hooks.expression + .for("__webpack_exports_info__") + .tap("ExportsInfoApiPlugin", expr => { + const dep = new ConstDependency("true", expr.range); + dep.loc = expr.loc; + parser.state.module.addPresentationalDependency(dep); + return true; + }); }; - normalModuleFactory.hooks.parser .for("javascript/auto") - .tap("JavascriptMetaInfoPlugin", handler); + .tap("ExportsInfoApiPlugin", handler); normalModuleFactory.hooks.parser .for("javascript/dynamic") - .tap("JavascriptMetaInfoPlugin", handler); + .tap("ExportsInfoApiPlugin", handler); normalModuleFactory.hooks.parser .for("javascript/esm") - .tap("JavascriptMetaInfoPlugin", handler); + .tap("ExportsInfoApiPlugin", handler); } ); } } -module.exports = JavascriptMetaInfoPlugin; +module.exports = ExportsInfoApiPlugin; /***/ }), -/***/ 30711: +/***/ 89805: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; @@ -48521,299 +43311,722 @@ module.exports = JavascriptMetaInfoPlugin; -const asyncLib = __webpack_require__(36386); -const EntryDependency = __webpack_require__(41075); -const { someInIterable } = __webpack_require__(31065); -const { compareModulesById } = __webpack_require__(26296); -const { dirname, mkdirp } = __webpack_require__(93204); +const { OriginalSource, RawSource } = __webpack_require__(96192); +const ConcatenationScope = __webpack_require__(14067); +const { UsageState } = __webpack_require__(4295); +const InitFragment = __webpack_require__(51739); +const Module = __webpack_require__(85887); +const RuntimeGlobals = __webpack_require__(49404); +const Template = __webpack_require__(92066); +const StaticExportsDependency = __webpack_require__(67967); +const createHash = __webpack_require__(24123); +const extractUrlAndGlobal = __webpack_require__(31670); +const makeSerializable = __webpack_require__(26522); +const propertyAccess = __webpack_require__(86709); +const { register } = __webpack_require__(99551); -/** @typedef {import("./Compiler")} Compiler */ +/** @typedef {import("webpack-sources").Source} Source */ +/** @typedef {import("../declarations/WebpackOptions").WebpackOptionsNormalized} WebpackOptions */ +/** @typedef {import("./Chunk")} Chunk */ +/** @typedef {import("./ChunkGraph")} ChunkGraph */ +/** @typedef {import("./Compilation")} Compilation */ +/** @typedef {import("./Dependency").UpdateHashContext} UpdateHashContext */ +/** @typedef {import("./DependencyTemplates")} DependencyTemplates */ +/** @typedef {import("./ExportsInfo")} ExportsInfo */ +/** @typedef {import("./Module").CodeGenerationContext} CodeGenerationContext */ +/** @typedef {import("./Module").CodeGenerationResult} CodeGenerationResult */ +/** @typedef {import("./Module").ConcatenationBailoutReasonContext} ConcatenationBailoutReasonContext */ +/** @typedef {import("./Module").LibIdentOptions} LibIdentOptions */ +/** @typedef {import("./Module").NeedBuildContext} NeedBuildContext */ +/** @typedef {import("./NormalModuleFactory")} NormalModuleFactory */ +/** @typedef {import("./RequestShortener")} RequestShortener */ +/** @typedef {import("./ResolverFactory").ResolverWithOptions} ResolverWithOptions */ +/** @typedef {import("./RuntimeTemplate")} RuntimeTemplate */ +/** @typedef {import("./WebpackError")} WebpackError */ +/** @typedef {import("./javascript/JavascriptModulesPlugin").ChunkRenderContext} ChunkRenderContext */ +/** @typedef {import("./util/Hash")} Hash */ +/** @typedef {typeof import("./util/Hash")} HashConstructor */ +/** @typedef {import("./util/fs").InputFileSystem} InputFileSystem */ +/** @typedef {import("./util/runtime").RuntimeSpec} RuntimeSpec */ /** - * @typedef {Object} ManifestModuleData - * @property {string | number} id - * @property {Object} buildMeta - * @property {boolean | string[]} exports + * @typedef {Object} SourceData + * @property {boolean=} iife + * @property {string=} init + * @property {string} expression + * @property {InitFragment[]=} chunkInitFragments + * @property {ReadonlySet=} runtimeRequirements */ -class LibManifestPlugin { - constructor(options) { - this.options = options; - } +const TYPES = new Set(["javascript"]); +const RUNTIME_REQUIREMENTS = new Set([RuntimeGlobals.module]); +const RUNTIME_REQUIREMENTS_FOR_SCRIPT = new Set([RuntimeGlobals.loadScript]); +const RUNTIME_REQUIREMENTS_FOR_MODULE = new Set([ + RuntimeGlobals.definePropertyGetters +]); +const EMPTY_RUNTIME_REQUIREMENTS = new Set([]); - /** - * Apply the plugin - * @param {Compiler} compiler the compiler instance - * @returns {void} - */ - apply(compiler) { - compiler.hooks.emit.tapAsync( - "LibManifestPlugin", - (compilation, callback) => { - const moduleGraph = compilation.moduleGraph; - asyncLib.forEach( - Array.from(compilation.chunks), - (chunk, callback) => { - if (!chunk.canBeInitial()) { - callback(); - return; - } - const chunkGraph = compilation.chunkGraph; - const targetPath = compilation.getPath(this.options.path, { - chunk - }); - const name = - this.options.name && - compilation.getPath(this.options.name, { - chunk - }); - const content = Object.create(null); - for (const module of chunkGraph.getOrderedChunkModulesIterable( - chunk, - compareModulesById(chunkGraph) - )) { - if ( - this.options.entryOnly && - !someInIterable( - moduleGraph.getIncomingConnections(module), - c => c.dependency instanceof EntryDependency - ) - ) { - continue; - } - const ident = module.libIdent({ - context: this.options.context || compiler.options.context, - associatedObjectForCache: compiler.root - }); - if (ident) { - const exportsInfo = moduleGraph.getExportsInfo(module); - const providedExports = exportsInfo.getProvidedExports(); - /** @type {ManifestModuleData} */ - const data = { - id: chunkGraph.getModuleId(module), - buildMeta: module.buildMeta, - exports: Array.isArray(providedExports) - ? providedExports - : undefined - }; - content[ident] = data; - } - } - const manifest = { - name, - type: this.options.type, - content - }; - // Apply formatting to content if format flag is true; - const manifestContent = this.options.format - ? JSON.stringify(manifest, null, 2) - : JSON.stringify(manifest); - const buffer = Buffer.from(manifestContent, "utf8"); - mkdirp( - compiler.intermediateFileSystem, - dirname(compiler.intermediateFileSystem, targetPath), - err => { - if (err) return callback(err); - compiler.intermediateFileSystem.writeFile( - targetPath, - buffer, - callback - ); - } - ); - }, - callback - ); - } - ); +/** + * @param {string|string[]} variableName the variable name or path + * @param {string} type the module system + * @returns {SourceData} the generated source + */ +const getSourceForGlobalVariableExternal = (variableName, type) => { + if (!Array.isArray(variableName)) { + // make it an array as the look up works the same basically + variableName = [variableName]; } -} -module.exports = LibManifestPlugin; - - -/***/ }), - -/***/ 81735: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ - + // needed for e.g. window["some"]["thing"] + const objectLookup = variableName.map(r => `[${JSON.stringify(r)}]`).join(""); + return { + iife: type === "this", + expression: `${type}${objectLookup}` + }; +}; -const EnableLibraryPlugin = __webpack_require__(35613); +/** + * @param {string|string[]} moduleAndSpecifiers the module request + * @returns {SourceData} the generated source + */ +const getSourceForCommonJsExternal = moduleAndSpecifiers => { + if (!Array.isArray(moduleAndSpecifiers)) { + return { + expression: `require(${JSON.stringify(moduleAndSpecifiers)})` + }; + } + const moduleName = moduleAndSpecifiers[0]; + return { + expression: `require(${JSON.stringify(moduleName)})${propertyAccess( + moduleAndSpecifiers, + 1 + )}` + }; +}; -/** @typedef {import("../declarations/WebpackOptions").AuxiliaryComment} AuxiliaryComment */ -/** @typedef {import("../declarations/WebpackOptions").LibraryExport} LibraryExport */ -/** @typedef {import("../declarations/WebpackOptions").LibraryName} LibraryName */ -/** @typedef {import("../declarations/WebpackOptions").LibraryType} LibraryType */ -/** @typedef {import("../declarations/WebpackOptions").UmdNamedDefine} UmdNamedDefine */ -/** @typedef {import("./Compiler")} Compiler */ +/** + * @param {string|string[]} moduleAndSpecifiers the module request + * @returns {SourceData} the generated source + */ +const getSourceForCommonJsExternalInNodeModule = moduleAndSpecifiers => { + const chunkInitFragments = [ + new InitFragment( + 'import { createRequire as __WEBPACK_EXTERNAL_createRequire } from "module";\n', + InitFragment.STAGE_HARMONY_IMPORTS, + 0, + "external module node-commonjs" + ) + ]; + if (!Array.isArray(moduleAndSpecifiers)) { + return { + expression: `__WEBPACK_EXTERNAL_createRequire(import.meta.url)(${JSON.stringify( + moduleAndSpecifiers + )})`, + chunkInitFragments + }; + } + const moduleName = moduleAndSpecifiers[0]; + return { + expression: `__WEBPACK_EXTERNAL_createRequire(import.meta.url)(${JSON.stringify( + moduleName + )})${propertyAccess(moduleAndSpecifiers, 1)}`, + chunkInitFragments + }; +}; -// TODO webpack 6 remove -class LibraryTemplatePlugin { - /** - * @param {LibraryName} name name of library - * @param {LibraryType} target type of library - * @param {UmdNamedDefine} umdNamedDefine setting this to true will name the UMD module - * @param {AuxiliaryComment} auxiliaryComment comment in the UMD wrapper - * @param {LibraryExport} exportProperty which export should be exposed as library - */ - constructor(name, target, umdNamedDefine, auxiliaryComment, exportProperty) { - this.library = { - type: target || "var", - name, - umdNamedDefine, - auxiliaryComment, - export: exportProperty +/** + * @param {string|string[]} moduleAndSpecifiers the module request + * @param {RuntimeTemplate} runtimeTemplate the runtime template + * @returns {SourceData} the generated source + */ +const getSourceForImportExternal = (moduleAndSpecifiers, runtimeTemplate) => { + const importName = runtimeTemplate.outputOptions.importFunctionName; + if (!runtimeTemplate.supportsDynamicImport() && importName === "import") { + throw new Error( + "The target environment doesn't support 'import()' so it's not possible to use external type 'import'" + ); + } + if (!Array.isArray(moduleAndSpecifiers)) { + return { + expression: `${importName}(${JSON.stringify(moduleAndSpecifiers)});` + }; + } + if (moduleAndSpecifiers.length === 1) { + return { + expression: `${importName}(${JSON.stringify(moduleAndSpecifiers[0])});` }; } + const moduleName = moduleAndSpecifiers[0]; + return { + expression: `${importName}(${JSON.stringify( + moduleName + )}).then(${runtimeTemplate.returningFunction( + `module${propertyAccess(moduleAndSpecifiers, 1)}`, + "module" + )});` + }; +}; +class ModuleExternalInitFragment extends InitFragment { /** - * Apply the plugin - * @param {Compiler} compiler the compiler instance - * @returns {void} + * @param {string} request import source + * @param {string=} ident recomputed ident + * @param {string | HashConstructor=} hashFunction the hash function to use */ - apply(compiler) { - const { output } = compiler.options; - output.library = this.library; - new EnableLibraryPlugin(this.library.type).apply(compiler); + constructor(request, ident, hashFunction = "md4") { + if (ident === undefined) { + ident = Template.toIdentifier(request); + if (ident !== request) { + ident += `_${createHash(hashFunction) + .update(request) + .digest("hex") + .slice(0, 8)}`; + } + } + const identifier = `__WEBPACK_EXTERNAL_MODULE_${ident}__`; + super( + `import * as ${identifier} from ${JSON.stringify(request)};\n`, + InitFragment.STAGE_HARMONY_IMPORTS, + 0, + `external module import ${ident}` + ); + this._ident = ident; + this._identifier = identifier; + this._request = request; } -} - -module.exports = LibraryTemplatePlugin; - - -/***/ }), - -/***/ 73047: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ - + getNamespaceIdentifier() { + return this._identifier; + } +} -const ModuleFilenameHelpers = __webpack_require__(80295); -const NormalModule = __webpack_require__(11026); -const createSchemaValidation = __webpack_require__(77695); - -/** @typedef {import("../declarations/plugins/LoaderOptionsPlugin").LoaderOptionsPluginOptions} LoaderOptionsPluginOptions */ -/** @typedef {import("./Compiler")} Compiler */ - -const validate = createSchemaValidation( - __webpack_require__(36012), - () => __webpack_require__(56086), +register( + ModuleExternalInitFragment, + "webpack/lib/ExternalModule", + "ModuleExternalInitFragment", { - name: "Loader Options Plugin", - baseDataPath: "options" - } -); -class LoaderOptionsPlugin { - /** - * @param {LoaderOptionsPluginOptions} options options object - */ - constructor(options = {}) { - validate(options); - if (typeof options !== "object") options = {}; - if (!options.test) { - options.test = { - test: () => true - }; + serialize(obj, { write }) { + write(obj._request); + write(obj._ident); + }, + deserialize({ read }) { + return new ModuleExternalInitFragment(read(), read()); } - this.options = options; } +); - /** - * Apply the plugin - * @param {Compiler} compiler the compiler instance - * @returns {void} - */ - apply(compiler) { - const options = this.options; - compiler.hooks.compilation.tap("LoaderOptionsPlugin", compilation => { - NormalModule.getCompilationHooks(compilation).loader.tap( - "LoaderOptionsPlugin", - (context, module) => { - const resource = module.resource; - if (!resource) return; - const i = resource.indexOf("?"); - if ( - ModuleFilenameHelpers.matchObject( - options, - i < 0 ? resource : resource.substr(0, i) - ) - ) { - for (const key of Object.keys(options)) { - if (key === "include" || key === "exclude" || key === "test") { - continue; - } - context[key] = options[key]; - } - } +const generateModuleRemapping = (input, exportsInfo, runtime) => { + if (exportsInfo.otherExportsInfo.getUsed(runtime) === UsageState.Unused) { + const properties = []; + for (const exportInfo of exportsInfo.orderedExports) { + const used = exportInfo.getUsedName(exportInfo.name, runtime); + if (!used) continue; + const nestedInfo = exportInfo.getNestedExportsInfo(); + if (nestedInfo) { + const nestedExpr = generateModuleRemapping( + `${input}${propertyAccess([exportInfo.name])}`, + nestedInfo + ); + if (nestedExpr) { + properties.push(`[${JSON.stringify(used)}]: y(${nestedExpr})`); + continue; } + } + properties.push( + `[${JSON.stringify(used)}]: () => ${input}${propertyAccess([ + exportInfo.name + ])}` ); - }); + } + return `x({ ${properties.join(", ")} })`; } -} - -module.exports = LoaderOptionsPlugin; - - -/***/ }), - -/***/ 94834: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ - - - -const NormalModule = __webpack_require__(11026); - -/** @typedef {import("./Compiler")} Compiler */ +}; -class LoaderTargetPlugin { - /** - * @param {string} target the target - */ - constructor(target) { - this.target = target; - } +/** + * @param {string|string[]} moduleAndSpecifiers the module request + * @param {ExportsInfo} exportsInfo exports info of this module + * @param {RuntimeSpec} runtime the runtime + * @param {string | HashConstructor=} hashFunction the hash function to use + * @returns {SourceData} the generated source + */ +const getSourceForModuleExternal = ( + moduleAndSpecifiers, + exportsInfo, + runtime, + hashFunction +) => { + if (!Array.isArray(moduleAndSpecifiers)) + moduleAndSpecifiers = [moduleAndSpecifiers]; + const initFragment = new ModuleExternalInitFragment( + moduleAndSpecifiers[0], + undefined, + hashFunction + ); + const baseAccess = `${initFragment.getNamespaceIdentifier()}${propertyAccess( + moduleAndSpecifiers, + 1 + )}`; + const moduleRemapping = generateModuleRemapping( + baseAccess, + exportsInfo, + runtime + ); + let expression = moduleRemapping || baseAccess; + return { + expression, + init: `var x = y => { var x = {}; ${RuntimeGlobals.definePropertyGetters}(x, y); return x; }\nvar y = x => () => x`, + runtimeRequirements: moduleRemapping + ? RUNTIME_REQUIREMENTS_FOR_MODULE + : undefined, + chunkInitFragments: [initFragment] + }; +}; + +/** + * @param {string|string[]} urlAndGlobal the script request + * @param {RuntimeTemplate} runtimeTemplate the runtime template + * @returns {SourceData} the generated source + */ +const getSourceForScriptExternal = (urlAndGlobal, runtimeTemplate) => { + if (typeof urlAndGlobal === "string") { + urlAndGlobal = extractUrlAndGlobal(urlAndGlobal); + } + const url = urlAndGlobal[0]; + const globalName = urlAndGlobal[1]; + return { + init: "var __webpack_error__ = new Error();", + expression: `new Promise(${runtimeTemplate.basicFunction( + "resolve, reject", + [ + `if(typeof ${globalName} !== "undefined") return resolve();`, + `${RuntimeGlobals.loadScript}(${JSON.stringify( + url + )}, ${runtimeTemplate.basicFunction("event", [ + `if(typeof ${globalName} !== "undefined") return resolve();`, + "var errorType = event && (event.type === 'load' ? 'missing' : event.type);", + "var realSrc = event && event.target && event.target.src;", + "__webpack_error__.message = 'Loading script failed.\\n(' + errorType + ': ' + realSrc + ')';", + "__webpack_error__.name = 'ScriptExternalLoadError';", + "__webpack_error__.type = errorType;", + "__webpack_error__.request = realSrc;", + "reject(__webpack_error__);" + ])}, ${JSON.stringify(globalName)});` + ] + )}).then(${runtimeTemplate.returningFunction( + `${globalName}${propertyAccess(urlAndGlobal, 2)}` + )})`, + runtimeRequirements: RUNTIME_REQUIREMENTS_FOR_SCRIPT + }; +}; + +/** + * @param {string} variableName the variable name to check + * @param {string} request the request path + * @param {RuntimeTemplate} runtimeTemplate the runtime template + * @returns {string} the generated source + */ +const checkExternalVariable = (variableName, request, runtimeTemplate) => { + return `if(typeof ${variableName} === 'undefined') { ${runtimeTemplate.throwMissingModuleErrorBlock( + { request } + )} }\n`; +}; + +/** + * @param {string|number} id the module id + * @param {boolean} optional true, if the module is optional + * @param {string|string[]} request the request path + * @param {RuntimeTemplate} runtimeTemplate the runtime template + * @returns {SourceData} the generated source + */ +const getSourceForAmdOrUmdExternal = ( + id, + optional, + request, + runtimeTemplate +) => { + const externalVariable = `__WEBPACK_EXTERNAL_MODULE_${Template.toIdentifier( + `${id}` + )}__`; + return { + init: optional + ? checkExternalVariable( + externalVariable, + Array.isArray(request) ? request.join(".") : request, + runtimeTemplate + ) + : undefined, + expression: externalVariable + }; +}; + +/** + * @param {boolean} optional true, if the module is optional + * @param {string|string[]} request the request path + * @param {RuntimeTemplate} runtimeTemplate the runtime template + * @returns {SourceData} the generated source + */ +const getSourceForDefaultCase = (optional, request, runtimeTemplate) => { + if (!Array.isArray(request)) { + // make it an array as the look up works the same basically + request = [request]; + } + + const variableName = request[0]; + const objectLookup = propertyAccess(request, 1); + return { + init: optional + ? checkExternalVariable(variableName, request.join("."), runtimeTemplate) + : undefined, + expression: `${variableName}${objectLookup}` + }; +}; + +class ExternalModule extends Module { + constructor(request, type, userRequest) { + super("javascript/dynamic", null); + + // Info from Factory + /** @type {string | string[] | Record} */ + this.request = request; + /** @type {string} */ + this.externalType = type; + /** @type {string} */ + this.userRequest = userRequest; + } /** - * Apply the plugin - * @param {Compiler} compiler the compiler instance + * @returns {Set} types available (do not mutate) + */ + getSourceTypes() { + return TYPES; + } + + /** + * @param {LibIdentOptions} options options + * @returns {string | null} an identifier for library inclusion + */ + libIdent(options) { + return this.userRequest; + } + + /** + * @param {Chunk} chunk the chunk which condition should be checked + * @param {Compilation} compilation the compilation + * @returns {boolean} true, if the chunk is ok for the module + */ + chunkCondition(chunk, { chunkGraph }) { + return chunkGraph.getNumberOfEntryModules(chunk) > 0; + } + + /** + * @returns {string} a unique identifier of the module + */ + identifier() { + return `external ${this.externalType} ${JSON.stringify(this.request)}`; + } + + /** + * @param {RequestShortener} requestShortener the request shortener + * @returns {string} a user readable identifier of the module + */ + readableIdentifier(requestShortener) { + return "external " + JSON.stringify(this.request); + } + + /** + * @param {NeedBuildContext} context context info + * @param {function(WebpackError=, boolean=): void} callback callback function, returns true, if the module needs a rebuild * @returns {void} */ - apply(compiler) { - compiler.hooks.compilation.tap("LoaderTargetPlugin", compilation => { - NormalModule.getCompilationHooks(compilation).loader.tap( - "LoaderTargetPlugin", - loaderContext => { - loaderContext.target = this.target; + needBuild(context, callback) { + return callback(null, !this.buildMeta); + } + + /** + * @param {WebpackOptions} options webpack options + * @param {Compilation} compilation the compilation + * @param {ResolverWithOptions} resolver the resolver + * @param {InputFileSystem} fs the file system + * @param {function(WebpackError=): void} callback callback function + * @returns {void} + */ + build(options, compilation, resolver, fs, callback) { + this.buildMeta = { + async: false, + exportsType: undefined + }; + this.buildInfo = { + strict: true, + topLevelDeclarations: new Set(), + module: compilation.outputOptions.module + }; + const { request, externalType } = this._getRequestAndExternalType(); + this.buildMeta.exportsType = "dynamic"; + let canMangle = false; + this.clearDependenciesAndBlocks(); + switch (externalType) { + case "this": + this.buildInfo.strict = false; + break; + case "system": + if (!Array.isArray(request) || request.length === 1) { + this.buildMeta.exportsType = "namespace"; + canMangle = true; + } + break; + case "module": + if (this.buildInfo.module) { + if (!Array.isArray(request) || request.length === 1) { + this.buildMeta.exportsType = "namespace"; + canMangle = true; + } + } else { + this.buildMeta.async = true; + if (!Array.isArray(request) || request.length === 1) { + this.buildMeta.exportsType = "namespace"; + canMangle = false; + } + } + break; + case "script": + case "promise": + this.buildMeta.async = true; + break; + case "import": + this.buildMeta.async = true; + if (!Array.isArray(request) || request.length === 1) { + this.buildMeta.exportsType = "namespace"; + canMangle = false; + } + break; + } + this.addDependency(new StaticExportsDependency(true, canMangle)); + callback(); + } + + restoreFromUnsafeCache(unsafeCacheData, normalModuleFactory) { + this._restoreFromUnsafeCache(unsafeCacheData, normalModuleFactory); + } + + /** + * @param {ConcatenationBailoutReasonContext} context context + * @returns {string | undefined} reason why this module can't be concatenated, undefined when it can be concatenated + */ + getConcatenationBailoutReason({ moduleGraph }) { + switch (this.externalType) { + case "amd": + case "amd-require": + case "umd": + case "umd2": + case "system": + case "jsonp": + return `${this.externalType} externals can't be concatenated`; + } + return undefined; + } + + _getRequestAndExternalType() { + let { request, externalType } = this; + if (typeof request === "object" && !Array.isArray(request)) + request = request[externalType]; + return { request, externalType }; + } + + _getSourceData(runtimeTemplate, moduleGraph, chunkGraph, runtime) { + const { request, externalType } = this._getRequestAndExternalType(); + switch (externalType) { + case "this": + case "window": + case "self": + return getSourceForGlobalVariableExternal(request, this.externalType); + case "global": + return getSourceForGlobalVariableExternal( + request, + runtimeTemplate.outputOptions.globalObject + ); + case "commonjs": + case "commonjs2": + case "commonjs-module": + return getSourceForCommonJsExternal(request); + case "node-commonjs": + return this.buildInfo.module + ? getSourceForCommonJsExternalInNodeModule(request) + : getSourceForCommonJsExternal(request); + case "amd": + case "amd-require": + case "umd": + case "umd2": + case "system": + case "jsonp": { + const id = chunkGraph.getModuleId(this); + return getSourceForAmdOrUmdExternal( + id !== null ? id : this.identifier(), + this.isOptional(moduleGraph), + request, + runtimeTemplate + ); + } + case "import": + return getSourceForImportExternal(request, runtimeTemplate); + case "script": + return getSourceForScriptExternal(request, runtimeTemplate); + case "module": { + if (!this.buildInfo.module) { + if (!runtimeTemplate.supportsDynamicImport()) { + throw new Error( + "The target environment doesn't support dynamic import() syntax so it's not possible to use external type 'module' within a script" + + (runtimeTemplate.supportsEcmaScriptModuleSyntax() + ? "\nDid you mean to build a EcmaScript Module ('output.module: true')?" + : "") + ); + } + return getSourceForImportExternal(request, runtimeTemplate); + } + if (!runtimeTemplate.supportsEcmaScriptModuleSyntax()) { + throw new Error( + "The target environment doesn't support EcmaScriptModule syntax so it's not possible to use external type 'module'" + ); } + return getSourceForModuleExternal( + request, + moduleGraph.getExportsInfo(this), + runtime, + runtimeTemplate.outputOptions.hashFunction + ); + } + case "var": + case "promise": + case "const": + case "let": + case "assign": + default: + return getSourceForDefaultCase( + this.isOptional(moduleGraph), + request, + runtimeTemplate + ); + } + } + + /** + * @param {CodeGenerationContext} context context for code generation + * @returns {CodeGenerationResult} result + */ + codeGeneration({ + runtimeTemplate, + moduleGraph, + chunkGraph, + runtime, + concatenationScope + }) { + const sourceData = this._getSourceData( + runtimeTemplate, + moduleGraph, + chunkGraph, + runtime + ); + + let sourceString = sourceData.expression; + if (sourceData.iife) + sourceString = `(function() { return ${sourceString}; }())`; + if (concatenationScope) { + sourceString = `${runtimeTemplate.supportsConst() ? "const" : "var"} ${ + ConcatenationScope.NAMESPACE_OBJECT_EXPORT + } = ${sourceString};`; + concatenationScope.registerNamespaceExport( + ConcatenationScope.NAMESPACE_OBJECT_EXPORT ); - }); + } else { + sourceString = `module.exports = ${sourceString};`; + } + if (sourceData.init) sourceString = `${sourceData.init}\n${sourceString}`; + + let data = undefined; + if (sourceData.chunkInitFragments) { + data = new Map(); + data.set("chunkInitFragments", sourceData.chunkInitFragments); + } + + const sources = new Map(); + if (this.useSourceMap || this.useSimpleSourceMap) { + sources.set( + "javascript", + new OriginalSource(sourceString, this.identifier()) + ); + } else { + sources.set("javascript", new RawSource(sourceString)); + } + + let runtimeRequirements = sourceData.runtimeRequirements; + if (!concatenationScope) { + if (!runtimeRequirements) { + runtimeRequirements = RUNTIME_REQUIREMENTS; + } else { + const set = new Set(runtimeRequirements); + set.add(RuntimeGlobals.module); + runtimeRequirements = set; + } + } + + return { + sources, + runtimeRequirements: runtimeRequirements || EMPTY_RUNTIME_REQUIREMENTS, + data + }; + } + + /** + * @param {string=} type the source type for which the size should be estimated + * @returns {number} the estimated size of the module (must be non-zero) + */ + size(type) { + return 42; + } + + /** + * @param {Hash} hash the hash used to track dependencies + * @param {UpdateHashContext} context context + * @returns {void} + */ + updateHash(hash, context) { + const { chunkGraph } = context; + hash.update( + `${this.externalType}${JSON.stringify(this.request)}${this.isOptional( + chunkGraph.moduleGraph + )}` + ); + super.updateHash(hash, context); + } + + serialize(context) { + const { write } = context; + + write(this.request); + write(this.externalType); + write(this.userRequest); + + super.serialize(context); + } + + deserialize(context) { + const { read } = context; + + this.request = read(); + this.externalType = read(); + this.userRequest = read(); + + super.deserialize(context); } } -module.exports = LoaderTargetPlugin; +makeSerializable(ExternalModule, "webpack/lib/ExternalModule"); + +module.exports = ExternalModule; /***/ }), -/***/ 30518: +/***/ 19364: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; @@ -48824,333 +44037,258 @@ module.exports = LoaderTargetPlugin; -const { SyncWaterfallHook } = __webpack_require__(34718); const util = __webpack_require__(31669); -const RuntimeGlobals = __webpack_require__(49404); -const memoize = __webpack_require__(84297); +const ExternalModule = __webpack_require__(89805); +const { resolveByProperty, cachedSetProperty } = __webpack_require__(11217); -/** @typedef {import("webpack-sources").ConcatSource} ConcatSource */ -/** @typedef {import("webpack-sources").Source} Source */ -/** @typedef {import("../declarations/WebpackOptions").Output} OutputOptions */ -/** @typedef {import("./ModuleTemplate")} ModuleTemplate */ -/** @typedef {import("./Chunk")} Chunk */ -/** @typedef {import("./Compilation")} Compilation */ -/** @typedef {import("./Compilation").AssetInfo} AssetInfo */ -/** @typedef {import("./Module")} Module} */ -/** @typedef {import("./util/Hash")} Hash} */ -/** @typedef {import("./DependencyTemplates")} DependencyTemplates} */ -/** @typedef {import("./javascript/JavascriptModulesPlugin").RenderContext} RenderContext} */ -/** @typedef {import("./RuntimeTemplate")} RuntimeTemplate} */ -/** @typedef {import("./ModuleGraph")} ModuleGraph} */ -/** @typedef {import("./ChunkGraph")} ChunkGraph} */ -/** @typedef {import("./Template").RenderManifestOptions} RenderManifestOptions} */ -/** @typedef {import("./Template").RenderManifestEntry} RenderManifestEntry} */ +/** @typedef {import("../declarations/WebpackOptions").Externals} Externals */ +/** @typedef {import("./NormalModuleFactory")} NormalModuleFactory */ -const getJavascriptModulesPlugin = memoize(() => - __webpack_require__(76767) -); -const getJsonpTemplatePlugin = memoize(() => - __webpack_require__(45968) -); -const getLoadScriptRuntimeModule = memoize(() => - __webpack_require__(80647) +const UNSPECIFIED_EXTERNAL_TYPE_REGEXP = /^[a-z0-9-]+ /; +const EMPTY_RESOLVE_OPTIONS = {}; + +// TODO webpack 6 remove this +const callDeprecatedExternals = util.deprecate( + (externalsFunction, context, request, cb) => { + externalsFunction.call(null, context, request, cb); + }, + "The externals-function should be defined like ({context, request}, cb) => { ... }", + "DEP_WEBPACK_EXTERNALS_FUNCTION_PARAMETERS" ); -// TODO webpack 6 remove this class -class MainTemplate { +const cache = new WeakMap(); + +const resolveLayer = (obj, layer) => { + let map = cache.get(obj); + if (map === undefined) { + map = new Map(); + cache.set(obj, map); + } else { + const cacheEntry = map.get(layer); + if (cacheEntry !== undefined) return cacheEntry; + } + const result = resolveByProperty(obj, "byLayer", layer); + map.set(layer, result); + return result; +}; + +class ExternalModuleFactoryPlugin { /** - * - * @param {OutputOptions} outputOptions output options for the MainTemplate - * @param {Compilation} compilation the compilation + * @param {string | undefined} type default external type + * @param {Externals} externals externals config */ - constructor(outputOptions, compilation) { - /** @type {OutputOptions} */ - this._outputOptions = outputOptions || {}; - this.hooks = Object.freeze({ - renderManifest: { - tap: util.deprecate( - (options, fn) => { - compilation.hooks.renderManifest.tap( - options, - (entries, options) => { - if (!options.chunk.hasRuntime()) return entries; - return fn(entries, options); - } - ); - }, - "MainTemplate.hooks.renderManifest is deprecated (use Compilation.hooks.renderManifest instead)", - "DEP_WEBPACK_MAIN_TEMPLATE_RENDER_MANIFEST" - ) - }, - modules: { - tap: () => { - throw new Error( - "MainTemplate.hooks.modules has been removed (there is no replacement, please create an issue to request that)" - ); - } - }, - moduleObj: { - tap: () => { - throw new Error( - "MainTemplate.hooks.moduleObj has been removed (there is no replacement, please create an issue to request that)" - ); - } - }, - require: { - tap: util.deprecate( - (options, fn) => { - getJavascriptModulesPlugin() - .getCompilationHooks(compilation) - .renderRequire.tap(options, fn); - }, - "MainTemplate.hooks.require is deprecated (use JavascriptModulesPlugin.getCompilationHooks().renderRequire instead)", - "DEP_WEBPACK_MAIN_TEMPLATE_REQUIRE" - ) - }, - beforeStartup: { - tap: () => { - throw new Error( - "MainTemplate.hooks.beforeStartup has been removed (use RuntimeGlobals.startupOnlyBefore instead)" - ); - } - }, - startup: { - tap: () => { - throw new Error( - "MainTemplate.hooks.startup has been removed (use RuntimeGlobals.startup instead)" - ); - } - }, - afterStartup: { - tap: () => { - throw new Error( - "MainTemplate.hooks.afterStartup has been removed (use RuntimeGlobals.startupOnlyAfter instead)" - ); - } - }, - render: { - tap: util.deprecate( - (options, fn) => { - getJavascriptModulesPlugin() - .getCompilationHooks(compilation) - .render.tap(options, (source, renderContext) => { - if ( - renderContext.chunkGraph.getNumberOfEntryModules( - renderContext.chunk - ) === 0 || - !renderContext.chunk.hasRuntime() - ) { - return source; - } - return fn( - source, - renderContext.chunk, - compilation.hash, - compilation.moduleTemplates.javascript, - compilation.dependencyTemplates - ); - }); - }, - "MainTemplate.hooks.render is deprecated (use JavascriptModulesPlugin.getCompilationHooks().render instead)", - "DEP_WEBPACK_MAIN_TEMPLATE_RENDER" - ) - }, - renderWithEntry: { - tap: util.deprecate( - (options, fn) => { - getJavascriptModulesPlugin() - .getCompilationHooks(compilation) - .render.tap(options, (source, renderContext) => { - if ( - renderContext.chunkGraph.getNumberOfEntryModules( - renderContext.chunk - ) === 0 || - !renderContext.chunk.hasRuntime() - ) { - return source; - } - return fn(source, renderContext.chunk, compilation.hash); - }); - }, - "MainTemplate.hooks.renderWithEntry is deprecated (use JavascriptModulesPlugin.getCompilationHooks().render instead)", - "DEP_WEBPACK_MAIN_TEMPLATE_RENDER_WITH_ENTRY" - ) - }, - assetPath: { - tap: util.deprecate( - (options, fn) => { - compilation.hooks.assetPath.tap(options, fn); - }, - "MainTemplate.hooks.assetPath is deprecated (use Compilation.hooks.assetPath instead)", - "DEP_WEBPACK_MAIN_TEMPLATE_ASSET_PATH" - ), - call: util.deprecate( - (filename, options) => { - return compilation.getAssetPath(filename, options); - }, - "MainTemplate.hooks.assetPath is deprecated (use Compilation.hooks.assetPath instead)", - "DEP_WEBPACK_MAIN_TEMPLATE_ASSET_PATH" - ) - }, - hash: { - tap: util.deprecate( - (options, fn) => { - compilation.hooks.fullHash.tap(options, fn); - }, - "MainTemplate.hooks.hash is deprecated (use Compilation.hooks.fullHash instead)", - "DEP_WEBPACK_MAIN_TEMPLATE_HASH" - ) - }, - hashForChunk: { - tap: util.deprecate( - (options, fn) => { - getJavascriptModulesPlugin() - .getCompilationHooks(compilation) - .chunkHash.tap(options, (chunk, hash) => { - if (!chunk.hasRuntime()) return; - return fn(hash, chunk); - }); - }, - "MainTemplate.hooks.hashForChunk is deprecated (use JavascriptModulesPlugin.getCompilationHooks().chunkHash instead)", - "DEP_WEBPACK_MAIN_TEMPLATE_HASH_FOR_CHUNK" - ) - }, - globalHashPaths: { - tap: util.deprecate( - () => {}, - "MainTemplate.hooks.globalHashPaths has been removed (it's no longer needed)", - "DEP_WEBPACK_MAIN_TEMPLATE_HASH_FOR_CHUNK" - ) - }, - globalHash: { - tap: util.deprecate( - () => {}, - "MainTemplate.hooks.globalHash has been removed (it's no longer needed)", - "DEP_WEBPACK_MAIN_TEMPLATE_HASH_FOR_CHUNK" - ) - }, - hotBootstrap: { - tap: () => { - throw new Error( - "MainTemplate.hooks.hotBootstrap has been removed (use your own RuntimeModule instead)" - ); - } - }, + constructor(type, externals) { + this.type = type; + this.externals = externals; + } - // for compatibility: - /** @type {SyncWaterfallHook<[string, Chunk, string, ModuleTemplate, DependencyTemplates]>} */ - bootstrap: new SyncWaterfallHook([ - "source", - "chunk", - "hash", - "moduleTemplate", - "dependencyTemplates" - ]), - /** @type {SyncWaterfallHook<[string, Chunk, string]>} */ - localVars: new SyncWaterfallHook(["source", "chunk", "hash"]), - /** @type {SyncWaterfallHook<[string, Chunk, string]>} */ - requireExtensions: new SyncWaterfallHook(["source", "chunk", "hash"]), - /** @type {SyncWaterfallHook<[string, Chunk, string, string]>} */ - requireEnsure: new SyncWaterfallHook([ - "source", - "chunk", - "hash", - "chunkIdExpression" - ]), - get jsonpScript() { - const hooks = - getLoadScriptRuntimeModule().getCompilationHooks(compilation); - return hooks.createScript; - }, - get linkPrefetch() { - const hooks = getJsonpTemplatePlugin().getCompilationHooks(compilation); - return hooks.linkPrefetch; - }, - get linkPreload() { - const hooks = getJsonpTemplatePlugin().getCompilationHooks(compilation); - return hooks.linkPreload; - } - }); + /** + * @param {NormalModuleFactory} normalModuleFactory the normal module factory + * @returns {void} + */ + apply(normalModuleFactory) { + const globalType = this.type; + normalModuleFactory.hooks.factorize.tapAsync( + "ExternalModuleFactoryPlugin", + (data, callback) => { + const context = data.context; + const contextInfo = data.contextInfo; + const dependency = data.dependencies[0]; + const dependencyType = data.dependencyType; - this.renderCurrentHashCode = util.deprecate( - /** - * @deprecated - * @param {string} hash the hash - * @param {number=} length length of the hash - * @returns {string} generated code - */ (hash, length) => { - if (length) { - return `${RuntimeGlobals.getFullHash} ? ${ - RuntimeGlobals.getFullHash - }().slice(0, ${length}) : ${hash.slice(0, length)}`; - } - return `${RuntimeGlobals.getFullHash} ? ${RuntimeGlobals.getFullHash}() : ${hash}`; - }, - "MainTemplate.renderCurrentHashCode is deprecated (use RuntimeGlobals.getFullHash runtime function instead)", - "DEP_WEBPACK_MAIN_TEMPLATE_RENDER_CURRENT_HASH_CODE" - ); + /** + * @param {string|string[]|boolean|Record} value the external config + * @param {string|undefined} type type of external + * @param {function(Error=, ExternalModule=): void} callback callback + * @returns {void} + */ + const handleExternal = (value, type, callback) => { + if (value === false) { + // Not externals, fallback to original factory + return callback(); + } + /** @type {string | string[] | Record} */ + let externalConfig; + if (value === true) { + externalConfig = dependency.request; + } else { + externalConfig = value; + } + // When no explicit type is specified, extract it from the externalConfig + if (type === undefined) { + if ( + typeof externalConfig === "string" && + UNSPECIFIED_EXTERNAL_TYPE_REGEXP.test(externalConfig) + ) { + const idx = externalConfig.indexOf(" "); + type = externalConfig.substr(0, idx); + externalConfig = externalConfig.substr(idx + 1); + } else if ( + Array.isArray(externalConfig) && + externalConfig.length > 0 && + UNSPECIFIED_EXTERNAL_TYPE_REGEXP.test(externalConfig[0]) + ) { + const firstItem = externalConfig[0]; + const idx = firstItem.indexOf(" "); + type = firstItem.substr(0, idx); + externalConfig = [ + firstItem.substr(idx + 1), + ...externalConfig.slice(1) + ]; + } + } + callback( + null, + new ExternalModule( + externalConfig, + type || globalType, + dependency.request + ) + ); + }; - this.getPublicPath = util.deprecate( - /** - * - * @param {object} options get public path options - * @returns {string} hook call - */ options => { - return compilation.getAssetPath( - compilation.outputOptions.publicPath, - options - ); - }, - "MainTemplate.getPublicPath is deprecated (use Compilation.getAssetPath(compilation.outputOptions.publicPath, options) instead)", - "DEP_WEBPACK_MAIN_TEMPLATE_GET_PUBLIC_PATH" - ); + /** + * @param {Externals} externals externals config + * @param {function(Error=, ExternalModule=): void} callback callback + * @returns {void} + */ + const handleExternals = (externals, callback) => { + if (typeof externals === "string") { + if (externals === dependency.request) { + return handleExternal(dependency.request, undefined, callback); + } + } else if (Array.isArray(externals)) { + let i = 0; + const next = () => { + let asyncFlag; + const handleExternalsAndCallback = (err, module) => { + if (err) return callback(err); + if (!module) { + if (asyncFlag) { + asyncFlag = false; + return; + } + return next(); + } + callback(null, module); + }; - this.getAssetPath = util.deprecate( - (path, options) => { - return compilation.getAssetPath(path, options); - }, - "MainTemplate.getAssetPath is deprecated (use Compilation.getAssetPath instead)", - "DEP_WEBPACK_MAIN_TEMPLATE_GET_ASSET_PATH" - ); + do { + asyncFlag = true; + if (i >= externals.length) return callback(); + handleExternals(externals[i++], handleExternalsAndCallback); + } while (!asyncFlag); + asyncFlag = false; + }; - this.getAssetPathWithInfo = util.deprecate( - (path, options) => { - return compilation.getAssetPathWithInfo(path, options); - }, - "MainTemplate.getAssetPathWithInfo is deprecated (use Compilation.getAssetPath instead)", - "DEP_WEBPACK_MAIN_TEMPLATE_GET_ASSET_PATH_WITH_INFO" + next(); + return; + } else if (externals instanceof RegExp) { + if (externals.test(dependency.request)) { + return handleExternal(dependency.request, undefined, callback); + } + } else if (typeof externals === "function") { + const cb = (err, value, type) => { + if (err) return callback(err); + if (value !== undefined) { + handleExternal(value, type, callback); + } else { + callback(); + } + }; + if (externals.length === 3) { + // TODO webpack 6 remove this + callDeprecatedExternals( + externals, + context, + dependency.request, + cb + ); + } else { + const promise = externals( + { + context, + request: dependency.request, + dependencyType, + contextInfo, + getResolve: options => (context, request, callback) => { + const resolveContext = { + fileDependencies: data.fileDependencies, + missingDependencies: data.missingDependencies, + contextDependencies: data.contextDependencies + }; + let resolver = normalModuleFactory.getResolver( + "normal", + dependencyType + ? cachedSetProperty( + data.resolveOptions || EMPTY_RESOLVE_OPTIONS, + "dependencyType", + dependencyType + ) + : data.resolveOptions + ); + if (options) resolver = resolver.withOptions(options); + if (callback) { + resolver.resolve( + {}, + context, + request, + resolveContext, + callback + ); + } else { + return new Promise((resolve, reject) => { + resolver.resolve( + {}, + context, + request, + resolveContext, + (err, result) => { + if (err) reject(err); + else resolve(result); + } + ); + }); + } + } + }, + cb + ); + if (promise && promise.then) promise.then(r => cb(null, r), cb); + } + return; + } else if (typeof externals === "object") { + const resolvedExternals = resolveLayer( + externals, + contextInfo.issuerLayer + ); + if ( + Object.prototype.hasOwnProperty.call( + resolvedExternals, + dependency.request + ) + ) { + return handleExternal( + resolvedExternals[dependency.request], + undefined, + callback + ); + } + } + callback(); + }; + + handleExternals(this.externals, callback); + } ); } } - -Object.defineProperty(MainTemplate.prototype, "requireFn", { - get: util.deprecate( - () => "__webpack_require__", - 'MainTemplate.requireFn is deprecated (use "__webpack_require__")', - "DEP_WEBPACK_MAIN_TEMPLATE_REQUIRE_FN" - ) -}); - -Object.defineProperty(MainTemplate.prototype, "outputOptions", { - get: util.deprecate( - /** - * @this {MainTemplate} - * @returns {OutputOptions} output options - */ - function () { - return this._outputOptions; - }, - "MainTemplate.outputOptions is deprecated (use Compilation.outputOptions instead)", - "DEP_WEBPACK_MAIN_TEMPLATE_OUTPUT_OPTIONS" - ) -}); - -module.exports = MainTemplate; +module.exports = ExternalModuleFactoryPlugin; /***/ }), -/***/ 85887: +/***/ 361: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; @@ -49161,4489 +44299,3605 @@ module.exports = MainTemplate; -const util = __webpack_require__(31669); -const ChunkGraph = __webpack_require__(97860); -const DependenciesBlock = __webpack_require__(21484); -const ModuleGraph = __webpack_require__(20258); -const RuntimeGlobals = __webpack_require__(49404); -const { first } = __webpack_require__(34715); -const { compareChunksById } = __webpack_require__(26296); +const ExternalModuleFactoryPlugin = __webpack_require__(19364); + +/** @typedef {import("../declarations/WebpackOptions").Externals} Externals */ +/** @typedef {import("./Compiler")} Compiler */ + +class ExternalsPlugin { + /** + * @param {string | undefined} type default external type + * @param {Externals} externals externals config + */ + constructor(type, externals) { + this.type = type; + this.externals = externals; + } + + /** + * Apply the plugin + * @param {Compiler} compiler the compiler instance + * @returns {void} + */ + apply(compiler) { + compiler.hooks.compile.tap("ExternalsPlugin", ({ normalModuleFactory }) => { + new ExternalModuleFactoryPlugin(this.type, this.externals).apply( + normalModuleFactory + ); + }); + } +} + +module.exports = ExternalsPlugin; + + +/***/ }), + +/***/ 13679: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ + + + +const { create: createResolver } = __webpack_require__(27480); +const asyncLib = __webpack_require__(36386); +const AsyncQueue = __webpack_require__(55531); +const StackedCacheMap = __webpack_require__(26009); +const createHash = __webpack_require__(24123); +const { join, dirname, relative, lstatReadlinkAbsolute } = __webpack_require__(93204); const makeSerializable = __webpack_require__(26522); +const processAsyncTree = __webpack_require__(76815); -/** @typedef {import("webpack-sources").Source} Source */ -/** @typedef {import("../declarations/WebpackOptions").ResolveOptions} ResolveOptions */ -/** @typedef {import("../declarations/WebpackOptions").WebpackOptionsNormalized} WebpackOptions */ -/** @typedef {import("./Chunk")} Chunk */ -/** @typedef {import("./ChunkGroup")} ChunkGroup */ -/** @typedef {import("./Compilation")} Compilation */ -/** @typedef {import("./ConcatenationScope")} ConcatenationScope */ -/** @typedef {import("./Dependency")} Dependency */ -/** @typedef {import("./Dependency").UpdateHashContext} UpdateHashContext */ -/** @typedef {import("./DependencyTemplates")} DependencyTemplates */ -/** @typedef {import("./ExportsInfo").UsageStateType} UsageStateType */ -/** @typedef {import("./FileSystemInfo")} FileSystemInfo */ -/** @typedef {import("./ModuleGraphConnection").ConnectionState} ConnectionState */ -/** @typedef {import("./NormalModuleFactory")} NormalModuleFactory */ -/** @typedef {import("./RequestShortener")} RequestShortener */ -/** @typedef {import("./ResolverFactory").ResolverWithOptions} ResolverWithOptions */ -/** @typedef {import("./RuntimeTemplate")} RuntimeTemplate */ /** @typedef {import("./WebpackError")} WebpackError */ -/** @typedef {import("./util/Hash")} Hash */ -/** @template T @typedef {import("./util/LazySet")} LazySet */ -/** @template T @typedef {import("./util/SortableSet")} SortableSet */ +/** @typedef {import("./logging/Logger").Logger} Logger */ +/** @typedef {typeof import("./util/Hash")} Hash */ +/** @typedef {import("./util/fs").IStats} IStats */ /** @typedef {import("./util/fs").InputFileSystem} InputFileSystem */ -/** @typedef {import("./util/runtime").RuntimeSpec} RuntimeSpec */ + +const supportsEsm = +process.versions.modules >= 83; + +let FS_ACCURACY = 2000; + +const EMPTY_SET = new Set(); + +const RBDT_RESOLVE_CJS = 0; +const RBDT_RESOLVE_ESM = 1; +const RBDT_RESOLVE_DIRECTORY = 2; +const RBDT_RESOLVE_CJS_FILE = 3; +const RBDT_RESOLVE_CJS_FILE_AS_CHILD = 4; +const RBDT_RESOLVE_ESM_FILE = 5; +const RBDT_DIRECTORY = 6; +const RBDT_FILE = 7; +const RBDT_DIRECTORY_DEPENDENCIES = 8; +const RBDT_FILE_DEPENDENCIES = 9; + +const INVALID = Symbol("invalid"); /** - * @typedef {Object} SourceContext - * @property {DependencyTemplates} dependencyTemplates the dependency templates - * @property {RuntimeTemplate} runtimeTemplate the runtime template - * @property {ModuleGraph} moduleGraph the module graph - * @property {ChunkGraph} chunkGraph the chunk graph - * @property {RuntimeSpec} runtime the runtimes code should be generated for - * @property {string=} type the type of source that should be generated + * @typedef {Object} FileSystemInfoEntry + * @property {number} safeTime + * @property {number=} timestamp */ /** - * @typedef {Object} CodeGenerationContext - * @property {DependencyTemplates} dependencyTemplates the dependency templates - * @property {RuntimeTemplate} runtimeTemplate the runtime template - * @property {ModuleGraph} moduleGraph the module graph - * @property {ChunkGraph} chunkGraph the chunk graph - * @property {RuntimeSpec} runtime the runtimes code should be generated for - * @property {ConcatenationScope=} concatenationScope when in concatenated module, information about other concatenated modules + * @typedef {Object} ResolvedContextFileSystemInfoEntry + * @property {number} safeTime + * @property {string=} timestampHash */ /** - * @typedef {Object} ConcatenationBailoutReasonContext - * @property {ModuleGraph} moduleGraph the module graph - * @property {ChunkGraph} chunkGraph the chunk graph + * @typedef {Object} ContextFileSystemInfoEntry + * @property {number} safeTime + * @property {string=} timestampHash + * @property {ResolvedContextFileSystemInfoEntry=} resolved + * @property {Set=} symlinks */ /** - * @typedef {Object} CodeGenerationResult - * @property {Map} sources the resulting sources for all source types - * @property {Map=} data the resulting data for all source types - * @property {ReadonlySet} runtimeRequirements the runtime requirements - * @property {string=} hash a hash of the code generation result (will be automatically calculated from sources and runtimeRequirements if not provided) + * @typedef {Object} TimestampAndHash + * @property {number} safeTime + * @property {number=} timestamp + * @property {string} hash */ /** - * @typedef {Object} LibIdentOptions - * @property {string} context absolute context path to which lib ident is relative to - * @property {Object=} associatedObjectForCache object for caching + * @typedef {Object} ResolvedContextTimestampAndHash + * @property {number} safeTime + * @property {string=} timestampHash + * @property {string} hash */ /** - * @typedef {Object} KnownBuildMeta - * @property {string=} moduleArgument - * @property {string=} exportsArgument - * @property {boolean=} strict - * @property {string=} moduleConcatenationBailout - * @property {("default" | "namespace" | "flagged" | "dynamic")=} exportsType - * @property {(false | "redirect" | "redirect-warn")=} defaultObject - * @property {boolean=} strictHarmonyModule - * @property {boolean=} async - * @property {boolean=} sideEffectFree + * @typedef {Object} ContextTimestampAndHash + * @property {number} safeTime + * @property {string=} timestampHash + * @property {string} hash + * @property {ResolvedContextTimestampAndHash=} resolved + * @property {Set=} symlinks */ /** - * @typedef {Object} NeedBuildContext - * @property {Compilation} compilation - * @property {FileSystemInfo} fileSystemInfo - * @property {Map>} valueCacheVersions + * @typedef {Object} ContextHash + * @property {string} hash + * @property {string=} resolved + * @property {Set=} symlinks */ -/** @typedef {KnownBuildMeta & Record} BuildMeta */ - -const EMPTY_RESOLVE_OPTIONS = {}; - -let debugId = 1000; +/** + * @typedef {Object} SnapshotOptimizationEntry + * @property {Snapshot} snapshot + * @property {number} shared + * @property {Set} snapshotContent + * @property {Set} children + */ -const DEFAULT_TYPES_UNKNOWN = new Set(["unknown"]); -const DEFAULT_TYPES_JS = new Set(["javascript"]); +/** + * @typedef {Object} ResolveBuildDependenciesResult + * @property {Set} files list of files + * @property {Set} directories list of directories + * @property {Set} missing list of missing entries + * @property {Map} resolveResults stored resolve results + * @property {Object} resolveDependencies dependencies of the resolving + * @property {Set} resolveDependencies.files list of files + * @property {Set} resolveDependencies.directories list of directories + * @property {Set} resolveDependencies.missing list of missing entries + */ -const deprecatedNeedRebuild = util.deprecate( - (module, context) => { - return module.needRebuild( - context.fileSystemInfo.getDeprecatedFileTimestamps(), - context.fileSystemInfo.getDeprecatedContextTimestamps() - ); - }, - "Module.needRebuild is deprecated in favor of Module.needBuild", - "DEP_WEBPACK_MODULE_NEED_REBUILD" -); +const DONE_ITERATOR_RESULT = new Set().keys().next(); -/** @typedef {(requestShortener: RequestShortener) => string} OptimizationBailoutFunction */ +// cspell:word tshs +// Tsh = Timestamp + Hash +// Tshs = Timestamp + Hash combinations -class Module extends DependenciesBlock { - /** - * @param {string} type the module type - * @param {string=} context an optional context - * @param {string=} layer an optional layer in which the module is - */ - constructor(type, context = null, layer = null) { - super(); +class SnapshotIterator { + constructor(next) { + this.next = next; + } +} - /** @type {string} */ - this.type = type; - /** @type {string | null} */ - this.context = context; - /** @type {string | null} */ - this.layer = layer; - /** @type {boolean} */ - this.needId = true; +class SnapshotIterable { + constructor(snapshot, getMaps) { + this.snapshot = snapshot; + this.getMaps = getMaps; + } - // Unique Id - /** @type {number} */ - this.debugId = debugId++; + [Symbol.iterator]() { + let state = 0; + /** @type {IterableIterator} */ + let it; + /** @type {(Snapshot) => (Map | Set)[]} */ + let getMaps; + /** @type {(Map | Set)[]} */ + let maps; + /** @type {Snapshot} */ + let snapshot; + let queue; + return new SnapshotIterator(() => { + for (;;) { + switch (state) { + case 0: + snapshot = this.snapshot; + getMaps = this.getMaps; + maps = getMaps(snapshot); + state = 1; + /* falls through */ + case 1: + if (maps.length > 0) { + const map = maps.pop(); + if (map !== undefined) { + it = map.keys(); + state = 2; + } else { + break; + } + } else { + state = 3; + break; + } + /* falls through */ + case 2: { + const result = it.next(); + if (!result.done) return result; + state = 1; + break; + } + case 3: { + const children = snapshot.children; + if (children !== undefined) { + if (children.size === 1) { + // shortcut for a single child + // avoids allocation of queue + for (const child of children) snapshot = child; + maps = getMaps(snapshot); + state = 1; + break; + } + if (queue === undefined) queue = []; + for (const child of children) { + queue.push(child); + } + } + if (queue !== undefined && queue.length > 0) { + snapshot = queue.pop(); + maps = getMaps(snapshot); + state = 1; + break; + } else { + state = 4; + } + } + /* falls through */ + case 4: + return DONE_ITERATOR_RESULT; + } + } + }); + } +} - // Info from Factory - /** @type {ResolveOptions} */ - this.resolveOptions = EMPTY_RESOLVE_OPTIONS; - /** @type {object | undefined} */ - this.factoryMeta = undefined; - // TODO refactor this -> options object filled from Factory - // TODO webpack 6: use an enum - /** @type {boolean} */ - this.useSourceMap = false; - /** @type {boolean} */ - this.useSimpleSourceMap = false; +class Snapshot { + constructor() { + this._flags = 0; + /** @type {number | undefined} */ + this.startTime = undefined; + /** @type {Map | undefined} */ + this.fileTimestamps = undefined; + /** @type {Map | undefined} */ + this.fileHashes = undefined; + /** @type {Map | undefined} */ + this.fileTshs = undefined; + /** @type {Map | undefined} */ + this.contextTimestamps = undefined; + /** @type {Map | undefined} */ + this.contextHashes = undefined; + /** @type {Map | undefined} */ + this.contextTshs = undefined; + /** @type {Map | undefined} */ + this.missingExistence = undefined; + /** @type {Map | undefined} */ + this.managedItemInfo = undefined; + /** @type {Set | undefined} */ + this.managedFiles = undefined; + /** @type {Set | undefined} */ + this.managedContexts = undefined; + /** @type {Set | undefined} */ + this.managedMissing = undefined; + /** @type {Set | undefined} */ + this.children = undefined; + } - // Info from Build - /** @type {WebpackError[] | undefined} */ - this._warnings = undefined; - /** @type {WebpackError[] | undefined} */ - this._errors = undefined; - /** @type {BuildMeta} */ - this.buildMeta = undefined; - /** @type {Record} */ - this.buildInfo = undefined; - /** @type {Dependency[] | undefined} */ - this.presentationalDependencies = undefined; + hasStartTime() { + return (this._flags & 1) !== 0; } - // TODO remove in webpack 6 - // BACKWARD-COMPAT START - get id() { - return ChunkGraph.getChunkGraphForModule( - this, - "Module.id", - "DEP_WEBPACK_MODULE_ID" - ).getModuleId(this); + setStartTime(value) { + this._flags = this._flags | 1; + this.startTime = value; } - set id(value) { - if (value === "") { - this.needId = false; - return; + setMergedStartTime(value, snapshot) { + if (value) { + if (snapshot.hasStartTime()) { + this.setStartTime(Math.min(value, snapshot.startTime)); + } else { + this.setStartTime(value); + } + } else { + if (snapshot.hasStartTime()) this.setStartTime(snapshot.startTime); } - ChunkGraph.getChunkGraphForModule( - this, - "Module.id", - "DEP_WEBPACK_MODULE_ID" - ).setModuleId(this, value); } - /** - * @returns {string} the hash of the module - */ - get hash() { - return ChunkGraph.getChunkGraphForModule( - this, - "Module.hash", - "DEP_WEBPACK_MODULE_HASH" - ).getModuleHash(this, undefined); + hasFileTimestamps() { + return (this._flags & 2) !== 0; } - /** - * @returns {string} the shortened hash of the module - */ - get renderedHash() { - return ChunkGraph.getChunkGraphForModule( - this, - "Module.renderedHash", - "DEP_WEBPACK_MODULE_RENDERED_HASH" - ).getRenderedModuleHash(this, undefined); + setFileTimestamps(value) { + this._flags = this._flags | 2; + this.fileTimestamps = value; } - get profile() { - return ModuleGraph.getModuleGraphForModule( - this, - "Module.profile", - "DEP_WEBPACK_MODULE_PROFILE" - ).getProfile(this); + hasFileHashes() { + return (this._flags & 4) !== 0; } - set profile(value) { - ModuleGraph.getModuleGraphForModule( - this, - "Module.profile", - "DEP_WEBPACK_MODULE_PROFILE" - ).setProfile(this, value); + setFileHashes(value) { + this._flags = this._flags | 4; + this.fileHashes = value; } - get index() { - return ModuleGraph.getModuleGraphForModule( - this, - "Module.index", - "DEP_WEBPACK_MODULE_INDEX" - ).getPreOrderIndex(this); + hasFileTshs() { + return (this._flags & 8) !== 0; } - set index(value) { - ModuleGraph.getModuleGraphForModule( - this, - "Module.index", - "DEP_WEBPACK_MODULE_INDEX" - ).setPreOrderIndex(this, value); + setFileTshs(value) { + this._flags = this._flags | 8; + this.fileTshs = value; } - get index2() { - return ModuleGraph.getModuleGraphForModule( - this, - "Module.index2", - "DEP_WEBPACK_MODULE_INDEX2" - ).getPostOrderIndex(this); + hasContextTimestamps() { + return (this._flags & 0x10) !== 0; } - set index2(value) { - ModuleGraph.getModuleGraphForModule( - this, - "Module.index2", - "DEP_WEBPACK_MODULE_INDEX2" - ).setPostOrderIndex(this, value); + setContextTimestamps(value) { + this._flags = this._flags | 0x10; + this.contextTimestamps = value; } - get depth() { - return ModuleGraph.getModuleGraphForModule( - this, - "Module.depth", - "DEP_WEBPACK_MODULE_DEPTH" - ).getDepth(this); + hasContextHashes() { + return (this._flags & 0x20) !== 0; } - set depth(value) { - ModuleGraph.getModuleGraphForModule( - this, - "Module.depth", - "DEP_WEBPACK_MODULE_DEPTH" - ).setDepth(this, value); + setContextHashes(value) { + this._flags = this._flags | 0x20; + this.contextHashes = value; } - get issuer() { - return ModuleGraph.getModuleGraphForModule( - this, - "Module.issuer", - "DEP_WEBPACK_MODULE_ISSUER" - ).getIssuer(this); + hasContextTshs() { + return (this._flags & 0x40) !== 0; } - set issuer(value) { - ModuleGraph.getModuleGraphForModule( - this, - "Module.issuer", - "DEP_WEBPACK_MODULE_ISSUER" - ).setIssuer(this, value); + setContextTshs(value) { + this._flags = this._flags | 0x40; + this.contextTshs = value; } - get usedExports() { - return ModuleGraph.getModuleGraphForModule( - this, - "Module.usedExports", - "DEP_WEBPACK_MODULE_USED_EXPORTS" - ).getUsedExports(this, undefined); + hasMissingExistence() { + return (this._flags & 0x80) !== 0; } - /** - * @deprecated - * @returns {(string | OptimizationBailoutFunction)[]} list - */ - get optimizationBailout() { - return ModuleGraph.getModuleGraphForModule( - this, - "Module.optimizationBailout", - "DEP_WEBPACK_MODULE_OPTIMIZATION_BAILOUT" - ).getOptimizationBailout(this); - } - - get optional() { - return this.isOptional( - ModuleGraph.getModuleGraphForModule( - this, - "Module.optional", - "DEP_WEBPACK_MODULE_OPTIONAL" - ) - ); + setMissingExistence(value) { + this._flags = this._flags | 0x80; + this.missingExistence = value; } - addChunk(chunk) { - const chunkGraph = ChunkGraph.getChunkGraphForModule( - this, - "Module.addChunk", - "DEP_WEBPACK_MODULE_ADD_CHUNK" - ); - if (chunkGraph.isModuleInChunk(this, chunk)) return false; - chunkGraph.connectChunkAndModule(chunk, this); - return true; + hasManagedItemInfo() { + return (this._flags & 0x100) !== 0; } - removeChunk(chunk) { - return ChunkGraph.getChunkGraphForModule( - this, - "Module.removeChunk", - "DEP_WEBPACK_MODULE_REMOVE_CHUNK" - ).disconnectChunkAndModule(chunk, this); + setManagedItemInfo(value) { + this._flags = this._flags | 0x100; + this.managedItemInfo = value; } - isInChunk(chunk) { - return ChunkGraph.getChunkGraphForModule( - this, - "Module.isInChunk", - "DEP_WEBPACK_MODULE_IS_IN_CHUNK" - ).isModuleInChunk(this, chunk); + hasManagedFiles() { + return (this._flags & 0x200) !== 0; } - isEntryModule() { - return ChunkGraph.getChunkGraphForModule( - this, - "Module.isEntryModule", - "DEP_WEBPACK_MODULE_IS_ENTRY_MODULE" - ).isEntryModule(this); + setManagedFiles(value) { + this._flags = this._flags | 0x200; + this.managedFiles = value; } - getChunks() { - return ChunkGraph.getChunkGraphForModule( - this, - "Module.getChunks", - "DEP_WEBPACK_MODULE_GET_CHUNKS" - ).getModuleChunks(this); + hasManagedContexts() { + return (this._flags & 0x400) !== 0; } - getNumberOfChunks() { - return ChunkGraph.getChunkGraphForModule( - this, - "Module.getNumberOfChunks", - "DEP_WEBPACK_MODULE_GET_NUMBER_OF_CHUNKS" - ).getNumberOfModuleChunks(this); + setManagedContexts(value) { + this._flags = this._flags | 0x400; + this.managedContexts = value; } - get chunksIterable() { - return ChunkGraph.getChunkGraphForModule( - this, - "Module.chunksIterable", - "DEP_WEBPACK_MODULE_CHUNKS_ITERABLE" - ).getOrderedModuleChunksIterable(this, compareChunksById); + hasManagedMissing() { + return (this._flags & 0x800) !== 0; } - /** - * @param {string} exportName a name of an export - * @returns {boolean | null} true, if the export is provided why the module. - * null, if it's unknown. - * false, if it's not provided. - */ - isProvided(exportName) { - return ModuleGraph.getModuleGraphForModule( - this, - "Module.usedExports", - "DEP_WEBPACK_MODULE_USED_EXPORTS" - ).isExportProvided(this, exportName); + setManagedMissing(value) { + this._flags = this._flags | 0x800; + this.managedMissing = value; } - // BACKWARD-COMPAT END - /** - * @deprecated moved to .buildInfo.exportsArgument - * @returns {string} name of the exports argument - */ - get exportsArgument() { - return (this.buildInfo && this.buildInfo.exportsArgument) || "exports"; + hasChildren() { + return (this._flags & 0x1000) !== 0; } - /** - * @deprecated moved to .buildInfo.moduleArgument - * @returns {string} name of the module argument - */ - get moduleArgument() { - return (this.buildInfo && this.buildInfo.moduleArgument) || "module"; + setChildren(value) { + this._flags = this._flags | 0x1000; + this.children = value; } - /** - * @param {ModuleGraph} moduleGraph the module graph - * @param {boolean} strict the importing module is strict - * @returns {"namespace" | "default-only" | "default-with-named" | "dynamic"} export type - * "namespace": Exports is already a namespace object. namespace = exports. - * "dynamic": Check at runtime if __esModule is set. When set: namespace = { ...exports, default: exports }. When not set: namespace = { default: exports }. - * "default-only": Provide a namespace object with only default export. namespace = { default: exports } - * "default-with-named": Provide a namespace object with named and default export. namespace = { ...exports, default: exports } - */ - getExportsType(moduleGraph, strict) { - switch (this.buildMeta && this.buildMeta.exportsType) { - case "flagged": - return strict ? "default-with-named" : "namespace"; - case "namespace": - return "namespace"; - case "default": - switch (this.buildMeta.defaultObject) { - case "redirect": - return "default-with-named"; - case "redirect-warn": - return strict ? "default-only" : "default-with-named"; - default: - return "default-only"; - } - case "dynamic": { - if (strict) return "default-with-named"; - // Try to figure out value of __esModule by following reexports - const handleDefault = () => { - switch (this.buildMeta.defaultObject) { - case "redirect": - case "redirect-warn": - return "default-with-named"; - default: - return "default-only"; - } - }; - const exportInfo = moduleGraph.getReadOnlyExportInfo( - this, - "__esModule" - ); - if (exportInfo.provided === false) { - return handleDefault(); - } - const target = exportInfo.getTarget(moduleGraph); - if ( - !target || - !target.export || - target.export.length !== 1 || - target.export[0] !== "__esModule" - ) { - return "dynamic"; - } - switch ( - target.module.buildMeta && - target.module.buildMeta.exportsType - ) { - case "flagged": - case "namespace": - return "namespace"; - case "default": - return handleDefault(); - default: - return "dynamic"; - } - } - default: - return strict ? "default-with-named" : "dynamic"; + addChild(child) { + if (!this.hasChildren()) { + this.setChildren(new Set()); } + this.children.add(child); } - /** - * @param {Dependency} presentationalDependency dependency being tied to module. - * This is a Dependency without edge in the module graph. It's only for presentation. - * @returns {void} - */ - addPresentationalDependency(presentationalDependency) { - if (this.presentationalDependencies === undefined) { - this.presentationalDependencies = []; - } - this.presentationalDependencies.push(presentationalDependency); + serialize({ write }) { + write(this._flags); + if (this.hasStartTime()) write(this.startTime); + if (this.hasFileTimestamps()) write(this.fileTimestamps); + if (this.hasFileHashes()) write(this.fileHashes); + if (this.hasFileTshs()) write(this.fileTshs); + if (this.hasContextTimestamps()) write(this.contextTimestamps); + if (this.hasContextHashes()) write(this.contextHashes); + if (this.hasContextTshs()) write(this.contextTshs); + if (this.hasMissingExistence()) write(this.missingExistence); + if (this.hasManagedItemInfo()) write(this.managedItemInfo); + if (this.hasManagedFiles()) write(this.managedFiles); + if (this.hasManagedContexts()) write(this.managedContexts); + if (this.hasManagedMissing()) write(this.managedMissing); + if (this.hasChildren()) write(this.children); } - /** - * Removes all dependencies and blocks - * @returns {void} - */ - clearDependenciesAndBlocks() { - if (this.presentationalDependencies !== undefined) { - this.presentationalDependencies.length = 0; - } - super.clearDependenciesAndBlocks(); + deserialize({ read }) { + this._flags = read(); + if (this.hasStartTime()) this.startTime = read(); + if (this.hasFileTimestamps()) this.fileTimestamps = read(); + if (this.hasFileHashes()) this.fileHashes = read(); + if (this.hasFileTshs()) this.fileTshs = read(); + if (this.hasContextTimestamps()) this.contextTimestamps = read(); + if (this.hasContextHashes()) this.contextHashes = read(); + if (this.hasContextTshs()) this.contextTshs = read(); + if (this.hasMissingExistence()) this.missingExistence = read(); + if (this.hasManagedItemInfo()) this.managedItemInfo = read(); + if (this.hasManagedFiles()) this.managedFiles = read(); + if (this.hasManagedContexts()) this.managedContexts = read(); + if (this.hasManagedMissing()) this.managedMissing = read(); + if (this.hasChildren()) this.children = read(); } /** - * @param {WebpackError} warning the warning - * @returns {void} + * @param {function(Snapshot): (ReadonlyMap | ReadonlySet)[]} getMaps first + * @returns {Iterable} iterable */ - addWarning(warning) { - if (this._warnings === undefined) { - this._warnings = []; - } - this._warnings.push(warning); + _createIterable(getMaps) { + return new SnapshotIterable(this, getMaps); } /** - * @returns {Iterable | undefined} list of warnings if any + * @returns {Iterable} iterable */ - getWarnings() { - return this._warnings; + getFileIterable() { + return this._createIterable(s => [ + s.fileTimestamps, + s.fileHashes, + s.fileTshs, + s.managedFiles + ]); } /** - * @returns {number} number of warnings + * @returns {Iterable} iterable */ - getNumberOfWarnings() { - return this._warnings !== undefined ? this._warnings.length : 0; + getContextIterable() { + return this._createIterable(s => [ + s.contextTimestamps, + s.contextHashes, + s.contextTshs, + s.managedContexts + ]); } /** - * @param {WebpackError} error the error - * @returns {void} + * @returns {Iterable} iterable */ - addError(error) { - if (this._errors === undefined) { - this._errors = []; - } - this._errors.push(error); + getMissingIterable() { + return this._createIterable(s => [s.missingExistence, s.managedMissing]); } +} - /** - * @returns {Iterable | undefined} list of errors if any - */ - getErrors() { - return this._errors; - } +makeSerializable(Snapshot, "webpack/lib/FileSystemInfo", "Snapshot"); - /** - * @returns {number} number of errors - */ - getNumberOfErrors() { - return this._errors !== undefined ? this._errors.length : 0; - } +const MIN_COMMON_SNAPSHOT_SIZE = 3; +/** + * @template T + */ +class SnapshotOptimization { /** - * removes all warnings and errors - * @returns {void} + * @param {function(Snapshot): boolean} has has value + * @param {function(Snapshot): Map | Set} get get value + * @param {function(Snapshot, Map | Set): void} set set value + * @param {boolean=} useStartTime use the start time of snapshots + * @param {boolean=} isSet value is an Set instead of a Map */ - clearWarningsAndErrors() { - if (this._warnings !== undefined) { - this._warnings.length = 0; - } - if (this._errors !== undefined) { - this._errors.length = 0; - } + constructor(has, get, set, useStartTime = true, isSet = false) { + this._has = has; + this._get = get; + this._set = set; + this._useStartTime = useStartTime; + this._isSet = isSet; + /** @type {Map} */ + this._map = new Map(); + this._statItemsShared = 0; + this._statItemsUnshared = 0; + this._statSharedSnapshots = 0; + this._statReusedSharedSnapshots = 0; } - /** - * @param {ModuleGraph} moduleGraph the module graph - * @returns {boolean} true, if the module is optional - */ - isOptional(moduleGraph) { - let hasConnections = false; - for (const r of moduleGraph.getIncomingConnections(this)) { - if ( - !r.dependency || - !r.dependency.optional || - !r.isTargetActive(undefined) - ) { - return false; - } - hasConnections = true; - } - return hasConnections; + getStatisticMessage() { + const total = this._statItemsShared + this._statItemsUnshared; + if (total === 0) return undefined; + return `${ + this._statItemsShared && Math.round((this._statItemsShared * 100) / total) + }% (${this._statItemsShared}/${total}) entries shared via ${ + this._statSharedSnapshots + } shared snapshots (${ + this._statReusedSharedSnapshots + this._statSharedSnapshots + } times referenced)`; } - /** - * @param {ChunkGraph} chunkGraph the chunk graph - * @param {Chunk} chunk a chunk - * @param {Chunk=} ignoreChunk chunk to be ignored - * @returns {boolean} true, if the module is accessible from "chunk" when ignoring "ignoreChunk" - */ - isAccessibleInChunk(chunkGraph, chunk, ignoreChunk) { - // Check if module is accessible in ALL chunk groups - for (const chunkGroup of chunk.groupsIterable) { - if (!this.isAccessibleInChunkGroup(chunkGraph, chunkGroup)) return false; - } - return true; + clear() { + this._map.clear(); + this._statItemsShared = 0; + this._statItemsUnshared = 0; + this._statSharedSnapshots = 0; + this._statReusedSharedSnapshots = 0; } /** - * @param {ChunkGraph} chunkGraph the chunk graph - * @param {ChunkGroup} chunkGroup a chunk group - * @param {Chunk=} ignoreChunk chunk to be ignored - * @returns {boolean} true, if the module is accessible from "chunkGroup" when ignoring "ignoreChunk" + * @param {Snapshot} newSnapshot snapshot + * @param {Set} capturedFiles files to snapshot/share + * @returns {void} */ - isAccessibleInChunkGroup(chunkGraph, chunkGroup, ignoreChunk) { - const queue = new Set([chunkGroup]); - - // Check if module is accessible from all items of the queue - queueFor: for (const cg of queue) { - // 1. If module is in one of the chunks of the group we can continue checking the next items - // because it's accessible. - for (const chunk of cg.chunks) { - if (chunk !== ignoreChunk && chunkGraph.isModuleInChunk(this, chunk)) - continue queueFor; + optimize(newSnapshot, capturedFiles) { + /** + * @param {SnapshotOptimizationEntry} entry optimization entry + * @returns {void} + */ + const increaseSharedAndStoreOptimizationEntry = entry => { + if (entry.children !== undefined) { + entry.children.forEach(increaseSharedAndStoreOptimizationEntry); } - // 2. If the chunk group is initial, we can break here because it's not accessible. - if (chunkGroup.isInitial()) return false; - // 3. Enqueue all parents because it must be accessible from ALL parents - for (const parent of chunkGroup.parentsIterable) queue.add(parent); - } - // When we processed through the whole list and we didn't bailout, the module is accessible - return true; - } - - /** - * @param {Chunk} chunk a chunk - * @param {ModuleGraph} moduleGraph the module graph - * @param {ChunkGraph} chunkGraph the chunk graph - * @returns {boolean} true, if the module has any reason why "chunk" should be included - */ - hasReasonForChunk(chunk, moduleGraph, chunkGraph) { - // check for each reason if we need the chunk - for (const [ - fromModule, - connections - ] of moduleGraph.getIncomingConnectionsByOriginModule(this)) { - if (!connections.some(c => c.isTargetActive(chunk.runtime))) continue; - for (const originChunk of chunkGraph.getModuleChunksIterable( - fromModule - )) { - // return true if module this is not reachable from originChunk when ignoring chunk - if (!this.isAccessibleInChunk(chunkGraph, originChunk, chunk)) - return true; + entry.shared++; + storeOptimizationEntry(entry); + }; + /** + * @param {SnapshotOptimizationEntry} entry optimization entry + * @returns {void} + */ + const storeOptimizationEntry = entry => { + for (const path of entry.snapshotContent) { + const old = this._map.get(path); + if (old.shared < entry.shared) { + this._map.set(path, entry); + } + capturedFiles.delete(path); } - } - return false; - } + }; - /** - * @param {ModuleGraph} moduleGraph the module graph - * @param {RuntimeSpec} runtime the runtime - * @returns {boolean} true if at least one other module depends on this module - */ - hasReasons(moduleGraph, runtime) { - for (const c of moduleGraph.getIncomingConnections(this)) { - if (c.isTargetActive(runtime)) return true; - } - return false; - } + /** @type {SnapshotOptimizationEntry} */ + let newOptimizationEntry = undefined; - /** - * @returns {string} for debugging - */ - toString() { - return `Module[${this.debugId}: ${this.identifier()}]`; - } + const capturedFilesSize = capturedFiles.size; - /** - * @param {NeedBuildContext} context context info - * @param {function(WebpackError=, boolean=): void} callback callback function, returns true, if the module needs a rebuild - * @returns {void} - */ - needBuild(context, callback) { - callback( - null, - !this.buildMeta || - this.needRebuild === Module.prototype.needRebuild || - deprecatedNeedRebuild(this, context) - ); - } + /** @type {Set | undefined} */ + const optimizationEntries = new Set(); - /** - * @deprecated Use needBuild instead - * @param {Map} fileTimestamps timestamps of files - * @param {Map} contextTimestamps timestamps of directories - * @returns {boolean} true, if the module needs a rebuild - */ - needRebuild(fileTimestamps, contextTimestamps) { - return true; - } + for (const path of capturedFiles) { + const optimizationEntry = this._map.get(path); + if (optimizationEntry === undefined) { + if (newOptimizationEntry === undefined) { + newOptimizationEntry = { + snapshot: newSnapshot, + shared: 0, + snapshotContent: undefined, + children: undefined + }; + } + this._map.set(path, newOptimizationEntry); + continue; + } else { + optimizationEntries.add(optimizationEntry); + } + } - /** - * @param {Hash} hash the hash used to track dependencies - * @param {UpdateHashContext} context context - * @returns {void} - */ - updateHash( - hash, - context = { - chunkGraph: ChunkGraph.getChunkGraphForModule( - this, - "Module.updateHash", - "DEP_WEBPACK_MODULE_UPDATE_HASH" - ), - runtime: undefined - } - ) { - const { chunkGraph, runtime } = context; - hash.update(chunkGraph.getModuleGraphHash(this, runtime)); - if (this.presentationalDependencies !== undefined) { - for (const dep of this.presentationalDependencies) { - dep.updateHash(hash, context); + optimizationEntries: for (const optimizationEntry of optimizationEntries) { + const snapshot = optimizationEntry.snapshot; + if (optimizationEntry.shared > 0) { + // It's a shared snapshot + // We can't change it, so we can only use it when all files match + // and startTime is compatible + if ( + this._useStartTime && + newSnapshot.startTime && + (!snapshot.startTime || snapshot.startTime > newSnapshot.startTime) + ) { + continue; + } + const nonSharedFiles = new Set(); + const snapshotContent = optimizationEntry.snapshotContent; + const snapshotEntries = this._get(snapshot); + for (const path of snapshotContent) { + if (!capturedFiles.has(path)) { + if (!snapshotEntries.has(path)) { + // File is not shared and can't be removed from the snapshot + // because it's in a child of the snapshot + continue optimizationEntries; + } + nonSharedFiles.add(path); + continue; + } + } + if (nonSharedFiles.size === 0) { + // The complete snapshot is shared + // add it as child + newSnapshot.addChild(snapshot); + increaseSharedAndStoreOptimizationEntry(optimizationEntry); + this._statReusedSharedSnapshots++; + } else { + // Only a part of the snapshot is shared + const sharedCount = snapshotContent.size - nonSharedFiles.size; + if (sharedCount < MIN_COMMON_SNAPSHOT_SIZE) { + // Common part it too small + continue optimizationEntries; + } + // Extract common timestamps from both snapshots + let commonMap; + if (this._isSet) { + commonMap = new Set(); + for (const path of /** @type {Set} */ (snapshotEntries)) { + if (nonSharedFiles.has(path)) continue; + commonMap.add(path); + snapshotEntries.delete(path); + } + } else { + commonMap = new Map(); + const map = /** @type {Map} */ (snapshotEntries); + for (const [path, value] of map) { + if (nonSharedFiles.has(path)) continue; + commonMap.set(path, value); + snapshotEntries.delete(path); + } + } + // Create and attach snapshot + const commonSnapshot = new Snapshot(); + if (this._useStartTime) { + commonSnapshot.setMergedStartTime(newSnapshot.startTime, snapshot); + } + this._set(commonSnapshot, commonMap); + newSnapshot.addChild(commonSnapshot); + snapshot.addChild(commonSnapshot); + // Create optimization entry + const newEntry = { + snapshot: commonSnapshot, + shared: optimizationEntry.shared + 1, + snapshotContent: new Set(commonMap.keys()), + children: undefined + }; + if (optimizationEntry.children === undefined) + optimizationEntry.children = new Set(); + optimizationEntry.children.add(newEntry); + storeOptimizationEntry(newEntry); + this._statSharedSnapshots++; + } + } else { + // It's a unshared snapshot + // We can extract a common shared snapshot + // with all common files + const snapshotEntries = this._get(snapshot); + if (snapshotEntries === undefined) { + // Incomplete snapshot, that can't be used + continue optimizationEntries; + } + let commonMap; + if (this._isSet) { + commonMap = new Set(); + const set = /** @type {Set} */ (snapshotEntries); + if (capturedFiles.size < set.size) { + for (const path of capturedFiles) { + if (set.has(path)) commonMap.add(path); + } + } else { + for (const path of set) { + if (capturedFiles.has(path)) commonMap.add(path); + } + } + } else { + commonMap = new Map(); + const map = /** @type {Map} */ (snapshotEntries); + for (const path of capturedFiles) { + const ts = map.get(path); + if (ts === undefined) continue; + commonMap.set(path, ts); + } + } + + if (commonMap.size < MIN_COMMON_SNAPSHOT_SIZE) { + // Common part it too small + continue optimizationEntries; + } + // Create and attach snapshot + const commonSnapshot = new Snapshot(); + if (this._useStartTime) { + commonSnapshot.setMergedStartTime(newSnapshot.startTime, snapshot); + } + this._set(commonSnapshot, commonMap); + newSnapshot.addChild(commonSnapshot); + snapshot.addChild(commonSnapshot); + // Remove files from snapshot + for (const path of commonMap.keys()) snapshotEntries.delete(path); + const sharedCount = commonMap.size; + this._statItemsUnshared -= sharedCount; + this._statItemsShared += sharedCount; + // Create optimization entry + storeOptimizationEntry({ + snapshot: commonSnapshot, + shared: 2, + snapshotContent: new Set(commonMap.keys()), + children: undefined + }); + this._statSharedSnapshots++; } } - super.updateHash(hash, context); + const unshared = capturedFiles.size; + this._statItemsUnshared += unshared; + this._statItemsShared += capturedFilesSize - unshared; } +} - /** - * @returns {void} - */ - invalidateBuild() { - // should be overridden to support this feature - } +const parseString = str => { + if (str[0] === "'") str = `"${str.slice(1, -1).replace(/"/g, '\\"')}"`; + return JSON.parse(str); +}; - /* istanbul ignore next */ - /** - * @abstract - * @returns {string} a unique identifier of the module - */ - identifier() { - const AbstractMethodError = __webpack_require__(570); - throw new AbstractMethodError(); - } +/* istanbul ignore next */ +/** + * @param {number} mtime mtime + */ +const applyMtime = mtime => { + if (FS_ACCURACY > 1 && mtime % 2 !== 0) FS_ACCURACY = 1; + else if (FS_ACCURACY > 10 && mtime % 20 !== 0) FS_ACCURACY = 10; + else if (FS_ACCURACY > 100 && mtime % 200 !== 0) FS_ACCURACY = 100; + else if (FS_ACCURACY > 1000 && mtime % 2000 !== 0) FS_ACCURACY = 1000; +}; - /* istanbul ignore next */ - /** - * @abstract - * @param {RequestShortener} requestShortener the request shortener - * @returns {string} a user readable identifier of the module - */ - readableIdentifier(requestShortener) { - const AbstractMethodError = __webpack_require__(570); - throw new AbstractMethodError(); +/** + * @template T + * @template K + * @param {Map} a source map + * @param {Map} b joining map + * @returns {Map} joined map + */ +const mergeMaps = (a, b) => { + if (!b || b.size === 0) return a; + if (!a || a.size === 0) return b; + const map = new Map(a); + for (const [key, value] of b) { + map.set(key, value); } + return map; +}; - /* istanbul ignore next */ - /** - * @abstract - * @param {WebpackOptions} options webpack options - * @param {Compilation} compilation the compilation - * @param {ResolverWithOptions} resolver the resolver - * @param {InputFileSystem} fs the file system - * @param {function(WebpackError=): void} callback callback function - * @returns {void} - */ - build(options, compilation, resolver, fs, callback) { - const AbstractMethodError = __webpack_require__(570); - throw new AbstractMethodError(); +/** + * @template T + * @template K + * @param {Set} a source map + * @param {Set} b joining map + * @returns {Set} joined map + */ +const mergeSets = (a, b) => { + if (!b || b.size === 0) return a; + if (!a || a.size === 0) return b; + const map = new Set(a); + for (const item of b) { + map.add(item); } + return map; +}; - /** - * @abstract - * @returns {Set} types available (do not mutate) - */ - getSourceTypes() { - // Better override this method to return the correct types - if (this.source === Module.prototype.source) { - return DEFAULT_TYPES_UNKNOWN; - } else { - return DEFAULT_TYPES_JS; +/** + * Finding file or directory to manage + * @param {string} managedPath path that is managing by {@link FileSystemInfo} + * @param {string} path path to file or directory + * @returns {string|null} managed item + * @example + * getManagedItem( + * '/Users/user/my-project/node_modules/', + * '/Users/user/my-project/node_modules/package/index.js' + * ) === '/Users/user/my-project/node_modules/package' + * getManagedItem( + * '/Users/user/my-project/node_modules/', + * '/Users/user/my-project/node_modules/package1/node_modules/package2' + * ) === '/Users/user/my-project/node_modules/package1/node_modules/package2' + * getManagedItem( + * '/Users/user/my-project/node_modules/', + * '/Users/user/my-project/node_modules/.bin/script.js' + * ) === null // hidden files are disallowed as managed items + * getManagedItem( + * '/Users/user/my-project/node_modules/', + * '/Users/user/my-project/node_modules/package' + * ) === '/Users/user/my-project/node_modules/package' + */ +const getManagedItem = (managedPath, path) => { + let i = managedPath.length; + let slashes = 1; + let startingPosition = true; + loop: while (i < path.length) { + switch (path.charCodeAt(i)) { + case 47: // slash + case 92: // backslash + if (--slashes === 0) break loop; + startingPosition = true; + break; + case 46: // . + // hidden files are disallowed as managed items + // it's probably .yarn-integrity or .cache + if (startingPosition) return null; + break; + case 64: // @ + if (!startingPosition) return null; + slashes++; + break; + default: + startingPosition = false; + break; } + i++; } - - /** - * @abstract - * @deprecated Use codeGeneration() instead - * @param {DependencyTemplates} dependencyTemplates the dependency templates - * @param {RuntimeTemplate} runtimeTemplate the runtime template - * @param {string=} type the type of source that should be generated - * @returns {Source} generated source - */ - source(dependencyTemplates, runtimeTemplate, type = "javascript") { - if (this.codeGeneration === Module.prototype.codeGeneration) { - const AbstractMethodError = __webpack_require__(570); - throw new AbstractMethodError(); + if (i === path.length) slashes--; + // return null when path is incomplete + if (slashes !== 0) return null; + // if (path.slice(i + 1, i + 13) === "node_modules") + if ( + path.length >= i + 13 && + path.charCodeAt(i + 1) === 110 && + path.charCodeAt(i + 2) === 111 && + path.charCodeAt(i + 3) === 100 && + path.charCodeAt(i + 4) === 101 && + path.charCodeAt(i + 5) === 95 && + path.charCodeAt(i + 6) === 109 && + path.charCodeAt(i + 7) === 111 && + path.charCodeAt(i + 8) === 100 && + path.charCodeAt(i + 9) === 117 && + path.charCodeAt(i + 10) === 108 && + path.charCodeAt(i + 11) === 101 && + path.charCodeAt(i + 12) === 115 + ) { + // if this is the end of the path + if (path.length === i + 13) { + // return the node_modules directory + // it's special + return path; } - const chunkGraph = ChunkGraph.getChunkGraphForModule( - this, - "Module.source() is deprecated. Use Compilation.codeGenerationResults.getSource(module, runtime, type) instead", - "DEP_WEBPACK_MODULE_SOURCE" - ); - /** @type {CodeGenerationContext} */ - const codeGenContext = { - dependencyTemplates, - runtimeTemplate, - moduleGraph: chunkGraph.moduleGraph, - chunkGraph, - runtime: undefined - }; - const sources = this.codeGeneration(codeGenContext).sources; - return type ? sources.get(type) : sources.get(first(this.getSourceTypes())); - } - - /* istanbul ignore next */ - /** - * @abstract - * @param {string=} type the source type for which the size should be estimated - * @returns {number} the estimated size of the module (must be non-zero) - */ - size(type) { - const AbstractMethodError = __webpack_require__(570); - throw new AbstractMethodError(); - } - - /** - * @param {LibIdentOptions} options options - * @returns {string | null} an identifier for library inclusion - */ - libIdent(options) { - return null; - } - - /** - * @returns {string | null} absolute path which should be used for condition matching (usually the resource path) - */ - nameForCondition() { - return null; - } - - /** - * @param {ConcatenationBailoutReasonContext} context context - * @returns {string | undefined} reason why this module can't be concatenated, undefined when it can be concatenated - */ - getConcatenationBailoutReason(context) { - return `Module Concatenation is not implemented for ${this.constructor.name}`; - } - - /** - * @param {ModuleGraph} moduleGraph the module graph - * @returns {ConnectionState} how this module should be connected to referencing modules when consumed for side-effects only - */ - getSideEffectsConnectionState(moduleGraph) { - return true; - } - - /** - * @param {CodeGenerationContext} context context for code generation - * @returns {CodeGenerationResult} result - */ - codeGeneration(context) { - // Best override this method - const sources = new Map(); - for (const type of this.getSourceTypes()) { - if (type !== "unknown") { - sources.set( - type, - this.source( - context.dependencyTemplates, - context.runtimeTemplate, - type - ) - ); - } + const c = path.charCodeAt(i + 13); + // if next symbol is slash or backslash + if (c === 47 || c === 92) { + // Managed subpath + return getManagedItem(path.slice(0, i + 14), path); } - return { - sources, - runtimeRequirements: new Set([ - RuntimeGlobals.module, - RuntimeGlobals.exports, - RuntimeGlobals.require - ]) - }; - } - - /** - * @param {Chunk} chunk the chunk which condition should be checked - * @param {Compilation} compilation the compilation - * @returns {boolean} true, if the chunk is ok for the module - */ - chunkCondition(chunk, compilation) { - return true; - } - - hasChunkCondition() { - return this.chunkCondition !== Module.prototype.chunkCondition; - } - - /** - * Assuming this module is in the cache. Update the (cached) module with - * the fresh module from the factory. Usually updates internal references - * and properties. - * @param {Module} module fresh module - * @returns {void} - */ - updateCacheModule(module) { - this.type = module.type; - this.layer = module.layer; - this.context = module.context; - this.factoryMeta = module.factoryMeta; - this.resolveOptions = module.resolveOptions; } + return path.slice(0, i); +}; - /** - * Module should be unsafe cached. Get data that's needed for that. - * This data will be passed to restoreFromUnsafeCache later. - * @returns {object} cached data - */ - getUnsafeCacheData() { - return { - factoryMeta: this.factoryMeta, - resolveOptions: this.resolveOptions - }; - } +/** + * @template {ContextFileSystemInfoEntry | ContextTimestampAndHash} T + * @param {T} entry entry + * @returns {T["resolved"] | undefined} the resolved entry + */ +const getResolvedTimestamp = entry => { + if (entry === null) return null; + if (entry.resolved !== undefined) return entry.resolved; + return entry.symlinks === undefined ? entry : undefined; +}; - /** - * restore unsafe cache data - * @param {object} unsafeCacheData data from getUnsafeCacheData - * @param {NormalModuleFactory} normalModuleFactory the normal module factory handling the unsafe caching - */ - _restoreFromUnsafeCache(unsafeCacheData, normalModuleFactory) { - this.factoryMeta = unsafeCacheData.factoryMeta; - this.resolveOptions = unsafeCacheData.resolveOptions; - } +/** + * @param {ContextHash} entry entry + * @returns {string | undefined} the resolved entry + */ +const getResolvedHash = entry => { + if (entry === null) return null; + if (entry.resolved !== undefined) return entry.resolved; + return entry.symlinks === undefined ? entry.hash : undefined; +}; - /** - * Assuming this module is in the cache. Remove internal references to allow freeing some memory. - */ - cleanupForCache() { - this.factoryMeta = undefined; - this.resolveOptions = undefined; - } +const addAll = (source, target) => { + for (const key of source) target.add(key); +}; +/** + * Used to access information about the filesystem in a cached way + */ +class FileSystemInfo { /** - * @returns {Source | null} the original source for the module before webpack transformation + * @param {InputFileSystem} fs file system + * @param {Object} options options + * @param {Iterable=} options.managedPaths paths that are only managed by a package manager + * @param {Iterable=} options.immutablePaths paths that are immutable + * @param {Logger=} options.logger logger used to log invalid snapshots + * @param {string | Hash=} options.hashFunction the hash function to use */ - originalSource() { - return null; - } - - /** - * @param {LazySet} fileDependencies set where file dependencies are added to - * @param {LazySet} contextDependencies set where context dependencies are added to - * @param {LazySet} missingDependencies set where missing dependencies are added to - * @param {LazySet} buildDependencies set where build dependencies are added to - */ - addCacheDependencies( - fileDependencies, - contextDependencies, - missingDependencies, - buildDependencies - ) {} - - serialize(context) { - const { write } = context; - write(this.type); - write(this.layer); - write(this.context); - write(this.resolveOptions); - write(this.factoryMeta); - write(this.useSourceMap); - write(this.useSimpleSourceMap); - write( - this._warnings !== undefined && this._warnings.length === 0 - ? undefined - : this._warnings + constructor( + fs, + { + managedPaths = [], + immutablePaths = [], + logger, + hashFunction = "md4" + } = {} + ) { + this.fs = fs; + this.logger = logger; + this._remainingLogs = logger ? 40 : 0; + this._loggedPaths = logger ? new Set() : undefined; + this._hashFunction = hashFunction; + /** @type {WeakMap} */ + this._snapshotCache = new WeakMap(); + this._fileTimestampsOptimization = new SnapshotOptimization( + s => s.hasFileTimestamps(), + s => s.fileTimestamps, + (s, v) => s.setFileTimestamps(v) ); - write( - this._errors !== undefined && this._errors.length === 0 - ? undefined - : this._errors + this._fileHashesOptimization = new SnapshotOptimization( + s => s.hasFileHashes(), + s => s.fileHashes, + (s, v) => s.setFileHashes(v), + false ); - write(this.buildMeta); - write(this.buildInfo); - write(this.presentationalDependencies); - super.serialize(context); - } + this._fileTshsOptimization = new SnapshotOptimization( + s => s.hasFileTshs(), + s => s.fileTshs, + (s, v) => s.setFileTshs(v) + ); + this._contextTimestampsOptimization = new SnapshotOptimization( + s => s.hasContextTimestamps(), + s => s.contextTimestamps, + (s, v) => s.setContextTimestamps(v) + ); + this._contextHashesOptimization = new SnapshotOptimization( + s => s.hasContextHashes(), + s => s.contextHashes, + (s, v) => s.setContextHashes(v), + false + ); + this._contextTshsOptimization = new SnapshotOptimization( + s => s.hasContextTshs(), + s => s.contextTshs, + (s, v) => s.setContextTshs(v) + ); + this._missingExistenceOptimization = new SnapshotOptimization( + s => s.hasMissingExistence(), + s => s.missingExistence, + (s, v) => s.setMissingExistence(v), + false + ); + this._managedItemInfoOptimization = new SnapshotOptimization( + s => s.hasManagedItemInfo(), + s => s.managedItemInfo, + (s, v) => s.setManagedItemInfo(v), + false + ); + this._managedFilesOptimization = new SnapshotOptimization( + s => s.hasManagedFiles(), + s => s.managedFiles, + (s, v) => s.setManagedFiles(v), + false, + true + ); + this._managedContextsOptimization = new SnapshotOptimization( + s => s.hasManagedContexts(), + s => s.managedContexts, + (s, v) => s.setManagedContexts(v), + false, + true + ); + this._managedMissingOptimization = new SnapshotOptimization( + s => s.hasManagedMissing(), + s => s.managedMissing, + (s, v) => s.setManagedMissing(v), + false, + true + ); + /** @type {StackedCacheMap} */ + this._fileTimestamps = new StackedCacheMap(); + /** @type {Map} */ + this._fileHashes = new Map(); + /** @type {Map} */ + this._fileTshs = new Map(); + /** @type {StackedCacheMap} */ + this._contextTimestamps = new StackedCacheMap(); + /** @type {Map} */ + this._contextHashes = new Map(); + /** @type {Map} */ + this._contextTshs = new Map(); + /** @type {Map} */ + this._managedItems = new Map(); + /** @type {AsyncQueue} */ + this.fileTimestampQueue = new AsyncQueue({ + name: "file timestamp", + parallelism: 30, + processor: this._readFileTimestamp.bind(this) + }); + /** @type {AsyncQueue} */ + this.fileHashQueue = new AsyncQueue({ + name: "file hash", + parallelism: 10, + processor: this._readFileHash.bind(this) + }); + /** @type {AsyncQueue} */ + this.contextTimestampQueue = new AsyncQueue({ + name: "context timestamp", + parallelism: 2, + processor: this._readContextTimestamp.bind(this) + }); + /** @type {AsyncQueue} */ + this.contextHashQueue = new AsyncQueue({ + name: "context hash", + parallelism: 2, + processor: this._readContextHash.bind(this) + }); + /** @type {AsyncQueue} */ + this.contextTshQueue = new AsyncQueue({ + name: "context hash and timestamp", + parallelism: 2, + processor: this._readContextTimestampAndHash.bind(this) + }); + /** @type {AsyncQueue} */ + this.managedItemQueue = new AsyncQueue({ + name: "managed item info", + parallelism: 10, + processor: this._getManagedItemInfo.bind(this) + }); + /** @type {AsyncQueue>} */ + this.managedItemDirectoryQueue = new AsyncQueue({ + name: "managed item directory info", + parallelism: 10, + processor: this._getManagedItemDirectoryInfo.bind(this) + }); + this.managedPaths = Array.from(managedPaths); + this.managedPathsWithSlash = /** @type {string[]} */ ( + this.managedPaths.filter(p => typeof p === "string") + ).map(p => join(fs, p, "_").slice(0, -1)); - deserialize(context) { - const { read } = context; - this.type = read(); - this.layer = read(); - this.context = read(); - this.resolveOptions = read(); - this.factoryMeta = read(); - this.useSourceMap = read(); - this.useSimpleSourceMap = read(); - this._warnings = read(); - this._errors = read(); - this.buildMeta = read(); - this.buildInfo = read(); - this.presentationalDependencies = read(); - super.deserialize(context); - } -} + this.managedPathsRegExps = /** @type {RegExp[]} */ ( + this.managedPaths.filter(p => typeof p !== "string") + ); + this.immutablePaths = Array.from(immutablePaths); + this.immutablePathsWithSlash = /** @type {string[]} */ ( + this.immutablePaths.filter(p => typeof p === "string") + ).map(p => join(fs, p, "_").slice(0, -1)); + this.immutablePathsRegExps = /** @type {RegExp[]} */ ( + this.immutablePaths.filter(p => typeof p !== "string") + ); -makeSerializable(Module, "webpack/lib/Module"); + this._cachedDeprecatedFileTimestamps = undefined; + this._cachedDeprecatedContextTimestamps = undefined; -// TODO remove in webpack 6 -Object.defineProperty(Module.prototype, "hasEqualsChunks", { - get() { - throw new Error( - "Module.hasEqualsChunks was renamed (use hasEqualChunks instead)" - ); - } -}); + this._warnAboutExperimentalEsmTracking = false; -// TODO remove in webpack 6 -Object.defineProperty(Module.prototype, "isUsed", { - get() { - throw new Error( - "Module.isUsed was renamed (use getUsedName, isExportUsed or isModuleUsed instead)" - ); + this._statCreatedSnapshots = 0; + this._statTestedSnapshotsCached = 0; + this._statTestedSnapshotsNotCached = 0; + this._statTestedChildrenCached = 0; + this._statTestedChildrenNotCached = 0; + this._statTestedEntries = 0; } -}); - -// TODO remove in webpack 6 -Object.defineProperty(Module.prototype, "errors", { - get: util.deprecate( - /** - * @this {Module} - * @returns {WebpackError[]} array - */ - function () { - if (this._errors === undefined) { - this._errors = []; - } - return this._errors; - }, - "Module.errors was removed (use getErrors instead)", - "DEP_WEBPACK_MODULE_ERRORS" - ) -}); -// TODO remove in webpack 6 -Object.defineProperty(Module.prototype, "warnings", { - get: util.deprecate( - /** - * @this {Module} - * @returns {WebpackError[]} array - */ - function () { - if (this._warnings === undefined) { - this._warnings = []; + logStatistics() { + const logWhenMessage = (header, message) => { + if (message) { + this.logger.log(`${header}: ${message}`); } - return this._warnings; - }, - "Module.warnings was removed (use getWarnings instead)", - "DEP_WEBPACK_MODULE_WARNINGS" - ) -}); - -// TODO remove in webpack 6 -Object.defineProperty(Module.prototype, "used", { - get() { - throw new Error( - "Module.used was refactored (use ModuleGraph.getUsedExports instead)" + }; + this.logger.log(`${this._statCreatedSnapshots} new snapshots created`); + this.logger.log( + `${ + this._statTestedSnapshotsNotCached && + Math.round( + (this._statTestedSnapshotsNotCached * 100) / + (this._statTestedSnapshotsCached + + this._statTestedSnapshotsNotCached) + ) + }% root snapshot uncached (${this._statTestedSnapshotsNotCached} / ${ + this._statTestedSnapshotsCached + this._statTestedSnapshotsNotCached + })` ); - }, - set(value) { - throw new Error( - "Module.used was refactored (use ModuleGraph.setUsedExports instead)" + this.logger.log( + `${ + this._statTestedChildrenNotCached && + Math.round( + (this._statTestedChildrenNotCached * 100) / + (this._statTestedChildrenCached + this._statTestedChildrenNotCached) + ) + }% children snapshot uncached (${this._statTestedChildrenNotCached} / ${ + this._statTestedChildrenCached + this._statTestedChildrenNotCached + })` + ); + this.logger.log(`${this._statTestedEntries} entries tested`); + this.logger.log( + `File info in cache: ${this._fileTimestamps.size} timestamps ${this._fileHashes.size} hashes ${this._fileTshs.size} timestamp hash combinations` + ); + logWhenMessage( + `File timestamp snapshot optimization`, + this._fileTimestampsOptimization.getStatisticMessage() + ); + logWhenMessage( + `File hash snapshot optimization`, + this._fileHashesOptimization.getStatisticMessage() + ); + logWhenMessage( + `File timestamp hash combination snapshot optimization`, + this._fileTshsOptimization.getStatisticMessage() + ); + this.logger.log( + `Directory info in cache: ${this._contextTimestamps.size} timestamps ${this._contextHashes.size} hashes ${this._contextTshs.size} timestamp hash combinations` + ); + logWhenMessage( + `Directory timestamp snapshot optimization`, + this._contextTimestampsOptimization.getStatisticMessage() + ); + logWhenMessage( + `Directory hash snapshot optimization`, + this._contextHashesOptimization.getStatisticMessage() + ); + logWhenMessage( + `Directory timestamp hash combination snapshot optimization`, + this._contextTshsOptimization.getStatisticMessage() + ); + logWhenMessage( + `Missing items snapshot optimization`, + this._missingExistenceOptimization.getStatisticMessage() + ); + this.logger.log( + `Managed items info in cache: ${this._managedItems.size} items` + ); + logWhenMessage( + `Managed items snapshot optimization`, + this._managedItemInfoOptimization.getStatisticMessage() + ); + logWhenMessage( + `Managed files snapshot optimization`, + this._managedFilesOptimization.getStatisticMessage() + ); + logWhenMessage( + `Managed contexts snapshot optimization`, + this._managedContextsOptimization.getStatisticMessage() + ); + logWhenMessage( + `Managed missing snapshot optimization`, + this._managedMissingOptimization.getStatisticMessage() ); } -}); - -module.exports = Module; - - -/***/ }), -/***/ 37991: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + _log(path, reason, ...args) { + const key = path + reason; + if (this._loggedPaths.has(key)) return; + this._loggedPaths.add(key); + this.logger.debug(`${path} invalidated because ${reason}`, ...args); + if (--this._remainingLogs === 0) { + this.logger.debug( + "Logging limit has been reached and no further logging will be emitted by FileSystemInfo" + ); + } + } -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ + clear() { + this._remainingLogs = this.logger ? 40 : 0; + if (this._loggedPaths !== undefined) this._loggedPaths.clear(); + this._snapshotCache = new WeakMap(); + this._fileTimestampsOptimization.clear(); + this._fileHashesOptimization.clear(); + this._fileTshsOptimization.clear(); + this._contextTimestampsOptimization.clear(); + this._contextHashesOptimization.clear(); + this._contextTshsOptimization.clear(); + this._missingExistenceOptimization.clear(); + this._managedItemInfoOptimization.clear(); + this._managedFilesOptimization.clear(); + this._managedContextsOptimization.clear(); + this._managedMissingOptimization.clear(); + this._fileTimestamps.clear(); + this._fileHashes.clear(); + this._fileTshs.clear(); + this._contextTimestamps.clear(); + this._contextHashes.clear(); + this._contextTshs.clear(); + this._managedItems.clear(); + this._managedItems.clear(); + this._cachedDeprecatedFileTimestamps = undefined; + this._cachedDeprecatedContextTimestamps = undefined; -const { cutOffLoaderExecution } = __webpack_require__(22569); -const WebpackError = __webpack_require__(68422); -const makeSerializable = __webpack_require__(26522); + this._statCreatedSnapshots = 0; + this._statTestedSnapshotsCached = 0; + this._statTestedSnapshotsNotCached = 0; + this._statTestedChildrenCached = 0; + this._statTestedChildrenNotCached = 0; + this._statTestedEntries = 0; + } -class ModuleBuildError extends WebpackError { /** - * @param {string | Error&any} err error thrown - * @param {{from?: string|null}} info additional info + * @param {ReadonlyMap} map timestamps + * @param {boolean=} immutable if 'map' is immutable and FileSystemInfo can keep referencing it + * @returns {void} */ - constructor(err, { from = null } = {}) { - let message = "Module build failed"; - let details = undefined; - - if (from) { - message += ` (from ${from}):\n`; - } else { - message += ": "; - } + addFileTimestamps(map, immutable) { + this._fileTimestamps.addAll(map, immutable); + this._cachedDeprecatedFileTimestamps = undefined; + } - if (err !== null && typeof err === "object") { - if (typeof err.stack === "string" && err.stack) { - const stack = cutOffLoaderExecution(err.stack); + /** + * @param {ReadonlyMap} map timestamps + * @param {boolean=} immutable if 'map' is immutable and FileSystemInfo can keep referencing it + * @returns {void} + */ + addContextTimestamps(map, immutable) { + this._contextTimestamps.addAll(map, immutable); + this._cachedDeprecatedContextTimestamps = undefined; + } - if (!err.hideStack) { - message += stack; - } else { - details = stack; + /** + * @param {string} path file path + * @param {function(WebpackError=, (FileSystemInfoEntry | "ignore" | null)=): void} callback callback function + * @returns {void} + */ + getFileTimestamp(path, callback) { + const cache = this._fileTimestamps.get(path); + if (cache !== undefined) return callback(null, cache); + this.fileTimestampQueue.add(path, callback); + } - if (typeof err.message === "string" && err.message) { - message += err.message; - } else { - message += err; - } - } - } else if (typeof err.message === "string" && err.message) { - message += err.message; - } else { - message += String(err); - } - } else { - message += String(err); + /** + * @param {string} path context path + * @param {function(WebpackError=, (ResolvedContextFileSystemInfoEntry | "ignore" | null)=): void} callback callback function + * @returns {void} + */ + getContextTimestamp(path, callback) { + const cache = this._contextTimestamps.get(path); + if (cache !== undefined) { + if (cache === "ignore") return callback(null, "ignore"); + const resolved = getResolvedTimestamp(cache); + if (resolved !== undefined) return callback(null, resolved); + return this._resolveContextTimestamp(cache, callback); } - - super(message); - - this.name = "ModuleBuildError"; - this.details = details; - this.error = err; + this.contextTimestampQueue.add(path, (err, entry) => { + if (err) return callback(err); + const resolved = getResolvedTimestamp(entry); + if (resolved !== undefined) return callback(null, resolved); + this._resolveContextTimestamp(entry, callback); + }); } - serialize(context) { - const { write } = context; - - write(this.error); - - super.serialize(context); + /** + * @param {string} path context path + * @param {function(WebpackError=, (ContextFileSystemInfoEntry | "ignore" | null)=): void} callback callback function + * @returns {void} + */ + _getUnresolvedContextTimestamp(path, callback) { + const cache = this._contextTimestamps.get(path); + if (cache !== undefined) return callback(null, cache); + this.contextTimestampQueue.add(path, callback); } - deserialize(context) { - const { read } = context; - - this.error = read(); - - super.deserialize(context); + /** + * @param {string} path file path + * @param {function(WebpackError=, string=): void} callback callback function + * @returns {void} + */ + getFileHash(path, callback) { + const cache = this._fileHashes.get(path); + if (cache !== undefined) return callback(null, cache); + this.fileHashQueue.add(path, callback); } -} - -makeSerializable(ModuleBuildError, "webpack/lib/ModuleBuildError"); - -module.exports = ModuleBuildError; - - -/***/ }), - -/***/ 30549: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ - - - -const WebpackError = __webpack_require__(68422); - -/** @typedef {import("./Dependency").DependencyLocation} DependencyLocation */ -/** @typedef {import("./Module")} Module */ -class ModuleDependencyError extends WebpackError { /** - * Creates an instance of ModuleDependencyError. - * @param {Module} module module tied to dependency - * @param {Error} err error thrown - * @param {DependencyLocation} loc location of dependency + * @param {string} path context path + * @param {function(WebpackError=, string=): void} callback callback function + * @returns {void} */ - constructor(module, err, loc) { - super(err.message); - - this.name = "ModuleDependencyError"; - this.details = - err && !(/** @type {any} */ (err).hideStack) - ? err.stack.split("\n").slice(1).join("\n") - : undefined; - this.module = module; - this.loc = loc; - /** error is not (de)serialized, so it might be undefined after deserialization */ - this.error = err; - - if (err && /** @type {any} */ (err).hideStack) { - this.stack = - err.stack.split("\n").slice(1).join("\n") + "\n\n" + this.stack; + getContextHash(path, callback) { + const cache = this._contextHashes.get(path); + if (cache !== undefined) { + const resolved = getResolvedHash(cache); + if (resolved !== undefined) return callback(null, resolved); + return this._resolveContextHash(cache, callback); } + this.contextHashQueue.add(path, (err, entry) => { + if (err) return callback(err); + const resolved = getResolvedHash(entry); + if (resolved !== undefined) return callback(null, resolved); + this._resolveContextHash(entry, callback); + }); } -} - -module.exports = ModuleDependencyError; - - -/***/ }), - -/***/ 61528: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ - - - -const WebpackError = __webpack_require__(68422); -const makeSerializable = __webpack_require__(26522); - -/** @typedef {import("./Dependency").DependencyLocation} DependencyLocation */ -/** @typedef {import("./Module")} Module */ -class ModuleDependencyWarning extends WebpackError { /** - * @param {Module} module module tied to dependency - * @param {Error} err error thrown - * @param {DependencyLocation} loc location of dependency + * @param {string} path context path + * @param {function(WebpackError=, ContextHash=): void} callback callback function + * @returns {void} */ - constructor(module, err, loc) { - super(err ? err.message : ""); - - this.name = "ModuleDependencyWarning"; - this.details = - err && !(/** @type {any} */ (err).hideStack) - ? err.stack.split("\n").slice(1).join("\n") - : undefined; - this.module = module; - this.loc = loc; - /** error is not (de)serialized, so it might be undefined after deserialization */ - this.error = err; - - if (err && /** @type {any} */ (err).hideStack) { - this.stack = - err.stack.split("\n").slice(1).join("\n") + "\n\n" + this.stack; - } + _getUnresolvedContextHash(path, callback) { + const cache = this._contextHashes.get(path); + if (cache !== undefined) return callback(null, cache); + this.contextHashQueue.add(path, callback); } -} - -makeSerializable( - ModuleDependencyWarning, - "webpack/lib/ModuleDependencyWarning" -); - -module.exports = ModuleDependencyWarning; - -/***/ }), - -/***/ 11686: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ - - - -const { cleanUp } = __webpack_require__(22569); -const WebpackError = __webpack_require__(68422); -const makeSerializable = __webpack_require__(26522); - -class ModuleError extends WebpackError { /** - * @param {Error} err error thrown - * @param {{from?: string|null}} info additional info + * @param {string} path context path + * @param {function(WebpackError=, ResolvedContextTimestampAndHash=): void} callback callback function + * @returns {void} */ - constructor(err, { from = null } = {}) { - let message = "Module Error"; - - if (from) { - message += ` (from ${from}):\n`; - } else { - message += ": "; - } - - if (err && typeof err === "object" && err.message) { - message += err.message; - } else if (err) { - message += err; + getContextTsh(path, callback) { + const cache = this._contextTshs.get(path); + if (cache !== undefined) { + const resolved = getResolvedTimestamp(cache); + if (resolved !== undefined) return callback(null, resolved); + return this._resolveContextTsh(cache, callback); } - - super(message); - - this.name = "ModuleError"; - this.error = err; - this.details = - err && typeof err === "object" && err.stack - ? cleanUp(err.stack, this.message) - : undefined; - } - - serialize(context) { - const { write } = context; - - write(this.error); - - super.serialize(context); - } - - deserialize(context) { - const { read } = context; - - this.error = read(); - - super.deserialize(context); + this.contextTshQueue.add(path, (err, entry) => { + if (err) return callback(err); + const resolved = getResolvedTimestamp(entry); + if (resolved !== undefined) return callback(null, resolved); + this._resolveContextTsh(entry, callback); + }); } -} - -makeSerializable(ModuleError, "webpack/lib/ModuleError"); - -module.exports = ModuleError; - - -/***/ }), - -/***/ 61574: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ - - - -/** @typedef {import("../declarations/WebpackOptions").ResolveOptions} ResolveOptions */ -/** @typedef {import("./Dependency")} Dependency */ -/** @typedef {import("./Module")} Module */ - -/** - * @typedef {Object} ModuleFactoryResult - * @property {Module=} module the created module or unset if no module was created - * @property {Set=} fileDependencies - * @property {Set=} contextDependencies - * @property {Set=} missingDependencies - * @property {boolean=} cacheable allow to use the unsafe cache - */ - -/** - * @typedef {Object} ModuleFactoryCreateDataContextInfo - * @property {string} issuer - * @property {string | null=} issuerLayer - * @property {string} compiler - */ - -/** - * @typedef {Object} ModuleFactoryCreateData - * @property {ModuleFactoryCreateDataContextInfo} contextInfo - * @property {ResolveOptions=} resolveOptions - * @property {string} context - * @property {Dependency[]} dependencies - */ -class ModuleFactory { - /* istanbul ignore next */ /** - * @abstract - * @param {ModuleFactoryCreateData} data data object - * @param {function(Error=, ModuleFactoryResult=): void} callback callback + * @param {string} path context path + * @param {function(WebpackError=, ContextTimestampAndHash=): void} callback callback function * @returns {void} */ - create(data, callback) { - const AbstractMethodError = __webpack_require__(570); - throw new AbstractMethodError(); - } -} - -module.exports = ModuleFactory; - - -/***/ }), - -/***/ 80295: -/***/ (function(__unused_webpack_module, exports, __webpack_require__) { - -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ - - - -const createHash = __webpack_require__(24123); -const memoize = __webpack_require__(84297); - -/** @typedef {import("./ChunkGraph")} ChunkGraph */ -/** @typedef {import("./Module")} Module */ -/** @typedef {import("./RequestShortener")} RequestShortener */ -/** @typedef {typeof import("./util/Hash")} Hash */ - -const ModuleFilenameHelpers = exports; - -// TODO webpack 6: consider removing these -ModuleFilenameHelpers.ALL_LOADERS_RESOURCE = "[all-loaders][resource]"; -ModuleFilenameHelpers.REGEXP_ALL_LOADERS_RESOURCE = - /\[all-?loaders\]\[resource\]/gi; -ModuleFilenameHelpers.LOADERS_RESOURCE = "[loaders][resource]"; -ModuleFilenameHelpers.REGEXP_LOADERS_RESOURCE = /\[loaders\]\[resource\]/gi; -ModuleFilenameHelpers.RESOURCE = "[resource]"; -ModuleFilenameHelpers.REGEXP_RESOURCE = /\[resource\]/gi; -ModuleFilenameHelpers.ABSOLUTE_RESOURCE_PATH = "[absolute-resource-path]"; -// cSpell:words olute -ModuleFilenameHelpers.REGEXP_ABSOLUTE_RESOURCE_PATH = - /\[abs(olute)?-?resource-?path\]/gi; -ModuleFilenameHelpers.RESOURCE_PATH = "[resource-path]"; -ModuleFilenameHelpers.REGEXP_RESOURCE_PATH = /\[resource-?path\]/gi; -ModuleFilenameHelpers.ALL_LOADERS = "[all-loaders]"; -ModuleFilenameHelpers.REGEXP_ALL_LOADERS = /\[all-?loaders\]/gi; -ModuleFilenameHelpers.LOADERS = "[loaders]"; -ModuleFilenameHelpers.REGEXP_LOADERS = /\[loaders\]/gi; -ModuleFilenameHelpers.QUERY = "[query]"; -ModuleFilenameHelpers.REGEXP_QUERY = /\[query\]/gi; -ModuleFilenameHelpers.ID = "[id]"; -ModuleFilenameHelpers.REGEXP_ID = /\[id\]/gi; -ModuleFilenameHelpers.HASH = "[hash]"; -ModuleFilenameHelpers.REGEXP_HASH = /\[hash\]/gi; -ModuleFilenameHelpers.NAMESPACE = "[namespace]"; -ModuleFilenameHelpers.REGEXP_NAMESPACE = /\[namespace\]/gi; - -const getAfter = (strFn, token) => { - return () => { - const str = strFn(); - const idx = str.indexOf(token); - return idx < 0 ? "" : str.substr(idx); - }; -}; - -const getBefore = (strFn, token) => { - return () => { - const str = strFn(); - const idx = str.lastIndexOf(token); - return idx < 0 ? "" : str.substr(0, idx); - }; -}; - -const getHash = (strFn, hashFunction) => { - return () => { - const hash = createHash(hashFunction); - hash.update(strFn()); - const digest = /** @type {string} */ (hash.digest("hex")); - return digest.substr(0, 4); - }; -}; - -const asRegExp = test => { - if (typeof test === "string") { - test = new RegExp("^" + test.replace(/[-[\]{}()*+?.,\\^$|#\s]/g, "\\$&")); + _getUnresolvedContextTsh(path, callback) { + const cache = this._contextTshs.get(path); + if (cache !== undefined) return callback(null, cache); + this.contextTshQueue.add(path, callback); } - return test; -}; -const lazyObject = obj => { - const newObj = {}; - for (const key of Object.keys(obj)) { - const fn = obj[key]; - Object.defineProperty(newObj, key, { - get: () => fn(), - set: v => { - Object.defineProperty(newObj, key, { - value: v, - enumerable: true, - writable: true - }); - }, - enumerable: true, - configurable: true + _createBuildDependenciesResolvers() { + const resolveContext = createResolver({ + resolveToContext: true, + exportsFields: [], + fileSystem: this.fs }); - } - return newObj; -}; - -const REGEXP = /\[\\*([\w-]+)\\*\]/gi; - -/** - * - * @param {Module | string} module the module - * @param {TODO} options options - * @param {Object} contextInfo context info - * @param {RequestShortener} contextInfo.requestShortener requestShortener - * @param {ChunkGraph} contextInfo.chunkGraph chunk graph - * @param {string | Hash} contextInfo.hashFunction the hash function to use - * @returns {string} the filename - */ -ModuleFilenameHelpers.createFilename = ( - module = "", - options, - { requestShortener, chunkGraph, hashFunction = "md4" } -) => { - const opts = { - namespace: "", - moduleFilenameTemplate: "", - ...(typeof options === "object" - ? options - : { - moduleFilenameTemplate: options - }) - }; - - let absoluteResourcePath; - let hash; - let identifier; - let moduleId; - let shortIdentifier; - if (typeof module === "string") { - shortIdentifier = memoize(() => requestShortener.shorten(module)); - identifier = shortIdentifier; - moduleId = () => ""; - absoluteResourcePath = () => module.split("!").pop(); - hash = getHash(identifier, hashFunction); - } else { - shortIdentifier = memoize(() => - module.readableIdentifier(requestShortener) - ); - identifier = memoize(() => requestShortener.shorten(module.identifier())); - moduleId = () => chunkGraph.getModuleId(module); - absoluteResourcePath = () => module.identifier().split("!").pop(); - hash = getHash(identifier, hashFunction); - } - const resource = memoize(() => shortIdentifier().split("!").pop()); - - const loaders = getBefore(shortIdentifier, "!"); - const allLoaders = getBefore(identifier, "!"); - const query = getAfter(resource, "?"); - const resourcePath = () => { - const q = query().length; - return q === 0 ? resource() : resource().slice(0, -q); - }; - if (typeof opts.moduleFilenameTemplate === "function") { - return opts.moduleFilenameTemplate( - lazyObject({ - identifier: identifier, - shortIdentifier: shortIdentifier, - resource: resource, - resourcePath: memoize(resourcePath), - absoluteResourcePath: memoize(absoluteResourcePath), - allLoaders: memoize(allLoaders), - query: memoize(query), - moduleId: memoize(moduleId), - hash: memoize(hash), - namespace: () => opts.namespace - }) - ); + const resolveCjs = createResolver({ + extensions: [".js", ".json", ".node"], + conditionNames: ["require", "node"], + exportsFields: ["exports"], + fileSystem: this.fs + }); + const resolveCjsAsChild = createResolver({ + extensions: [".js", ".json", ".node"], + conditionNames: ["require", "node"], + exportsFields: [], + fileSystem: this.fs + }); + const resolveEsm = createResolver({ + extensions: [".js", ".json", ".node"], + fullySpecified: true, + conditionNames: ["import", "node"], + exportsFields: ["exports"], + fileSystem: this.fs + }); + return { resolveContext, resolveEsm, resolveCjs, resolveCjsAsChild }; } - // TODO webpack 6: consider removing alternatives without dashes - /** @type {Map} */ - const replacements = new Map([ - ["identifier", identifier], - ["short-identifier", shortIdentifier], - ["resource", resource], - ["resource-path", resourcePath], - // cSpell:words resourcepath - ["resourcepath", resourcePath], - ["absolute-resource-path", absoluteResourcePath], - ["abs-resource-path", absoluteResourcePath], - // cSpell:words absoluteresource - ["absoluteresource-path", absoluteResourcePath], - // cSpell:words absresource - ["absresource-path", absoluteResourcePath], - // cSpell:words resourcepath - ["absolute-resourcepath", absoluteResourcePath], - // cSpell:words resourcepath - ["abs-resourcepath", absoluteResourcePath], - // cSpell:words absoluteresourcepath - ["absoluteresourcepath", absoluteResourcePath], - // cSpell:words absresourcepath - ["absresourcepath", absoluteResourcePath], - ["all-loaders", allLoaders], - // cSpell:words allloaders - ["allloaders", allLoaders], - ["loaders", loaders], - ["query", query], - ["id", moduleId], - ["hash", hash], - ["namespace", () => opts.namespace] - ]); + /** + * @param {string} context context directory + * @param {Iterable} deps dependencies + * @param {function(Error=, ResolveBuildDependenciesResult=): void} callback callback function + * @returns {void} + */ + resolveBuildDependencies(context, deps, callback) { + const { resolveContext, resolveEsm, resolveCjs, resolveCjsAsChild } = + this._createBuildDependenciesResolvers(); - // TODO webpack 6: consider removing weird double placeholders - return opts.moduleFilenameTemplate - .replace(ModuleFilenameHelpers.REGEXP_ALL_LOADERS_RESOURCE, "[identifier]") - .replace( - ModuleFilenameHelpers.REGEXP_LOADERS_RESOURCE, - "[short-identifier]" - ) - .replace(REGEXP, (match, content) => { - if (content.length + 2 === match.length) { - const replacement = replacements.get(content.toLowerCase()); - if (replacement !== undefined) { - return replacement(); - } - } else if (match.startsWith("[\\") && match.endsWith("\\]")) { - return `[${match.slice(2, -2)}]`; - } - return match; - }); -}; - -ModuleFilenameHelpers.replaceDuplicates = (array, fn, comparator) => { - const countMap = Object.create(null); - const posMap = Object.create(null); - array.forEach((item, idx) => { - countMap[item] = countMap[item] || []; - countMap[item].push(idx); - posMap[item] = 0; - }); - if (comparator) { - Object.keys(countMap).forEach(item => { - countMap[item].sort(comparator); - }); - } - return array.map((item, i) => { - if (countMap[item].length > 1) { - if (comparator && countMap[item][0] === i) return item; - return fn(item, i, posMap[item]++); - } else { - return item; - } - }); -}; - -ModuleFilenameHelpers.matchPart = (str, test) => { - if (!test) return true; - test = asRegExp(test); - if (Array.isArray(test)) { - return test.map(asRegExp).some(regExp => regExp.test(str)); - } else { - return test.test(str); - } -}; - -ModuleFilenameHelpers.matchObject = (obj, str) => { - if (obj.test) { - if (!ModuleFilenameHelpers.matchPart(str, obj.test)) { - return false; - } - } - if (obj.include) { - if (!ModuleFilenameHelpers.matchPart(str, obj.include)) { - return false; - } - } - if (obj.exclude) { - if (ModuleFilenameHelpers.matchPart(str, obj.exclude)) { - return false; - } - } - return true; -}; - - -/***/ }), - -/***/ 20258: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ - - - -const util = __webpack_require__(31669); -const ExportsInfo = __webpack_require__(4295); -const ModuleGraphConnection = __webpack_require__(94144); -const SortableSet = __webpack_require__(67563); -const WeakTupleMap = __webpack_require__(73963); - -/** @typedef {import("./DependenciesBlock")} DependenciesBlock */ -/** @typedef {import("./Dependency")} Dependency */ -/** @typedef {import("./ExportsInfo").ExportInfo} ExportInfo */ -/** @typedef {import("./Module")} Module */ -/** @typedef {import("./ModuleProfile")} ModuleProfile */ -/** @typedef {import("./RequestShortener")} RequestShortener */ -/** @typedef {import("./util/runtime").RuntimeSpec} RuntimeSpec */ - -/** - * @callback OptimizationBailoutFunction - * @param {RequestShortener} requestShortener - * @returns {string} - */ - -const EMPTY_SET = new Set(); - -/** - * @param {SortableSet} set input - * @returns {readonly Map} mapped by origin module - */ -const getConnectionsByOriginModule = set => { - const map = new Map(); - /** @type {Module | 0} */ - let lastModule = 0; - /** @type {ModuleGraphConnection[]} */ - let lastList = undefined; - for (const connection of set) { - const { originModule } = connection; - if (lastModule === originModule) { - lastList.push(connection); - } else { - lastModule = originModule; - const list = map.get(originModule); - if (list !== undefined) { - lastList = list; - list.push(connection); - } else { - const list = [connection]; - lastList = list; - map.set(originModule, list); - } - } - } - return map; -}; - -/** - * @param {SortableSet} set input - * @returns {readonly Map} mapped by module - */ -const getConnectionsByModule = set => { - const map = new Map(); - /** @type {Module | 0} */ - let lastModule = 0; - /** @type {ModuleGraphConnection[]} */ - let lastList = undefined; - for (const connection of set) { - const { module } = connection; - if (lastModule === module) { - lastList.push(connection); - } else { - lastModule = module; - const list = map.get(module); - if (list !== undefined) { - lastList = list; - list.push(connection); - } else { - const list = [connection]; - lastList = list; - map.set(module, list); - } - } - } - return map; -}; - -class ModuleGraphModule { - constructor() { - /** @type {SortableSet} */ - this.incomingConnections = new SortableSet(); - /** @type {SortableSet | undefined} */ - this.outgoingConnections = undefined; - /** @type {Module | null} */ - this.issuer = undefined; - /** @type {(string | OptimizationBailoutFunction)[]} */ - this.optimizationBailout = []; - /** @type {ExportsInfo} */ - this.exports = new ExportsInfo(); - /** @type {number} */ - this.preOrderIndex = null; - /** @type {number} */ - this.postOrderIndex = null; - /** @type {number} */ - this.depth = null; - /** @type {ModuleProfile} */ - this.profile = undefined; - /** @type {boolean} */ - this.async = false; - /** @type {ModuleGraphConnection[]} */ - this._unassignedConnections = undefined; - } -} - -class ModuleGraph { - constructor() { - /** @type {WeakMap} */ - this._dependencyMap = new WeakMap(); - /** @type {Map} */ - this._moduleMap = new Map(); - /** @type {WeakMap} */ - this._metaMap = new WeakMap(); - - /** @type {WeakTupleMap} */ - this._cache = undefined; - - /** @type {Map>} */ - this._moduleMemCaches = undefined; - } - - /** - * @param {Module} module the module - * @returns {ModuleGraphModule} the internal module - */ - _getModuleGraphModule(module) { - let mgm = this._moduleMap.get(module); - if (mgm === undefined) { - mgm = new ModuleGraphModule(); - this._moduleMap.set(module, mgm); - } - return mgm; - } - - /** - * @param {Dependency} dependency the dependency - * @param {DependenciesBlock} block parent block - * @param {Module} module parent module - * @param {number=} indexInBlock position in block - * @returns {void} - */ - setParents(dependency, block, module, indexInBlock = -1) { - dependency._parentDependenciesBlockIndex = indexInBlock; - dependency._parentDependenciesBlock = block; - dependency._parentModule = module; - } - - /** - * @param {Dependency} dependency the dependency - * @returns {Module} parent module - */ - getParentModule(dependency) { - return dependency._parentModule; - } - - /** - * @param {Dependency} dependency the dependency - * @returns {DependenciesBlock} parent block - */ - getParentBlock(dependency) { - return dependency._parentDependenciesBlock; - } - - /** - * @param {Dependency} dependency the dependency - * @returns {number} index - */ - getParentBlockIndex(dependency) { - return dependency._parentDependenciesBlockIndex; - } - - /** - * @param {Module} originModule the referencing module - * @param {Dependency} dependency the referencing dependency - * @param {Module} module the referenced module - * @returns {void} - */ - setResolvedModule(originModule, dependency, module) { - const connection = new ModuleGraphConnection( - originModule, - dependency, - module, - undefined, - dependency.weak, - dependency.getCondition(this) - ); - const connections = this._getModuleGraphModule(module).incomingConnections; - connections.add(connection); - if (originModule) { - const mgm = this._getModuleGraphModule(originModule); - if (mgm._unassignedConnections === undefined) { - mgm._unassignedConnections = []; - } - mgm._unassignedConnections.push(connection); - if (mgm.outgoingConnections === undefined) { - mgm.outgoingConnections = new SortableSet(); - } - mgm.outgoingConnections.add(connection); - } else { - this._dependencyMap.set(dependency, connection); - } - } - - /** - * @param {Dependency} dependency the referencing dependency - * @param {Module} module the referenced module - * @returns {void} - */ - updateModule(dependency, module) { - const connection = this.getConnection(dependency); - if (connection.module === module) return; - const newConnection = connection.clone(); - newConnection.module = module; - this._dependencyMap.set(dependency, newConnection); - connection.setActive(false); - const originMgm = this._getModuleGraphModule(connection.originModule); - originMgm.outgoingConnections.add(newConnection); - const targetMgm = this._getModuleGraphModule(module); - targetMgm.incomingConnections.add(newConnection); - } - - /** - * @param {Dependency} dependency the referencing dependency - * @returns {void} - */ - removeConnection(dependency) { - const connection = this.getConnection(dependency); - const targetMgm = this._getModuleGraphModule(connection.module); - targetMgm.incomingConnections.delete(connection); - const originMgm = this._getModuleGraphModule(connection.originModule); - originMgm.outgoingConnections.delete(connection); - this._dependencyMap.set(dependency, null); - } - - /** - * @param {Dependency} dependency the referencing dependency - * @param {string} explanation an explanation - * @returns {void} - */ - addExplanation(dependency, explanation) { - const connection = this.getConnection(dependency); - connection.addExplanation(explanation); - } - - /** - * @param {Module} sourceModule the source module - * @param {Module} targetModule the target module - * @returns {void} - */ - cloneModuleAttributes(sourceModule, targetModule) { - const oldMgm = this._getModuleGraphModule(sourceModule); - const newMgm = this._getModuleGraphModule(targetModule); - newMgm.postOrderIndex = oldMgm.postOrderIndex; - newMgm.preOrderIndex = oldMgm.preOrderIndex; - newMgm.depth = oldMgm.depth; - newMgm.exports = oldMgm.exports; - newMgm.async = oldMgm.async; - } - - /** - * @param {Module} module the module - * @returns {void} - */ - removeModuleAttributes(module) { - const mgm = this._getModuleGraphModule(module); - mgm.postOrderIndex = null; - mgm.preOrderIndex = null; - mgm.depth = null; - mgm.async = false; - } - - /** - * @returns {void} - */ - removeAllModuleAttributes() { - for (const mgm of this._moduleMap.values()) { - mgm.postOrderIndex = null; - mgm.preOrderIndex = null; - mgm.depth = null; - mgm.async = false; - } - } - - /** - * @param {Module} oldModule the old referencing module - * @param {Module} newModule the new referencing module - * @param {function(ModuleGraphConnection): boolean} filterConnection filter predicate for replacement - * @returns {void} - */ - moveModuleConnections(oldModule, newModule, filterConnection) { - if (oldModule === newModule) return; - const oldMgm = this._getModuleGraphModule(oldModule); - const newMgm = this._getModuleGraphModule(newModule); - // Outgoing connections - const oldConnections = oldMgm.outgoingConnections; - if (oldConnections !== undefined) { - if (newMgm.outgoingConnections === undefined) { - newMgm.outgoingConnections = new SortableSet(); - } - const newConnections = newMgm.outgoingConnections; - for (const connection of oldConnections) { - if (filterConnection(connection)) { - connection.originModule = newModule; - newConnections.add(connection); - oldConnections.delete(connection); - } - } - } - // Incoming connections - const oldConnections2 = oldMgm.incomingConnections; - const newConnections2 = newMgm.incomingConnections; - for (const connection of oldConnections2) { - if (filterConnection(connection)) { - connection.module = newModule; - newConnections2.add(connection); - oldConnections2.delete(connection); + /** @type {Set} */ + const files = new Set(); + /** @type {Set} */ + const fileSymlinks = new Set(); + /** @type {Set} */ + const directories = new Set(); + /** @type {Set} */ + const directorySymlinks = new Set(); + /** @type {Set} */ + const missing = new Set(); + /** @type {Set} */ + const resolveFiles = new Set(); + /** @type {Set} */ + const resolveDirectories = new Set(); + /** @type {Set} */ + const resolveMissing = new Set(); + /** @type {Map} */ + const resolveResults = new Map(); + const invalidResolveResults = new Set(); + const resolverContext = { + fileDependencies: resolveFiles, + contextDependencies: resolveDirectories, + missingDependencies: resolveMissing + }; + const expectedToString = expected => { + return expected ? ` (expected ${expected})` : ""; + }; + const jobToString = job => { + switch (job.type) { + case RBDT_RESOLVE_CJS: + return `resolve commonjs ${job.path}${expectedToString( + job.expected + )}`; + case RBDT_RESOLVE_ESM: + return `resolve esm ${job.path}${expectedToString(job.expected)}`; + case RBDT_RESOLVE_DIRECTORY: + return `resolve directory ${job.path}`; + case RBDT_RESOLVE_CJS_FILE: + return `resolve commonjs file ${job.path}${expectedToString( + job.expected + )}`; + case RBDT_RESOLVE_ESM_FILE: + return `resolve esm file ${job.path}${expectedToString( + job.expected + )}`; + case RBDT_DIRECTORY: + return `directory ${job.path}`; + case RBDT_FILE: + return `file ${job.path}`; + case RBDT_DIRECTORY_DEPENDENCIES: + return `directory dependencies ${job.path}`; + case RBDT_FILE_DEPENDENCIES: + return `file dependencies ${job.path}`; } - } - } - - /** - * @param {Module} oldModule the old referencing module - * @param {Module} newModule the new referencing module - * @param {function(ModuleGraphConnection): boolean} filterConnection filter predicate for replacement - * @returns {void} - */ - copyOutgoingModuleConnections(oldModule, newModule, filterConnection) { - if (oldModule === newModule) return; - const oldMgm = this._getModuleGraphModule(oldModule); - const newMgm = this._getModuleGraphModule(newModule); - // Outgoing connections - const oldConnections = oldMgm.outgoingConnections; - if (oldConnections !== undefined) { - if (newMgm.outgoingConnections === undefined) { - newMgm.outgoingConnections = new SortableSet(); + return `unknown ${job.type} ${job.path}`; + }; + const pathToString = job => { + let result = ` at ${jobToString(job)}`; + job = job.issuer; + while (job !== undefined) { + result += `\n at ${jobToString(job)}`; + job = job.issuer; } - const newConnections = newMgm.outgoingConnections; - for (const connection of oldConnections) { - if (filterConnection(connection)) { - const newConnection = connection.clone(); - newConnection.originModule = newModule; - newConnections.add(newConnection); - if (newConnection.module !== undefined) { - const otherMgm = this._getModuleGraphModule(newConnection.module); - otherMgm.incomingConnections.add(newConnection); + return result; + }; + processAsyncTree( + Array.from(deps, dep => ({ + type: RBDT_RESOLVE_CJS, + context, + path: dep, + expected: undefined, + issuer: undefined + })), + 20, + (job, push, callback) => { + const { type, context, path, expected } = job; + const resolveDirectory = path => { + const key = `d\n${context}\n${path}`; + if (resolveResults.has(key)) { + return callback(); } - } - } - } - } - - /** - * @param {Module} module the referenced module - * @param {string} explanation an explanation why it's referenced - * @returns {void} - */ - addExtraReason(module, explanation) { - const connections = this._getModuleGraphModule(module).incomingConnections; - connections.add(new ModuleGraphConnection(null, null, module, explanation)); - } - - /** - * @param {Dependency} dependency the dependency to look for a referenced module - * @returns {Module} the referenced module - */ - getResolvedModule(dependency) { - const connection = this.getConnection(dependency); - return connection !== undefined ? connection.resolvedModule : null; - } - - /** - * @param {Dependency} dependency the dependency to look for a referenced module - * @returns {ModuleGraphConnection | undefined} the connection - */ - getConnection(dependency) { - const connection = this._dependencyMap.get(dependency); - if (connection === undefined) { - const module = this.getParentModule(dependency); - if (module !== undefined) { - const mgm = this._getModuleGraphModule(module); - if ( - mgm._unassignedConnections && - mgm._unassignedConnections.length !== 0 - ) { - let foundConnection; - for (const connection of mgm._unassignedConnections) { - this._dependencyMap.set(connection.dependency, connection); - if (connection.dependency === dependency) - foundConnection = connection; - } - mgm._unassignedConnections.length = 0; - if (foundConnection !== undefined) { - return foundConnection; - } - } - } - this._dependencyMap.set(dependency, null); - return undefined; - } - return connection === null ? undefined : connection; - } - - /** - * @param {Dependency} dependency the dependency to look for a referenced module - * @returns {Module} the referenced module - */ - getModule(dependency) { - const connection = this.getConnection(dependency); - return connection !== undefined ? connection.module : null; - } - - /** - * @param {Dependency} dependency the dependency to look for a referencing module - * @returns {Module} the referencing module - */ - getOrigin(dependency) { - const connection = this.getConnection(dependency); - return connection !== undefined ? connection.originModule : null; - } - - /** - * @param {Dependency} dependency the dependency to look for a referencing module - * @returns {Module} the original referencing module - */ - getResolvedOrigin(dependency) { - const connection = this.getConnection(dependency); - return connection !== undefined ? connection.resolvedOriginModule : null; - } - - /** - * @param {Module} module the module - * @returns {Iterable} reasons why a module is included - */ - getIncomingConnections(module) { - const connections = this._getModuleGraphModule(module).incomingConnections; - return connections; - } - - /** - * @param {Module} module the module - * @returns {Iterable} list of outgoing connections - */ - getOutgoingConnections(module) { - const connections = this._getModuleGraphModule(module).outgoingConnections; - return connections === undefined ? EMPTY_SET : connections; - } - - /** - * @param {Module} module the module - * @returns {readonly Map} reasons why a module is included, in a map by source module - */ - getIncomingConnectionsByOriginModule(module) { - const connections = this._getModuleGraphModule(module).incomingConnections; - return connections.getFromUnorderedCache(getConnectionsByOriginModule); - } - - /** - * @param {Module} module the module - * @returns {readonly Map | undefined} connections to modules, in a map by module - */ - getOutgoingConnectionsByModule(module) { - const connections = this._getModuleGraphModule(module).outgoingConnections; - return connections === undefined - ? undefined - : connections.getFromUnorderedCache(getConnectionsByModule); - } - - /** - * @param {Module} module the module - * @returns {ModuleProfile | null} the module profile - */ - getProfile(module) { - const mgm = this._getModuleGraphModule(module); - return mgm.profile; - } - - /** - * @param {Module} module the module - * @param {ModuleProfile | null} profile the module profile - * @returns {void} - */ - setProfile(module, profile) { - const mgm = this._getModuleGraphModule(module); - mgm.profile = profile; - } - - /** - * @param {Module} module the module - * @returns {Module | null} the issuer module - */ - getIssuer(module) { - const mgm = this._getModuleGraphModule(module); - return mgm.issuer; - } - - /** - * @param {Module} module the module - * @param {Module | null} issuer the issuer module - * @returns {void} - */ - setIssuer(module, issuer) { - const mgm = this._getModuleGraphModule(module); - mgm.issuer = issuer; - } - - /** - * @param {Module} module the module - * @param {Module | null} issuer the issuer module - * @returns {void} - */ - setIssuerIfUnset(module, issuer) { - const mgm = this._getModuleGraphModule(module); - if (mgm.issuer === undefined) mgm.issuer = issuer; - } - - /** - * @param {Module} module the module - * @returns {(string | OptimizationBailoutFunction)[]} optimization bailouts - */ - getOptimizationBailout(module) { - const mgm = this._getModuleGraphModule(module); - return mgm.optimizationBailout; - } - - /** - * @param {Module} module the module - * @returns {true | string[] | null} the provided exports - */ - getProvidedExports(module) { - const mgm = this._getModuleGraphModule(module); - return mgm.exports.getProvidedExports(); - } - - /** - * @param {Module} module the module - * @param {string | string[]} exportName a name of an export - * @returns {boolean | null} true, if the export is provided by the module. - * null, if it's unknown. - * false, if it's not provided. - */ - isExportProvided(module, exportName) { - const mgm = this._getModuleGraphModule(module); - const result = mgm.exports.isExportProvided(exportName); - return result === undefined ? null : result; - } - - /** - * @param {Module} module the module - * @returns {ExportsInfo} info about the exports - */ - getExportsInfo(module) { - const mgm = this._getModuleGraphModule(module); - return mgm.exports; - } - - /** - * @param {Module} module the module - * @param {string} exportName the export - * @returns {ExportInfo} info about the export - */ - getExportInfo(module, exportName) { - const mgm = this._getModuleGraphModule(module); - return mgm.exports.getExportInfo(exportName); - } - - /** - * @param {Module} module the module - * @param {string} exportName the export - * @returns {ExportInfo} info about the export (do not modify) - */ - getReadOnlyExportInfo(module, exportName) { - const mgm = this._getModuleGraphModule(module); - return mgm.exports.getReadOnlyExportInfo(exportName); - } - - /** - * @param {Module} module the module - * @param {RuntimeSpec} runtime the runtime - * @returns {false | true | SortableSet | null} the used exports - * false: module is not used at all. - * true: the module namespace/object export is used. - * SortableSet: these export names are used. - * empty SortableSet: module is used but no export. - * null: unknown, worst case should be assumed. - */ - getUsedExports(module, runtime) { - const mgm = this._getModuleGraphModule(module); - return mgm.exports.getUsedExports(runtime); - } - - /** - * @param {Module} module the module - * @returns {number} the index of the module - */ - getPreOrderIndex(module) { - const mgm = this._getModuleGraphModule(module); - return mgm.preOrderIndex; - } - - /** - * @param {Module} module the module - * @returns {number} the index of the module - */ - getPostOrderIndex(module) { - const mgm = this._getModuleGraphModule(module); - return mgm.postOrderIndex; - } - - /** - * @param {Module} module the module - * @param {number} index the index of the module - * @returns {void} - */ - setPreOrderIndex(module, index) { - const mgm = this._getModuleGraphModule(module); - mgm.preOrderIndex = index; - } - - /** - * @param {Module} module the module - * @param {number} index the index of the module - * @returns {boolean} true, if the index was set - */ - setPreOrderIndexIfUnset(module, index) { - const mgm = this._getModuleGraphModule(module); - if (mgm.preOrderIndex === null) { - mgm.preOrderIndex = index; - return true; - } - return false; - } - - /** - * @param {Module} module the module - * @param {number} index the index of the module - * @returns {void} - */ - setPostOrderIndex(module, index) { - const mgm = this._getModuleGraphModule(module); - mgm.postOrderIndex = index; - } - - /** - * @param {Module} module the module - * @param {number} index the index of the module - * @returns {boolean} true, if the index was set - */ - setPostOrderIndexIfUnset(module, index) { - const mgm = this._getModuleGraphModule(module); - if (mgm.postOrderIndex === null) { - mgm.postOrderIndex = index; - return true; - } - return false; - } - - /** - * @param {Module} module the module - * @returns {number} the depth of the module - */ - getDepth(module) { - const mgm = this._getModuleGraphModule(module); - return mgm.depth; - } - - /** - * @param {Module} module the module - * @param {number} depth the depth of the module - * @returns {void} - */ - setDepth(module, depth) { - const mgm = this._getModuleGraphModule(module); - mgm.depth = depth; - } - - /** - * @param {Module} module the module - * @param {number} depth the depth of the module - * @returns {boolean} true, if the depth was set - */ - setDepthIfLower(module, depth) { - const mgm = this._getModuleGraphModule(module); - if (mgm.depth === null || mgm.depth > depth) { - mgm.depth = depth; - return true; - } - return false; - } - - /** - * @param {Module} module the module - * @returns {boolean} true, if the module is async - */ - isAsync(module) { - const mgm = this._getModuleGraphModule(module); - return mgm.async; - } - - /** - * @param {Module} module the module - * @returns {void} - */ - setAsync(module) { - const mgm = this._getModuleGraphModule(module); - mgm.async = true; - } - - /** - * @param {any} thing any thing - * @returns {Object} metadata - */ - getMeta(thing) { - let meta = this._metaMap.get(thing); - if (meta === undefined) { - meta = Object.create(null); - this._metaMap.set(thing, meta); - } - return meta; - } - - /** - * @param {any} thing any thing - * @returns {Object} metadata - */ - getMetaIfExisting(thing) { - return this._metaMap.get(thing); - } - - /** - * @param {string=} cacheStage a persistent stage name for caching - */ - freeze(cacheStage) { - this._cache = new WeakTupleMap(); - this._cacheStage = cacheStage; - } - - unfreeze() { - this._cache = undefined; - this._cacheStage = undefined; - } - - /** - * @template {any[]} T - * @template V - * @param {(moduleGraph: ModuleGraph, ...args: T) => V} fn computer - * @param {T} args arguments - * @returns {V} computed value or cached - */ - cached(fn, ...args) { - if (this._cache === undefined) return fn(this, ...args); - return this._cache.provide(fn, ...args, () => fn(this, ...args)); - } - - /** - * @param {Map>} moduleMemCaches mem caches for modules for better caching - */ - setModuleMemCaches(moduleMemCaches) { - this._moduleMemCaches = moduleMemCaches; - } - - /** - * @param {Dependency} dependency dependency - * @param {...any} args arguments, last argument is a function called with moduleGraph, dependency, ...args - * @returns {any} computed value or cached - */ - dependencyCacheProvide(dependency, ...args) { - /** @type {(moduleGraph: ModuleGraph, dependency: Dependency, ...args: any[]) => any} */ - const fn = args.pop(); - if (this._moduleMemCaches && this._cacheStage) { - const memCache = this._moduleMemCaches.get( - this.getParentModule(dependency) - ); - if (memCache !== undefined) { - return memCache.provide(dependency, this._cacheStage, ...args, () => - fn(this, dependency, ...args) - ); - } - } - if (this._cache === undefined) return fn(this, dependency, ...args); - return this._cache.provide(dependency, ...args, () => - fn(this, dependency, ...args) - ); - } - - // TODO remove in webpack 6 - /** - * @param {Module} module the module - * @param {string} deprecateMessage message for the deprecation message - * @param {string} deprecationCode code for the deprecation - * @returns {ModuleGraph} the module graph - */ - static getModuleGraphForModule(module, deprecateMessage, deprecationCode) { - const fn = deprecateMap.get(deprecateMessage); - if (fn) return fn(module); - const newFn = util.deprecate( - /** - * @param {Module} module the module - * @returns {ModuleGraph} the module graph - */ - module => { - const moduleGraph = moduleGraphForModuleMap.get(module); - if (!moduleGraph) - throw new Error( - deprecateMessage + - "There was no ModuleGraph assigned to the Module for backward-compat (Use the new API)" - ); - return moduleGraph; - }, - deprecateMessage + ": Use new ModuleGraph API", - deprecationCode - ); - deprecateMap.set(deprecateMessage, newFn); - return newFn(module); - } - - // TODO remove in webpack 6 - /** - * @param {Module} module the module - * @param {ModuleGraph} moduleGraph the module graph - * @returns {void} - */ - static setModuleGraphForModule(module, moduleGraph) { - moduleGraphForModuleMap.set(module, moduleGraph); - } - - // TODO remove in webpack 6 - /** - * @param {Module} module the module - * @returns {void} - */ - static clearModuleGraphForModule(module) { - moduleGraphForModuleMap.delete(module); - } -} - -// TODO remove in webpack 6 -/** @type {WeakMap} */ -const moduleGraphForModuleMap = new WeakMap(); - -// TODO remove in webpack 6 -/** @type {Map ModuleGraph>} */ -const deprecateMap = new Map(); - -module.exports = ModuleGraph; -module.exports.ModuleGraphConnection = ModuleGraphConnection; - - -/***/ }), - -/***/ 94144: -/***/ (function(module) { - -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ - - - -/** @typedef {import("./Dependency")} Dependency */ -/** @typedef {import("./Module")} Module */ -/** @typedef {import("./util/runtime").RuntimeSpec} RuntimeSpec */ - -/** - * Module itself is not connected, but transitive modules are connected transitively. - */ -const TRANSITIVE_ONLY = Symbol("transitive only"); - -/** - * While determining the active state, this flag is used to signal a circular connection. - */ -const CIRCULAR_CONNECTION = Symbol("circular connection"); - -/** @typedef {boolean | typeof TRANSITIVE_ONLY | typeof CIRCULAR_CONNECTION} ConnectionState */ - -/** - * @param {ConnectionState} a first - * @param {ConnectionState} b second - * @returns {ConnectionState} merged - */ -const addConnectionStates = (a, b) => { - if (a === true || b === true) return true; - if (a === false) return b; - if (b === false) return a; - if (a === TRANSITIVE_ONLY) return b; - if (b === TRANSITIVE_ONLY) return a; - return a; -}; - -/** - * @param {ConnectionState} a first - * @param {ConnectionState} b second - * @returns {ConnectionState} intersected - */ -const intersectConnectionStates = (a, b) => { - if (a === false || b === false) return false; - if (a === true) return b; - if (b === true) return a; - if (a === CIRCULAR_CONNECTION) return b; - if (b === CIRCULAR_CONNECTION) return a; - return a; -}; - -class ModuleGraphConnection { - /** - * @param {Module|null} originModule the referencing module - * @param {Dependency|null} dependency the referencing dependency - * @param {Module} module the referenced module - * @param {string=} explanation some extra detail - * @param {boolean=} weak the reference is weak - * @param {false | function(ModuleGraphConnection, RuntimeSpec): ConnectionState=} condition condition for the connection - */ - constructor( - originModule, - dependency, - module, - explanation, - weak = false, - condition = undefined - ) { - this.originModule = originModule; - this.resolvedOriginModule = originModule; - this.dependency = dependency; - this.resolvedModule = module; - this.module = module; - this.weak = weak; - this.conditional = !!condition; - this._active = condition !== false; - /** @type {function(ModuleGraphConnection, RuntimeSpec): ConnectionState} */ - this.condition = condition || undefined; - /** @type {Set} */ - this.explanations = undefined; - if (explanation) { - this.explanations = new Set(); - this.explanations.add(explanation); - } - } - - clone() { - const clone = new ModuleGraphConnection( - this.resolvedOriginModule, - this.dependency, - this.resolvedModule, - undefined, - this.weak, - this.condition - ); - clone.originModule = this.originModule; - clone.module = this.module; - clone.conditional = this.conditional; - clone._active = this._active; - if (this.explanations) clone.explanations = new Set(this.explanations); - return clone; - } - - /** - * @param {function(ModuleGraphConnection, RuntimeSpec): ConnectionState} condition condition for the connection - * @returns {void} - */ - addCondition(condition) { - if (this.conditional) { - const old = this.condition; - this.condition = (c, r) => - intersectConnectionStates(old(c, r), condition(c, r)); - } else if (this._active) { - this.conditional = true; - this.condition = condition; - } - } - - /** - * @param {string} explanation the explanation to add - * @returns {void} - */ - addExplanation(explanation) { - if (this.explanations === undefined) { - this.explanations = new Set(); - } - this.explanations.add(explanation); - } - - get explanation() { - if (this.explanations === undefined) return ""; - return Array.from(this.explanations).join(" "); - } - - // TODO webpack 5 remove - get active() { - throw new Error("Use getActiveState instead"); - } - - /** - * @param {RuntimeSpec} runtime the runtime - * @returns {boolean} true, if the connection is active - */ - isActive(runtime) { - if (!this.conditional) return this._active; - return this.condition(this, runtime) !== false; - } - - /** - * @param {RuntimeSpec} runtime the runtime - * @returns {boolean} true, if the connection is active - */ - isTargetActive(runtime) { - if (!this.conditional) return this._active; - return this.condition(this, runtime) === true; - } - - /** - * @param {RuntimeSpec} runtime the runtime - * @returns {ConnectionState} true: fully active, false: inactive, TRANSITIVE: direct module inactive, but transitive connection maybe active - */ - getActiveState(runtime) { - if (!this.conditional) return this._active; - return this.condition(this, runtime); - } - - /** - * @param {boolean} value active or not - * @returns {void} - */ - setActive(value) { - this.conditional = false; - this._active = value; - } - - set active(value) { - throw new Error("Use setActive instead"); - } -} - -/** @typedef {typeof TRANSITIVE_ONLY} TRANSITIVE_ONLY */ -/** @typedef {typeof CIRCULAR_CONNECTION} CIRCULAR_CONNECTION */ - -module.exports = ModuleGraphConnection; -module.exports.addConnectionStates = addConnectionStates; -module.exports.TRANSITIVE_ONLY = /** @type {typeof TRANSITIVE_ONLY} */ ( - TRANSITIVE_ONLY -); -module.exports.CIRCULAR_CONNECTION = /** @type {typeof CIRCULAR_CONNECTION} */ ( - CIRCULAR_CONNECTION -); - - -/***/ }), - -/***/ 45095: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ - - - -const { ConcatSource, RawSource, CachedSource } = __webpack_require__(96192); -const { UsageState } = __webpack_require__(4295); -const Template = __webpack_require__(92066); -const JavascriptModulesPlugin = __webpack_require__(76767); - -/** @typedef {import("webpack-sources").Source} Source */ -/** @typedef {import("./Compiler")} Compiler */ -/** @typedef {import("./ExportsInfo")} ExportsInfo */ -/** @typedef {import("./ExportsInfo").ExportInfo} ExportInfo */ -/** @typedef {import("./Module")} Module */ -/** @typedef {import("./ModuleGraph")} ModuleGraph */ -/** @typedef {import("./ModuleTemplate")} ModuleTemplate */ -/** @typedef {import("./RequestShortener")} RequestShortener */ - -const joinIterableWithComma = iterable => { - // This is more performant than Array.from().join(", ") - // as it doesn't create an array - let str = ""; - let first = true; - for (const item of iterable) { - if (first) { - first = false; - } else { - str += ", "; - } - str += item; - } - return str; -}; - -/** - * @param {ConcatSource} source output - * @param {string} indent spacing - * @param {ExportsInfo} exportsInfo data - * @param {ModuleGraph} moduleGraph moduleGraph - * @param {RequestShortener} requestShortener requestShortener - * @param {Set} alreadyPrinted deduplication set - * @returns {void} - */ -const printExportsInfoToSource = ( - source, - indent, - exportsInfo, - moduleGraph, - requestShortener, - alreadyPrinted = new Set() -) => { - const otherExportsInfo = exportsInfo.otherExportsInfo; - - let alreadyPrintedExports = 0; - - // determine exports to print - const printedExports = []; - for (const exportInfo of exportsInfo.orderedExports) { - if (!alreadyPrinted.has(exportInfo)) { - alreadyPrinted.add(exportInfo); - printedExports.push(exportInfo); - } else { - alreadyPrintedExports++; - } - } - let showOtherExports = false; - if (!alreadyPrinted.has(otherExportsInfo)) { - alreadyPrinted.add(otherExportsInfo); - showOtherExports = true; - } else { - alreadyPrintedExports++; - } - - // print the exports - for (const exportInfo of printedExports) { - const target = exportInfo.getTarget(moduleGraph); - source.add( - Template.toComment( - `${indent}export ${JSON.stringify(exportInfo.name).slice( - 1, - -1 - )} [${exportInfo.getProvidedInfo()}] [${exportInfo.getUsedInfo()}] [${exportInfo.getRenameInfo()}]${ - target - ? ` -> ${target.module.readableIdentifier(requestShortener)}${ - target.export - ? ` .${target.export - .map(e => JSON.stringify(e).slice(1, -1)) - .join(".")}` - : "" - }` - : "" - }` - ) + "\n" - ); - if (exportInfo.exportsInfo) { - printExportsInfoToSource( - source, - indent + " ", - exportInfo.exportsInfo, - moduleGraph, - requestShortener, - alreadyPrinted - ); - } - } - - if (alreadyPrintedExports) { - source.add( - Template.toComment( - `${indent}... (${alreadyPrintedExports} already listed exports)` - ) + "\n" - ); - } - - if (showOtherExports) { - const target = otherExportsInfo.getTarget(moduleGraph); - if ( - target || - otherExportsInfo.provided !== false || - otherExportsInfo.getUsed(undefined) !== UsageState.Unused - ) { - const title = - printedExports.length > 0 || alreadyPrintedExports > 0 - ? "other exports" - : "exports"; - source.add( - Template.toComment( - `${indent}${title} [${otherExportsInfo.getProvidedInfo()}] [${otherExportsInfo.getUsedInfo()}]${ - target - ? ` -> ${target.module.readableIdentifier(requestShortener)}` - : "" - }` - ) + "\n" - ); - } - } -}; - -/** @type {WeakMap }>>} */ -const caches = new WeakMap(); - -class ModuleInfoHeaderPlugin { - /** - * @param {boolean=} verbose add more information like exports, runtime requirements and bailouts - */ - constructor(verbose = true) { - this._verbose = verbose; - } - /** - * @param {Compiler} compiler the compiler - * @returns {void} - */ - apply(compiler) { - const { _verbose: verbose } = this; - compiler.hooks.compilation.tap("ModuleInfoHeaderPlugin", compilation => { - const hooks = JavascriptModulesPlugin.getCompilationHooks(compilation); - hooks.renderModulePackage.tap( - "ModuleInfoHeaderPlugin", - ( - moduleSource, - module, - { chunk, chunkGraph, moduleGraph, runtimeTemplate } - ) => { - const { requestShortener } = runtimeTemplate; - let cacheEntry; - let cache = caches.get(requestShortener); - if (cache === undefined) { - caches.set(requestShortener, (cache = new WeakMap())); - cache.set( - module, - (cacheEntry = { header: undefined, full: new WeakMap() }) - ); - } else { - cacheEntry = cache.get(module); - if (cacheEntry === undefined) { - cache.set( - module, - (cacheEntry = { header: undefined, full: new WeakMap() }) - ); - } else if (!verbose) { - const cachedSource = cacheEntry.full.get(moduleSource); - if (cachedSource !== undefined) return cachedSource; + resolveResults.set(key, undefined); + resolveContext(context, path, resolverContext, (err, _, result) => { + if (err) { + if (expected === false) { + resolveResults.set(key, false); + return callback(); + } + invalidResolveResults.add(key); + err.message += `\nwhile resolving '${path}' in ${context} to a directory`; + return callback(err); + } + const resultPath = result.path; + resolveResults.set(key, resultPath); + push({ + type: RBDT_DIRECTORY, + context: undefined, + path: resultPath, + expected: undefined, + issuer: job + }); + callback(); + }); + }; + const resolveFile = (path, symbol, resolve) => { + const key = `${symbol}\n${context}\n${path}`; + if (resolveResults.has(key)) { + return callback(); + } + resolveResults.set(key, undefined); + resolve(context, path, resolverContext, (err, _, result) => { + if (typeof expected === "string") { + if (!err && result && result.path === expected) { + resolveResults.set(key, result.path); + } else { + invalidResolveResults.add(key); + this.logger.warn( + `Resolving '${path}' in ${context} for build dependencies doesn't lead to expected result '${expected}', but to '${ + err || (result && result.path) + }' instead. Resolving dependencies are ignored for this path.\n${pathToString( + job + )}` + ); + } + } else { + if (err) { + if (expected === false) { + resolveResults.set(key, false); + return callback(); + } + invalidResolveResults.add(key); + err.message += `\nwhile resolving '${path}' in ${context} as file\n${pathToString( + job + )}`; + return callback(err); + } + const resultPath = result.path; + resolveResults.set(key, resultPath); + push({ + type: RBDT_FILE, + context: undefined, + path: resultPath, + expected: undefined, + issuer: job + }); + } + callback(); + }); + }; + switch (type) { + case RBDT_RESOLVE_CJS: { + const isDirectory = /[\\/]$/.test(path); + if (isDirectory) { + resolveDirectory(path.slice(0, path.length - 1)); + } else { + resolveFile(path, "f", resolveCjs); } + break; } - const source = new ConcatSource(); - let header = cacheEntry.header; - if (header === undefined) { - const req = module.readableIdentifier(requestShortener); - const reqStr = req.replace(/\*\//g, "*_/"); - const reqStrStar = "*".repeat(reqStr.length); - const headerStr = `/*!****${reqStrStar}****!*\\\n !*** ${reqStr} ***!\n \\****${reqStrStar}****/\n`; - header = new RawSource(headerStr); - cacheEntry.header = header; + case RBDT_RESOLVE_ESM: { + const isDirectory = /[\\/]$/.test(path); + if (isDirectory) { + resolveDirectory(path.slice(0, path.length - 1)); + } else { + resolveFile(path); + } + break; } - source.add(header); - if (verbose) { - const exportsType = module.buildMeta.exportsType; - source.add( - Template.toComment( - exportsType - ? `${exportsType} exports` - : "unknown exports (runtime-defined)" - ) + "\n" - ); - if (exportsType) { - const exportsInfo = moduleGraph.getExportsInfo(module); - printExportsInfoToSource( - source, - "", - exportsInfo, - moduleGraph, - requestShortener - ); + case RBDT_RESOLVE_DIRECTORY: { + resolveDirectory(path); + break; + } + case RBDT_RESOLVE_CJS_FILE: { + resolveFile(path, "f", resolveCjs); + break; + } + case RBDT_RESOLVE_CJS_FILE_AS_CHILD: { + resolveFile(path, "c", resolveCjsAsChild); + break; + } + case RBDT_RESOLVE_ESM_FILE: { + resolveFile(path, "e", resolveEsm); + break; + } + case RBDT_FILE: { + if (files.has(path)) { + callback(); + break; } - source.add( - Template.toComment( - `runtime requirements: ${joinIterableWithComma( - chunkGraph.getModuleRuntimeRequirements(module, chunk.runtime) - )}` - ) + "\n" - ); - const optimizationBailout = - moduleGraph.getOptimizationBailout(module); - if (optimizationBailout) { - for (const text of optimizationBailout) { - let code; - if (typeof text === "function") { - code = text(requestShortener); - } else { - code = text; + files.add(path); + this.fs.realpath(path, (err, _realPath) => { + if (err) return callback(err); + const realPath = /** @type {string} */ (_realPath); + if (realPath !== path) { + fileSymlinks.add(path); + resolveFiles.add(path); + if (files.has(realPath)) return callback(); + files.add(realPath); + } + push({ + type: RBDT_FILE_DEPENDENCIES, + context: undefined, + path: realPath, + expected: undefined, + issuer: job + }); + callback(); + }); + break; + } + case RBDT_DIRECTORY: { + if (directories.has(path)) { + callback(); + break; + } + directories.add(path); + this.fs.realpath(path, (err, _realPath) => { + if (err) return callback(err); + const realPath = /** @type {string} */ (_realPath); + if (realPath !== path) { + directorySymlinks.add(path); + resolveFiles.add(path); + if (directories.has(realPath)) return callback(); + directories.add(realPath); + } + push({ + type: RBDT_DIRECTORY_DEPENDENCIES, + context: undefined, + path: realPath, + expected: undefined, + issuer: job + }); + callback(); + }); + break; + } + case RBDT_FILE_DEPENDENCIES: { + // Check for known files without dependencies + if (/\.json5?$|\.yarn-integrity$|yarn\.lock$|\.ya?ml/.test(path)) { + process.nextTick(callback); + break; + } + // Check commonjs cache for the module + /** @type {NodeModule} */ + const module = require.cache[path]; + if (module && Array.isArray(module.children)) { + children: for (const child of module.children) { + let childPath = child.filename; + if (childPath) { + push({ + type: RBDT_FILE, + context: undefined, + path: childPath, + expected: undefined, + issuer: job + }); + const context = dirname(this.fs, path); + for (const modulePath of module.paths) { + if (childPath.startsWith(modulePath)) { + let subPath = childPath.slice(modulePath.length + 1); + const packageMatch = /^(@[^\\/]+[\\/])[^\\/]+/.exec( + subPath + ); + if (packageMatch) { + push({ + type: RBDT_FILE, + context: undefined, + path: + modulePath + + childPath[modulePath.length] + + packageMatch[0] + + childPath[modulePath.length] + + "package.json", + expected: false, + issuer: job + }); + } + let request = subPath.replace(/\\/g, "/"); + if (request.endsWith(".js")) + request = request.slice(0, -3); + push({ + type: RBDT_RESOLVE_CJS_FILE_AS_CHILD, + context, + path: request, + expected: child.filename, + issuer: job + }); + continue children; + } + } + let request = relative(this.fs, context, childPath); + if (request.endsWith(".js")) request = request.slice(0, -3); + request = request.replace(/\\/g, "/"); + if (!request.startsWith("../")) request = `./${request}`; + push({ + type: RBDT_RESOLVE_CJS_FILE, + context, + path: request, + expected: child.filename, + issuer: job + }); } - source.add(Template.toComment(`${code}`) + "\n"); } + } else if (supportsEsm && /\.m?js$/.test(path)) { + if (!this._warnAboutExperimentalEsmTracking) { + this.logger.log( + "Node.js doesn't offer a (nice) way to introspect the ESM dependency graph yet.\n" + + "Until a full solution is available webpack uses an experimental ESM tracking based on parsing.\n" + + "As best effort webpack parses the ESM files to guess dependencies. But this can lead to expensive and incorrect tracking." + ); + this._warnAboutExperimentalEsmTracking = true; + } + const lexer = __webpack_require__(79366); + lexer.init.then(() => { + this.fs.readFile(path, (err, content) => { + if (err) return callback(err); + try { + const context = dirname(this.fs, path); + const source = content.toString(); + const [imports] = lexer.parse(source); + for (const imp of imports) { + try { + let dependency; + if (imp.d === -1) { + // import ... from "..." + dependency = parseString( + source.substring(imp.s - 1, imp.e + 1) + ); + } else if (imp.d > -1) { + // import() + let expr = source.substring(imp.s, imp.e).trim(); + dependency = parseString(expr); + } else { + // e.g. import.meta + continue; + } + push({ + type: RBDT_RESOLVE_ESM_FILE, + context, + path: dependency, + expected: undefined, + issuer: job + }); + } catch (e) { + this.logger.warn( + `Parsing of ${path} for build dependencies failed at 'import(${source.substring( + imp.s, + imp.e + )})'.\n` + + "Build dependencies behind this expression are ignored and might cause incorrect cache invalidation." + ); + this.logger.debug(pathToString(job)); + this.logger.debug(e.stack); + } + } + } catch (e) { + this.logger.warn( + `Parsing of ${path} for build dependencies failed and all dependencies of this file are ignored, which might cause incorrect cache invalidation..` + ); + this.logger.debug(pathToString(job)); + this.logger.debug(e.stack); + } + process.nextTick(callback); + }); + }, callback); + break; + } else { + this.logger.log( + `Assuming ${path} has no dependencies as we were unable to assign it to any module system.` + ); + this.logger.debug(pathToString(job)); } - source.add(moduleSource); - return source; - } else { - source.add(moduleSource); - const cachedSource = new CachedSource(source); - cacheEntry.full.set(moduleSource, cachedSource); - return cachedSource; + process.nextTick(callback); + break; + } + case RBDT_DIRECTORY_DEPENDENCIES: { + const match = + /(^.+[\\/]node_modules[\\/](?:@[^\\/]+[\\/])?[^\\/]+)/.exec(path); + const packagePath = match ? match[1] : path; + const packageJson = join(this.fs, packagePath, "package.json"); + this.fs.readFile(packageJson, (err, content) => { + if (err) { + if (err.code === "ENOENT") { + resolveMissing.add(packageJson); + const parent = dirname(this.fs, packagePath); + if (parent !== packagePath) { + push({ + type: RBDT_DIRECTORY_DEPENDENCIES, + context: undefined, + path: parent, + expected: undefined, + issuer: job + }); + } + callback(); + return; + } + return callback(err); + } + resolveFiles.add(packageJson); + let packageData; + try { + packageData = JSON.parse(content.toString("utf-8")); + } catch (e) { + return callback(e); + } + const depsObject = packageData.dependencies; + const optionalDepsObject = packageData.optionalDependencies; + const allDeps = new Set(); + const optionalDeps = new Set(); + if (typeof depsObject === "object" && depsObject) { + for (const dep of Object.keys(depsObject)) { + allDeps.add(dep); + } + } + if ( + typeof optionalDepsObject === "object" && + optionalDepsObject + ) { + for (const dep of Object.keys(optionalDepsObject)) { + allDeps.add(dep); + optionalDeps.add(dep); + } + } + for (const dep of allDeps) { + push({ + type: RBDT_RESOLVE_DIRECTORY, + context: packagePath, + path: dep, + expected: !optionalDeps.has(dep), + issuer: job + }); + } + callback(); + }); + break; } } - ); - hooks.chunkHash.tap("ModuleInfoHeaderPlugin", (chunk, hash) => { - hash.update("ModuleInfoHeaderPlugin"); - hash.update("1"); - }); - }); - } -} -module.exports = ModuleInfoHeaderPlugin; - - -/***/ }), - -/***/ 82908: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ - - - -const WebpackError = __webpack_require__(68422); - -/** @typedef {import("./Dependency").DependencyLocation} DependencyLocation */ -/** @typedef {import("./Module")} Module */ - -const previouslyPolyfilledBuiltinModules = { - assert: "assert/", - buffer: "buffer/", - console: "console-browserify", - constants: "constants-browserify", - crypto: "crypto-browserify", - domain: "domain-browser", - events: "events/", - http: "stream-http", - https: "https-browserify", - os: "os-browserify/browser", - path: "path-browserify", - punycode: "punycode/", - process: "process/browser", - querystring: "querystring-es3", - stream: "stream-browserify", - _stream_duplex: "readable-stream/duplex", - _stream_passthrough: "readable-stream/passthrough", - _stream_readable: "readable-stream/readable", - _stream_transform: "readable-stream/transform", - _stream_writable: "readable-stream/writable", - string_decoder: "string_decoder/", - sys: "util/", - timers: "timers-browserify", - tty: "tty-browserify", - url: "url/", - util: "util/", - vm: "vm-browserify", - zlib: "browserify-zlib" -}; - -class ModuleNotFoundError extends WebpackError { - /** - * @param {Module} module module tied to dependency - * @param {Error&any} err error thrown - * @param {DependencyLocation} loc location of dependency - */ - constructor(module, err, loc) { - let message = `Module not found: ${err.toString()}`; - - // TODO remove in webpack 6 - const match = err.message.match(/Can't resolve '([^']+)'/); - if (match) { - const request = match[1]; - const alias = previouslyPolyfilledBuiltinModules[request]; - if (alias) { - const pathIndex = alias.indexOf("/"); - const dependency = pathIndex > 0 ? alias.slice(0, pathIndex) : alias; - message += - "\n\n" + - "BREAKING CHANGE: " + - "webpack < 5 used to include polyfills for node.js core modules by default.\n" + - "This is no longer the case. Verify if you need this module and configure a polyfill for it.\n\n"; - message += - "If you want to include a polyfill, you need to:\n" + - `\t- add a fallback 'resolve.fallback: { "${request}": require.resolve("${alias}") }'\n` + - `\t- install '${dependency}'\n`; - message += - "If you don't want to include a polyfill, you can use an empty module like this:\n" + - `\tresolve.fallback: { "${request}": false }`; - } - } - - super(message); - - this.name = "ModuleNotFoundError"; - this.details = err.details; - this.module = module; - this.error = err; - this.loc = loc; - } -} - -module.exports = ModuleNotFoundError; - - -/***/ }), - -/***/ 13110: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ - - - -const WebpackError = __webpack_require__(68422); -const makeSerializable = __webpack_require__(26522); - -const WASM_HEADER = Buffer.from([0x00, 0x61, 0x73, 0x6d]); + }, + err => { + if (err) return callback(err); + for (const l of fileSymlinks) files.delete(l); + for (const l of directorySymlinks) directories.delete(l); + for (const k of invalidResolveResults) resolveResults.delete(k); + callback(null, { + files, + directories, + missing, + resolveResults, + resolveDependencies: { + files: resolveFiles, + directories: resolveDirectories, + missing: resolveMissing + } + }); + } + ); + } -class ModuleParseError extends WebpackError { /** - * @param {string | Buffer} source source code - * @param {Error&any} err the parse error - * @param {string[]} loaders the loaders used - * @param {string} type module type + * @param {Map} resolveResults results from resolving + * @param {function(Error=, boolean=): void} callback callback with true when resolveResults resolve the same way + * @returns {void} */ - constructor(source, err, loaders, type) { - let message = "Module parse failed: " + (err && err.message); - let loc = undefined; - - if ( - ((Buffer.isBuffer(source) && source.slice(0, 4).equals(WASM_HEADER)) || - (typeof source === "string" && /^\0asm/.test(source))) && - !type.startsWith("webassembly") - ) { - message += - "\nThe module seem to be a WebAssembly module, but module is not flagged as WebAssembly module for webpack."; - message += - "\nBREAKING CHANGE: Since webpack 5 WebAssembly is not enabled by default and flagged as experimental feature."; - message += - "\nYou need to enable one of the WebAssembly experiments via 'experiments.asyncWebAssembly: true' (based on async modules) or 'experiments.syncWebAssembly: true' (like webpack 4, deprecated)."; - message += - "\nFor files that transpile to WebAssembly, make sure to set the module type in the 'module.rules' section of the config (e. g. 'type: \"webassembly/async\"')."; - } else if (!loaders) { - message += - "\nYou may need an appropriate loader to handle this file type."; - } else if (loaders.length >= 1) { - message += `\nFile was processed with these loaders:${loaders - .map(loader => `\n * ${loader}`) - .join("")}`; - message += - "\nYou may need an additional loader to handle the result of these loaders."; - } else { - message += - "\nYou may need an appropriate loader to handle this file type, currently no loaders are configured to process this file. See https://webpack.js.org/concepts#loaders"; - } - - if ( - err && - err.loc && - typeof err.loc === "object" && - typeof err.loc.line === "number" - ) { - var lineNumber = err.loc.line; - - if ( - Buffer.isBuffer(source) || - /[\0\u0001\u0002\u0003\u0004\u0005\u0006\u0007]/.test(source) - ) { - // binary file - message += "\n(Source code omitted for this binary file)"; - } else { - const sourceLines = source.split(/\r?\n/); - const start = Math.max(0, lineNumber - 3); - const linesBefore = sourceLines.slice(start, lineNumber - 1); - const theLine = sourceLines[lineNumber - 1]; - const linesAfter = sourceLines.slice(lineNumber, lineNumber + 2); - - message += - linesBefore.map(l => `\n| ${l}`).join("") + - `\n> ${theLine}` + - linesAfter.map(l => `\n| ${l}`).join(""); + checkResolveResultsValid(resolveResults, callback) { + const { resolveCjs, resolveCjsAsChild, resolveEsm, resolveContext } = + this._createBuildDependenciesResolvers(); + asyncLib.eachLimit( + resolveResults, + 20, + ([key, expectedResult], callback) => { + const [type, context, path] = key.split("\n"); + switch (type) { + case "d": + resolveContext(context, path, {}, (err, _, result) => { + if (expectedResult === false) + return callback(err ? undefined : INVALID); + if (err) return callback(err); + const resultPath = result.path; + if (resultPath !== expectedResult) return callback(INVALID); + callback(); + }); + break; + case "f": + resolveCjs(context, path, {}, (err, _, result) => { + if (expectedResult === false) + return callback(err ? undefined : INVALID); + if (err) return callback(err); + const resultPath = result.path; + if (resultPath !== expectedResult) return callback(INVALID); + callback(); + }); + break; + case "c": + resolveCjsAsChild(context, path, {}, (err, _, result) => { + if (expectedResult === false) + return callback(err ? undefined : INVALID); + if (err) return callback(err); + const resultPath = result.path; + if (resultPath !== expectedResult) return callback(INVALID); + callback(); + }); + break; + case "e": + resolveEsm(context, path, {}, (err, _, result) => { + if (expectedResult === false) + return callback(err ? undefined : INVALID); + if (err) return callback(err); + const resultPath = result.path; + if (resultPath !== expectedResult) return callback(INVALID); + callback(); + }); + break; + default: + callback(new Error("Unexpected type in resolve result key")); + break; + } + }, + /** + * @param {Error | typeof INVALID=} err error or invalid flag + * @returns {void} + */ + err => { + if (err === INVALID) { + return callback(null, false); + } + if (err) { + return callback(err); + } + return callback(null, true); } - - loc = { start: err.loc }; - } else if (err && err.stack) { - message += "\n" + err.stack; - } - - super(message); - - this.name = "ModuleParseError"; - this.loc = loc; - this.error = err; - } - - serialize(context) { - const { write } = context; - - write(this.error); - - super.serialize(context); - } - - deserialize(context) { - const { read } = context; - - this.error = read(); - - super.deserialize(context); - } -} - -makeSerializable(ModuleParseError, "webpack/lib/ModuleParseError"); - -module.exports = ModuleParseError; - - -/***/ }), - -/***/ 69631: -/***/ (function(module) { - -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ - - - -class ModuleProfile { - constructor() { - this.startTime = Date.now(); - - this.factoryStartTime = 0; - this.factoryEndTime = 0; - this.factory = 0; - this.factoryParallelismFactor = 0; - - this.restoringStartTime = 0; - this.restoringEndTime = 0; - this.restoring = 0; - this.restoringParallelismFactor = 0; - - this.integrationStartTime = 0; - this.integrationEndTime = 0; - this.integration = 0; - this.integrationParallelismFactor = 0; - - this.buildingStartTime = 0; - this.buildingEndTime = 0; - this.building = 0; - this.buildingParallelismFactor = 0; - - this.storingStartTime = 0; - this.storingEndTime = 0; - this.storing = 0; - this.storingParallelismFactor = 0; - - this.additionalFactoryTimes = undefined; - this.additionalFactories = 0; - this.additionalFactoriesParallelismFactor = 0; - - /** @deprecated */ - this.additionalIntegration = 0; - } - - markFactoryStart() { - this.factoryStartTime = Date.now(); - } - - markFactoryEnd() { - this.factoryEndTime = Date.now(); - this.factory = this.factoryEndTime - this.factoryStartTime; - } - - markRestoringStart() { - this.restoringStartTime = Date.now(); - } - - markRestoringEnd() { - this.restoringEndTime = Date.now(); - this.restoring = this.restoringEndTime - this.restoringStartTime; - } - - markIntegrationStart() { - this.integrationStartTime = Date.now(); - } - - markIntegrationEnd() { - this.integrationEndTime = Date.now(); - this.integration = this.integrationEndTime - this.integrationStartTime; - } - - markBuildingStart() { - this.buildingStartTime = Date.now(); - } - - markBuildingEnd() { - this.buildingEndTime = Date.now(); - this.building = this.buildingEndTime - this.buildingStartTime; - } - - markStoringStart() { - this.storingStartTime = Date.now(); - } - - markStoringEnd() { - this.storingEndTime = Date.now(); - this.storing = this.storingEndTime - this.storingStartTime; + ); } - // This depends on timing so we ignore it for coverage - /* istanbul ignore next */ /** - * Merge this profile into another one - * @param {ModuleProfile} realProfile the profile to merge into + * + * @param {number} startTime when processing the files has started + * @param {Iterable} files all files + * @param {Iterable} directories all directories + * @param {Iterable} missing all missing files or directories + * @param {Object} options options object (for future extensions) + * @param {boolean=} options.hash should use hash to snapshot + * @param {boolean=} options.timestamp should use timestamp to snapshot + * @param {function(WebpackError=, Snapshot=): void} callback callback function * @returns {void} */ - mergeInto(realProfile) { - realProfile.additionalFactories = this.factory; - (realProfile.additionalFactoryTimes = - realProfile.additionalFactoryTimes || []).push({ - start: this.factoryStartTime, - end: this.factoryEndTime - }); - } -} - -module.exports = ModuleProfile; - - -/***/ }), - -/***/ 93106: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ + createSnapshot(startTime, files, directories, missing, options, callback) { + /** @type {Map} */ + const fileTimestamps = new Map(); + /** @type {Map} */ + const fileHashes = new Map(); + /** @type {Map} */ + const fileTshs = new Map(); + /** @type {Map} */ + const contextTimestamps = new Map(); + /** @type {Map} */ + const contextHashes = new Map(); + /** @type {Map} */ + const contextTshs = new Map(); + /** @type {Map} */ + const missingExistence = new Map(); + /** @type {Map} */ + const managedItemInfo = new Map(); + /** @type {Set} */ + const managedFiles = new Set(); + /** @type {Set} */ + const managedContexts = new Set(); + /** @type {Set} */ + const managedMissing = new Set(); + /** @type {Set} */ + const children = new Set(); + const snapshot = new Snapshot(); + if (startTime) snapshot.setStartTime(startTime); + /** @type {Set} */ + const managedItems = new Set(); -const WebpackError = __webpack_require__(68422); + /** 1 = timestamp, 2 = hash, 3 = timestamp + hash */ + const mode = options && options.hash ? (options.timestamp ? 3 : 2) : 1; -/** @typedef {import("./Module")} Module */ + let jobs = 1; + const jobDone = () => { + if (--jobs === 0) { + if (fileTimestamps.size !== 0) { + snapshot.setFileTimestamps(fileTimestamps); + } + if (fileHashes.size !== 0) { + snapshot.setFileHashes(fileHashes); + } + if (fileTshs.size !== 0) { + snapshot.setFileTshs(fileTshs); + } + if (contextTimestamps.size !== 0) { + snapshot.setContextTimestamps(contextTimestamps); + } + if (contextHashes.size !== 0) { + snapshot.setContextHashes(contextHashes); + } + if (contextTshs.size !== 0) { + snapshot.setContextTshs(contextTshs); + } + if (missingExistence.size !== 0) { + snapshot.setMissingExistence(missingExistence); + } + if (managedItemInfo.size !== 0) { + snapshot.setManagedItemInfo(managedItemInfo); + } + this._managedFilesOptimization.optimize(snapshot, managedFiles); + if (managedFiles.size !== 0) { + snapshot.setManagedFiles(managedFiles); + } + this._managedContextsOptimization.optimize(snapshot, managedContexts); + if (managedContexts.size !== 0) { + snapshot.setManagedContexts(managedContexts); + } + this._managedMissingOptimization.optimize(snapshot, managedMissing); + if (managedMissing.size !== 0) { + snapshot.setManagedMissing(managedMissing); + } + if (children.size !== 0) { + snapshot.setChildren(children); + } + this._snapshotCache.set(snapshot, true); + this._statCreatedSnapshots++; -class ModuleRestoreError extends WebpackError { - /** - * @param {Module} module module tied to dependency - * @param {string | Error} err error thrown - */ - constructor(module, err) { - let message = "Module restore failed: "; - let details = undefined; - if (err !== null && typeof err === "object") { - if (typeof err.stack === "string" && err.stack) { - const stack = err.stack; - message += stack; - } else if (typeof err.message === "string" && err.message) { - message += err.message; - } else { - message += err; + callback(null, snapshot); + } + }; + const jobError = () => { + if (jobs > 0) { + // large negative number instead of NaN or something else to keep jobs to stay a SMI (v8) + jobs = -100000000; + callback(null, null); + } + }; + const checkManaged = (path, managedSet) => { + for (const immutablePath of this.immutablePathsRegExps) { + if (immutablePath.test(path)) { + managedSet.add(path); + return true; + } + } + for (const immutablePath of this.immutablePathsWithSlash) { + if (path.startsWith(immutablePath)) { + managedSet.add(path); + return true; + } + } + for (const managedPath of this.managedPathsRegExps) { + const match = managedPath.exec(path); + if (match) { + const managedItem = getManagedItem(match[1], path); + if (managedItem) { + managedItems.add(managedItem); + managedSet.add(path); + return true; + } + } + } + for (const managedPath of this.managedPathsWithSlash) { + if (path.startsWith(managedPath)) { + const managedItem = getManagedItem(managedPath, path); + if (managedItem) { + managedItems.add(managedItem); + managedSet.add(path); + return true; + } + } + } + return false; + }; + const captureNonManaged = (items, managedSet) => { + const capturedItems = new Set(); + for (const path of items) { + if (!checkManaged(path, managedSet)) capturedItems.add(path); + } + return capturedItems; + }; + const processCapturedFiles = capturedFiles => { + switch (mode) { + case 3: + this._fileTshsOptimization.optimize(snapshot, capturedFiles); + for (const path of capturedFiles) { + const cache = this._fileTshs.get(path); + if (cache !== undefined) { + fileTshs.set(path, cache); + } else { + jobs++; + this._getFileTimestampAndHash(path, (err, entry) => { + if (err) { + if (this.logger) { + this.logger.debug( + `Error snapshotting file timestamp hash combination of ${path}: ${err.stack}` + ); + } + jobError(); + } else { + fileTshs.set(path, entry); + jobDone(); + } + }); + } + } + break; + case 2: + this._fileHashesOptimization.optimize(snapshot, capturedFiles); + for (const path of capturedFiles) { + const cache = this._fileHashes.get(path); + if (cache !== undefined) { + fileHashes.set(path, cache); + } else { + jobs++; + this.fileHashQueue.add(path, (err, entry) => { + if (err) { + if (this.logger) { + this.logger.debug( + `Error snapshotting file hash of ${path}: ${err.stack}` + ); + } + jobError(); + } else { + fileHashes.set(path, entry); + jobDone(); + } + }); + } + } + break; + case 1: + this._fileTimestampsOptimization.optimize(snapshot, capturedFiles); + for (const path of capturedFiles) { + const cache = this._fileTimestamps.get(path); + if (cache !== undefined) { + if (cache !== "ignore") { + fileTimestamps.set(path, cache); + } + } else { + jobs++; + this.fileTimestampQueue.add(path, (err, entry) => { + if (err) { + if (this.logger) { + this.logger.debug( + `Error snapshotting file timestamp of ${path}: ${err.stack}` + ); + } + jobError(); + } else { + fileTimestamps.set(path, entry); + jobDone(); + } + }); + } + } + break; } - } else { - message += String(err); + }; + if (files) { + processCapturedFiles(captureNonManaged(files, managedFiles)); } - - super(message); - - this.name = "ModuleRestoreError"; - this.details = details; - this.module = module; - this.error = err; - } -} - -module.exports = ModuleRestoreError; - - -/***/ }), - -/***/ 84521: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ - - - -const WebpackError = __webpack_require__(68422); - -/** @typedef {import("./Module")} Module */ - -class ModuleStoreError extends WebpackError { - /** - * @param {Module} module module tied to dependency - * @param {string | Error} err error thrown - */ - constructor(module, err) { - let message = "Module storing failed: "; - let details = undefined; - if (err !== null && typeof err === "object") { - if (typeof err.stack === "string" && err.stack) { - const stack = err.stack; - message += stack; - } else if (typeof err.message === "string" && err.message) { - message += err.message; - } else { - message += err; + const processCapturedDirectories = capturedDirectories => { + switch (mode) { + case 3: + this._contextTshsOptimization.optimize(snapshot, capturedDirectories); + for (const path of capturedDirectories) { + const cache = this._contextTshs.get(path); + /** @type {ResolvedContextTimestampAndHash} */ + let resolved; + if ( + cache !== undefined && + (resolved = getResolvedTimestamp(cache)) !== undefined + ) { + contextTshs.set(path, resolved); + } else { + jobs++; + /** + * @param {Error=} err error + * @param {ResolvedContextTimestampAndHash=} entry entry + * @returns {void} + */ + const callback = (err, entry) => { + if (err) { + if (this.logger) { + this.logger.debug( + `Error snapshotting context timestamp hash combination of ${path}: ${err.stack}` + ); + } + jobError(); + } else { + contextTshs.set(path, entry); + jobDone(); + } + }; + if (cache !== undefined) { + this._resolveContextTsh(cache, callback); + } else { + this.getContextTsh(path, callback); + } + } + } + break; + case 2: + this._contextHashesOptimization.optimize( + snapshot, + capturedDirectories + ); + for (const path of capturedDirectories) { + const cache = this._contextHashes.get(path); + let resolved; + if ( + cache !== undefined && + (resolved = getResolvedHash(cache)) !== undefined + ) { + contextHashes.set(path, resolved); + } else { + jobs++; + const callback = (err, entry) => { + if (err) { + if (this.logger) { + this.logger.debug( + `Error snapshotting context hash of ${path}: ${err.stack}` + ); + } + jobError(); + } else { + contextHashes.set(path, entry); + jobDone(); + } + }; + if (cache !== undefined) { + this._resolveContextHash(cache, callback); + } else { + this.getContextHash(path, callback); + } + } + } + break; + case 1: + this._contextTimestampsOptimization.optimize( + snapshot, + capturedDirectories + ); + for (const path of capturedDirectories) { + const cache = this._contextTimestamps.get(path); + if (cache === "ignore") continue; + let resolved; + if ( + cache !== undefined && + (resolved = getResolvedTimestamp(cache)) !== undefined + ) { + contextTimestamps.set(path, resolved); + } else { + jobs++; + /** + * @param {Error=} err error + * @param {ResolvedContextFileSystemInfoEntry=} entry entry + * @returns {void} + */ + const callback = (err, entry) => { + if (err) { + if (this.logger) { + this.logger.debug( + `Error snapshotting context timestamp of ${path}: ${err.stack}` + ); + } + jobError(); + } else { + contextTimestamps.set(path, entry); + jobDone(); + } + }; + if (cache !== undefined) { + this._resolveContextTimestamp(cache, callback); + } else { + this.getContextTimestamp(path, callback); + } + } + } + break; } - } else { - message += String(err); + }; + if (directories) { + processCapturedDirectories( + captureNonManaged(directories, managedContexts) + ); } - - super(message); - - this.name = "ModuleStoreError"; - this.details = details; - this.module = module; - this.error = err; - } -} - -module.exports = ModuleStoreError; - - -/***/ }), - -/***/ 38256: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ - - - -const util = __webpack_require__(31669); -const memoize = __webpack_require__(84297); - -/** @typedef {import("webpack-sources").Source} Source */ -/** @typedef {import("./Chunk")} Chunk */ -/** @typedef {import("./ChunkGraph")} ChunkGraph */ -/** @typedef {import("./Compilation")} Compilation */ -/** @typedef {import("./DependencyTemplates")} DependencyTemplates */ -/** @typedef {import("./Module")} Module */ -/** @typedef {import("./ModuleGraph")} ModuleGraph */ -/** @typedef {import("./RuntimeTemplate")} RuntimeTemplate */ -/** @typedef {import("./util/Hash")} Hash */ - -const getJavascriptModulesPlugin = memoize(() => - __webpack_require__(76767) -); - -// TODO webpack 6: remove this class -class ModuleTemplate { - /** - * @param {RuntimeTemplate} runtimeTemplate the runtime template - * @param {Compilation} compilation the compilation - */ - constructor(runtimeTemplate, compilation) { - this._runtimeTemplate = runtimeTemplate; - this.type = "javascript"; - this.hooks = Object.freeze({ - content: { - tap: util.deprecate( - (options, fn) => { - getJavascriptModulesPlugin() - .getCompilationHooks(compilation) - .renderModuleContent.tap( - options, - (source, module, renderContext) => - fn( - source, - module, - renderContext, - renderContext.dependencyTemplates - ) - ); - }, - "ModuleTemplate.hooks.content is deprecated (use JavascriptModulesPlugin.getCompilationHooks().renderModuleContent instead)", - "DEP_MODULE_TEMPLATE_CONTENT" - ) - }, - module: { - tap: util.deprecate( - (options, fn) => { - getJavascriptModulesPlugin() - .getCompilationHooks(compilation) - .renderModuleContent.tap( - options, - (source, module, renderContext) => - fn( - source, - module, - renderContext, - renderContext.dependencyTemplates - ) - ); - }, - "ModuleTemplate.hooks.module is deprecated (use JavascriptModulesPlugin.getCompilationHooks().renderModuleContent instead)", - "DEP_MODULE_TEMPLATE_MODULE" - ) - }, - render: { - tap: util.deprecate( - (options, fn) => { - getJavascriptModulesPlugin() - .getCompilationHooks(compilation) - .renderModuleContainer.tap( - options, - (source, module, renderContext) => - fn( - source, - module, - renderContext, - renderContext.dependencyTemplates - ) - ); - }, - "ModuleTemplate.hooks.render is deprecated (use JavascriptModulesPlugin.getCompilationHooks().renderModuleContainer instead)", - "DEP_MODULE_TEMPLATE_RENDER" - ) - }, - package: { - tap: util.deprecate( - (options, fn) => { - getJavascriptModulesPlugin() - .getCompilationHooks(compilation) - .renderModulePackage.tap( - options, - (source, module, renderContext) => - fn( - source, - module, - renderContext, - renderContext.dependencyTemplates - ) + const processCapturedMissing = capturedMissing => { + this._missingExistenceOptimization.optimize(snapshot, capturedMissing); + for (const path of capturedMissing) { + const cache = this._fileTimestamps.get(path); + if (cache !== undefined) { + if (cache !== "ignore") { + missingExistence.set(path, Boolean(cache)); + } + } else { + jobs++; + this.fileTimestampQueue.add(path, (err, entry) => { + if (err) { + if (this.logger) { + this.logger.debug( + `Error snapshotting missing timestamp of ${path}: ${err.stack}` + ); + } + jobError(); + } else { + missingExistence.set(path, Boolean(entry)); + jobDone(); + } + }); + } + } + }; + if (missing) { + processCapturedMissing(captureNonManaged(missing, managedMissing)); + } + this._managedItemInfoOptimization.optimize(snapshot, managedItems); + for (const path of managedItems) { + const cache = this._managedItems.get(path); + if (cache !== undefined) { + if (cache !== "missing") { + managedFiles.add(join(this.fs, path, "package.json")); + } + managedItemInfo.set(path, cache); + } else { + jobs++; + this.managedItemQueue.add(path, (err, entry) => { + if (err) { + if (this.logger) { + this.logger.debug( + `Error snapshotting managed item ${path}: ${err.stack}` ); - }, - "ModuleTemplate.hooks.package is deprecated (use JavascriptModulesPlugin.getCompilationHooks().renderModulePackage instead)", - "DEP_MODULE_TEMPLATE_PACKAGE" - ) - }, - hash: { - tap: util.deprecate( - (options, fn) => { - compilation.hooks.fullHash.tap(options, fn); - }, - "ModuleTemplate.hooks.hash is deprecated (use Compilation.hooks.fullHash instead)", - "DEP_MODULE_TEMPLATE_HASH" - ) + } + jobError(); + } else if (entry) { + if (entry !== "missing") { + managedFiles.add(join(this.fs, path, "package.json")); + } + managedItemInfo.set(path, entry); + jobDone(); + } else { + // Fallback to normal snapshotting + const process = (set, fn) => { + if (set.size === 0) return; + const captured = new Set(); + for (const file of set) { + if (file.startsWith(path)) captured.add(file); + } + if (captured.size > 0) fn(captured); + }; + process(managedFiles, processCapturedFiles); + process(managedContexts, processCapturedDirectories); + process(managedMissing, processCapturedMissing); + jobDone(); + } + }); } - }); + } + jobDone(); } -} - -Object.defineProperty(ModuleTemplate.prototype, "runtimeTemplate", { - get: util.deprecate( - /** - * @this {ModuleTemplate} - * @returns {TODO} output options - */ - function () { - return this._runtimeTemplate; - }, - "ModuleTemplate.runtimeTemplate is deprecated (use Compilation.runtimeTemplate instead)", - "DEP_WEBPACK_CHUNK_TEMPLATE_OUTPUT_OPTIONS" - ) -}); - -module.exports = ModuleTemplate; - -/***/ }), - -/***/ 92085: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ - - - -const { cleanUp } = __webpack_require__(22569); -const WebpackError = __webpack_require__(68422); -const makeSerializable = __webpack_require__(26522); - -class ModuleWarning extends WebpackError { /** - * @param {Error} warning error thrown - * @param {{from?: string|null}} info additional info + * @param {Snapshot} snapshot1 a snapshot + * @param {Snapshot} snapshot2 a snapshot + * @returns {Snapshot} merged snapshot */ - constructor(warning, { from = null } = {}) { - let message = "Module Warning"; - - if (from) { - message += ` (from ${from}):\n`; - } else { - message += ": "; + mergeSnapshots(snapshot1, snapshot2) { + const snapshot = new Snapshot(); + if (snapshot1.hasStartTime() && snapshot2.hasStartTime()) + snapshot.setStartTime(Math.min(snapshot1.startTime, snapshot2.startTime)); + else if (snapshot2.hasStartTime()) snapshot.startTime = snapshot2.startTime; + else if (snapshot1.hasStartTime()) snapshot.startTime = snapshot1.startTime; + if (snapshot1.hasFileTimestamps() || snapshot2.hasFileTimestamps()) { + snapshot.setFileTimestamps( + mergeMaps(snapshot1.fileTimestamps, snapshot2.fileTimestamps) + ); } - - if (warning && typeof warning === "object" && warning.message) { - message += warning.message; - } else if (warning) { - message += String(warning); + if (snapshot1.hasFileHashes() || snapshot2.hasFileHashes()) { + snapshot.setFileHashes( + mergeMaps(snapshot1.fileHashes, snapshot2.fileHashes) + ); + } + if (snapshot1.hasFileTshs() || snapshot2.hasFileTshs()) { + snapshot.setFileTshs(mergeMaps(snapshot1.fileTshs, snapshot2.fileTshs)); + } + if (snapshot1.hasContextTimestamps() || snapshot2.hasContextTimestamps()) { + snapshot.setContextTimestamps( + mergeMaps(snapshot1.contextTimestamps, snapshot2.contextTimestamps) + ); + } + if (snapshot1.hasContextHashes() || snapshot2.hasContextHashes()) { + snapshot.setContextHashes( + mergeMaps(snapshot1.contextHashes, snapshot2.contextHashes) + ); + } + if (snapshot1.hasContextTshs() || snapshot2.hasContextTshs()) { + snapshot.setContextTshs( + mergeMaps(snapshot1.contextTshs, snapshot2.contextTshs) + ); + } + if (snapshot1.hasMissingExistence() || snapshot2.hasMissingExistence()) { + snapshot.setMissingExistence( + mergeMaps(snapshot1.missingExistence, snapshot2.missingExistence) + ); + } + if (snapshot1.hasManagedItemInfo() || snapshot2.hasManagedItemInfo()) { + snapshot.setManagedItemInfo( + mergeMaps(snapshot1.managedItemInfo, snapshot2.managedItemInfo) + ); + } + if (snapshot1.hasManagedFiles() || snapshot2.hasManagedFiles()) { + snapshot.setManagedFiles( + mergeSets(snapshot1.managedFiles, snapshot2.managedFiles) + ); + } + if (snapshot1.hasManagedContexts() || snapshot2.hasManagedContexts()) { + snapshot.setManagedContexts( + mergeSets(snapshot1.managedContexts, snapshot2.managedContexts) + ); + } + if (snapshot1.hasManagedMissing() || snapshot2.hasManagedMissing()) { + snapshot.setManagedMissing( + mergeSets(snapshot1.managedMissing, snapshot2.managedMissing) + ); + } + if (snapshot1.hasChildren() || snapshot2.hasChildren()) { + snapshot.setChildren(mergeSets(snapshot1.children, snapshot2.children)); + } + if ( + this._snapshotCache.get(snapshot1) === true && + this._snapshotCache.get(snapshot2) === true + ) { + this._snapshotCache.set(snapshot, true); } - - super(message); - - this.name = "ModuleWarning"; - this.warning = warning; - this.details = - warning && typeof warning === "object" && warning.stack - ? cleanUp(warning.stack, this.message) - : undefined; - } - - serialize(context) { - const { write } = context; - - write(this.warning); - - super.serialize(context); + return snapshot; } - deserialize(context) { - const { read } = context; - - this.warning = read(); - - super.deserialize(context); + /** + * @param {Snapshot} snapshot the snapshot made + * @param {function(WebpackError=, boolean=): void} callback callback function + * @returns {void} + */ + checkSnapshotValid(snapshot, callback) { + const cachedResult = this._snapshotCache.get(snapshot); + if (cachedResult !== undefined) { + this._statTestedSnapshotsCached++; + if (typeof cachedResult === "boolean") { + callback(null, cachedResult); + } else { + cachedResult.push(callback); + } + return; + } + this._statTestedSnapshotsNotCached++; + this._checkSnapshotValidNoCache(snapshot, callback); } -} - -makeSerializable(ModuleWarning, "webpack/lib/ModuleWarning"); - -module.exports = ModuleWarning; - - -/***/ }), - -/***/ 73663: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ - - -const asyncLib = __webpack_require__(36386); -const { SyncHook, MultiHook } = __webpack_require__(34718); - -const ConcurrentCompilationError = __webpack_require__(51684); -const MultiStats = __webpack_require__(76396); -const MultiWatching = __webpack_require__(22831); -const ArrayQueue = __webpack_require__(29704); - -/** @template T @typedef {import("tapable").AsyncSeriesHook} AsyncSeriesHook */ -/** @template T @template R @typedef {import("tapable").SyncBailHook} SyncBailHook */ -/** @typedef {import("../declarations/WebpackOptions").WatchOptions} WatchOptions */ -/** @typedef {import("./Compiler")} Compiler */ -/** @typedef {import("./Stats")} Stats */ -/** @typedef {import("./Watching")} Watching */ -/** @typedef {import("./util/fs").InputFileSystem} InputFileSystem */ -/** @typedef {import("./util/fs").IntermediateFileSystem} IntermediateFileSystem */ -/** @typedef {import("./util/fs").OutputFileSystem} OutputFileSystem */ -/** @typedef {import("./util/fs").WatchFileSystem} WatchFileSystem */ - -/** - * @template T - * @callback Callback - * @param {Error=} err - * @param {T=} result - */ - -/** - * @callback RunWithDependenciesHandler - * @param {Compiler} compiler - * @param {Callback} callback - */ - -/** - * @typedef {Object} MultiCompilerOptions - * @property {number=} parallelism how many Compilers are allows to run at the same time in parallel - */ - -module.exports = class MultiCompiler { /** - * @param {Compiler[] | Record} compilers child compilers - * @param {MultiCompilerOptions} options options + * @param {Snapshot} snapshot the snapshot made + * @param {function(WebpackError=, boolean=): void} callback callback function + * @returns {void} */ - constructor(compilers, options) { - if (!Array.isArray(compilers)) { - compilers = Object.keys(compilers).map(name => { - compilers[name].name = name; - return compilers[name]; - }); + _checkSnapshotValidNoCache(snapshot, callback) { + /** @type {number | undefined} */ + let startTime = undefined; + if (snapshot.hasStartTime()) { + startTime = snapshot.startTime; } - - this.hooks = Object.freeze({ - /** @type {SyncHook<[MultiStats]>} */ - done: new SyncHook(["stats"]), - /** @type {MultiHook>} */ - invalid: new MultiHook(compilers.map(c => c.hooks.invalid)), - /** @type {MultiHook>} */ - run: new MultiHook(compilers.map(c => c.hooks.run)), - /** @type {SyncHook<[]>} */ - watchClose: new SyncHook([]), - /** @type {MultiHook>} */ - watchRun: new MultiHook(compilers.map(c => c.hooks.watchRun)), - /** @type {MultiHook>} */ - infrastructureLog: new MultiHook( - compilers.map(c => c.hooks.infrastructureLog) - ) - }); - this.compilers = compilers; - /** @type {MultiCompilerOptions} */ - this._options = { - parallelism: options.parallelism || Infinity + let jobs = 1; + const jobDone = () => { + if (--jobs === 0) { + this._snapshotCache.set(snapshot, true); + callback(null, true); + } }; - /** @type {WeakMap} */ - this.dependencies = new WeakMap(); - this.running = false; - - /** @type {Stats[]} */ - const compilerStats = this.compilers.map(() => null); - let doneCompilers = 0; - for (let index = 0; index < this.compilers.length; index++) { - const compiler = this.compilers[index]; - const compilerIndex = index; - let compilerDone = false; - compiler.hooks.done.tap("MultiCompiler", stats => { - if (!compilerDone) { - compilerDone = true; - doneCompilers++; + const invalid = () => { + if (jobs > 0) { + // large negative number instead of NaN or something else to keep jobs to stay a SMI (v8) + jobs = -100000000; + this._snapshotCache.set(snapshot, false); + callback(null, false); + } + }; + const invalidWithError = (path, err) => { + if (this._remainingLogs > 0) { + this._log(path, `error occurred: %s`, err); + } + invalid(); + }; + /** + * @param {string} path file path + * @param {string} current current hash + * @param {string} snap snapshot hash + * @returns {boolean} true, if ok + */ + const checkHash = (path, current, snap) => { + if (current !== snap) { + // If hash differ it's invalid + if (this._remainingLogs > 0) { + this._log(path, `hashes differ (%s != %s)`, current, snap); } - compilerStats[compilerIndex] = stats; - if (doneCompilers === this.compilers.length) { - this.hooks.done.call(new MultiStats(compilerStats)); + return false; + } + return true; + }; + /** + * @param {string} path file path + * @param {boolean} current current entry + * @param {boolean} snap entry from snapshot + * @returns {boolean} true, if ok + */ + const checkExistence = (path, current, snap) => { + if (!current !== !snap) { + // If existence of item differs + // it's invalid + if (this._remainingLogs > 0) { + this._log( + path, + current ? "it didn't exist before" : "it does no longer exist" + ); + } + return false; + } + return true; + }; + /** + * @param {string} path file path + * @param {FileSystemInfoEntry} current current entry + * @param {FileSystemInfoEntry} snap entry from snapshot + * @param {boolean} log log reason + * @returns {boolean} true, if ok + */ + const checkFile = (path, current, snap, log = true) => { + if (current === snap) return true; + if (!checkExistence(path, Boolean(current), Boolean(snap))) return false; + if (current) { + // For existing items only + if (typeof startTime === "number" && current.safeTime > startTime) { + // If a change happened after starting reading the item + // this may no longer be valid + if (log && this._remainingLogs > 0) { + this._log( + path, + `it may have changed (%d) after the start time of the snapshot (%d)`, + current.safeTime, + startTime + ); + } + return false; + } + if ( + snap.timestamp !== undefined && + current.timestamp !== snap.timestamp + ) { + // If we have a timestamp (it was a file or symlink) and it differs from current timestamp + // it's invalid + if (log && this._remainingLogs > 0) { + this._log( + path, + `timestamps differ (%d != %d)`, + current.timestamp, + snap.timestamp + ); + } + return false; + } + } + return true; + }; + /** + * @param {string} path file path + * @param {ResolvedContextFileSystemInfoEntry} current current entry + * @param {ResolvedContextFileSystemInfoEntry} snap entry from snapshot + * @param {boolean} log log reason + * @returns {boolean} true, if ok + */ + const checkContext = (path, current, snap, log = true) => { + if (current === snap) return true; + if (!checkExistence(path, Boolean(current), Boolean(snap))) return false; + if (current) { + // For existing items only + if (typeof startTime === "number" && current.safeTime > startTime) { + // If a change happened after starting reading the item + // this may no longer be valid + if (log && this._remainingLogs > 0) { + this._log( + path, + `it may have changed (%d) after the start time of the snapshot (%d)`, + current.safeTime, + startTime + ); + } + return false; + } + if ( + snap.timestampHash !== undefined && + current.timestampHash !== snap.timestampHash + ) { + // If we have a timestampHash (it was a directory) and it differs from current timestampHash + // it's invalid + if (log && this._remainingLogs > 0) { + this._log( + path, + `timestamps hashes differ (%s != %s)`, + current.timestampHash, + snap.timestampHash + ); + } + return false; + } + } + return true; + }; + if (snapshot.hasChildren()) { + const childCallback = (err, result) => { + if (err || !result) return invalid(); + else jobDone(); + }; + for (const child of snapshot.children) { + const cache = this._snapshotCache.get(child); + if (cache !== undefined) { + this._statTestedChildrenCached++; + /* istanbul ignore else */ + if (typeof cache === "boolean") { + if (cache === false) { + invalid(); + return; + } + } else { + jobs++; + cache.push(childCallback); + } + } else { + this._statTestedChildrenNotCached++; + jobs++; + this._checkSnapshotValidNoCache(child, childCallback); + } + } + } + if (snapshot.hasFileTimestamps()) { + const { fileTimestamps } = snapshot; + this._statTestedEntries += fileTimestamps.size; + for (const [path, ts] of fileTimestamps) { + const cache = this._fileTimestamps.get(path); + if (cache !== undefined) { + if (cache !== "ignore" && !checkFile(path, cache, ts)) { + invalid(); + return; + } + } else { + jobs++; + this.fileTimestampQueue.add(path, (err, entry) => { + if (err) return invalidWithError(path, err); + if (!checkFile(path, entry, ts)) { + invalid(); + } else { + jobDone(); + } + }); + } + } + } + const processFileHashSnapshot = (path, hash) => { + const cache = this._fileHashes.get(path); + if (cache !== undefined) { + if (cache !== "ignore" && !checkHash(path, cache, hash)) { + invalid(); + return; + } + } else { + jobs++; + this.fileHashQueue.add(path, (err, entry) => { + if (err) return invalidWithError(path, err); + if (!checkHash(path, entry, hash)) { + invalid(); + } else { + jobDone(); + } + }); + } + }; + if (snapshot.hasFileHashes()) { + const { fileHashes } = snapshot; + this._statTestedEntries += fileHashes.size; + for (const [path, hash] of fileHashes) { + processFileHashSnapshot(path, hash); + } + } + if (snapshot.hasFileTshs()) { + const { fileTshs } = snapshot; + this._statTestedEntries += fileTshs.size; + for (const [path, tsh] of fileTshs) { + if (typeof tsh === "string") { + processFileHashSnapshot(path, tsh); + } else { + const cache = this._fileTimestamps.get(path); + if (cache !== undefined) { + if (cache === "ignore" || !checkFile(path, cache, tsh, false)) { + processFileHashSnapshot(path, tsh && tsh.hash); + } + } else { + jobs++; + this.fileTimestampQueue.add(path, (err, entry) => { + if (err) return invalidWithError(path, err); + if (!checkFile(path, entry, tsh, false)) { + processFileHashSnapshot(path, tsh && tsh.hash); + } + jobDone(); + }); + } + } + } + } + if (snapshot.hasContextTimestamps()) { + const { contextTimestamps } = snapshot; + this._statTestedEntries += contextTimestamps.size; + for (const [path, ts] of contextTimestamps) { + const cache = this._contextTimestamps.get(path); + if (cache === "ignore") continue; + let resolved; + if ( + cache !== undefined && + (resolved = getResolvedTimestamp(cache)) !== undefined + ) { + if (!checkContext(path, resolved, ts)) { + invalid(); + return; + } + } else { + jobs++; + /** + * @param {Error=} err error + * @param {ResolvedContextFileSystemInfoEntry=} entry entry + * @returns {void} + */ + const callback = (err, entry) => { + if (err) return invalidWithError(path, err); + if (!checkContext(path, entry, ts)) { + invalid(); + } else { + jobDone(); + } + }; + if (cache !== undefined) { + this._resolveContextTimestamp(cache, callback); + } else { + this.getContextTimestamp(path, callback); + } + } + } + } + const processContextHashSnapshot = (path, hash) => { + const cache = this._contextHashes.get(path); + let resolved; + if ( + cache !== undefined && + (resolved = getResolvedHash(cache)) !== undefined + ) { + if (!checkHash(path, resolved, hash)) { + invalid(); + return; + } + } else { + jobs++; + const callback = (err, entry) => { + if (err) return invalidWithError(path, err); + if (!checkHash(path, entry, hash)) { + invalid(); + } else { + jobDone(); + } + }; + if (cache !== undefined) { + this._resolveContextHash(cache, callback); + } else { + this.getContextHash(path, callback); + } + } + }; + if (snapshot.hasContextHashes()) { + const { contextHashes } = snapshot; + this._statTestedEntries += contextHashes.size; + for (const [path, hash] of contextHashes) { + processContextHashSnapshot(path, hash); + } + } + if (snapshot.hasContextTshs()) { + const { contextTshs } = snapshot; + this._statTestedEntries += contextTshs.size; + for (const [path, tsh] of contextTshs) { + if (typeof tsh === "string") { + processContextHashSnapshot(path, tsh); + } else { + const cache = this._contextTimestamps.get(path); + if (cache === "ignore") continue; + let resolved; + if ( + cache !== undefined && + (resolved = getResolvedTimestamp(cache)) !== undefined + ) { + if (!checkContext(path, resolved, tsh, false)) { + processContextHashSnapshot(path, tsh && tsh.hash); + } + } else { + jobs++; + /** + * @param {Error=} err error + * @param {ResolvedContextFileSystemInfoEntry=} entry entry + * @returns {void} + */ + const callback = (err, entry) => { + if (err) return invalidWithError(path, err); + if (!checkContext(path, entry, tsh, false)) { + processContextHashSnapshot(path, tsh && tsh.hash); + } + jobDone(); + }; + if (cache !== undefined) { + this._resolveContextTimestamp(cache, callback); + } else { + this.getContextTimestamp(path, callback); + } + } } - }); - compiler.hooks.invalid.tap("MultiCompiler", () => { - if (compilerDone) { - compilerDone = false; - doneCompilers--; + } + } + if (snapshot.hasMissingExistence()) { + const { missingExistence } = snapshot; + this._statTestedEntries += missingExistence.size; + for (const [path, existence] of missingExistence) { + const cache = this._fileTimestamps.get(path); + if (cache !== undefined) { + if ( + cache !== "ignore" && + !checkExistence(path, Boolean(cache), Boolean(existence)) + ) { + invalid(); + return; + } + } else { + jobs++; + this.fileTimestampQueue.add(path, (err, entry) => { + if (err) return invalidWithError(path, err); + if (!checkExistence(path, Boolean(entry), Boolean(existence))) { + invalid(); + } else { + jobDone(); + } + }); } - }); + } } - } + if (snapshot.hasManagedItemInfo()) { + const { managedItemInfo } = snapshot; + this._statTestedEntries += managedItemInfo.size; + for (const [path, info] of managedItemInfo) { + const cache = this._managedItems.get(path); + if (cache !== undefined) { + if (!checkHash(path, cache, info)) { + invalid(); + return; + } + } else { + jobs++; + this.managedItemQueue.add(path, (err, entry) => { + if (err) return invalidWithError(path, err); + if (!checkHash(path, entry, info)) { + invalid(); + } else { + jobDone(); + } + }); + } + } + } + jobDone(); - get options() { - return Object.assign( - this.compilers.map(c => c.options), - this._options - ); + // if there was an async action + // try to join multiple concurrent request for this snapshot + if (jobs > 0) { + const callbacks = [callback]; + callback = (err, result) => { + for (const callback of callbacks) callback(err, result); + }; + this._snapshotCache.set(snapshot, callbacks); + } } - get outputPath() { - let commonPath = this.compilers[0].outputPath; - for (const compiler of this.compilers) { - while ( - compiler.outputPath.indexOf(commonPath) !== 0 && - /[/\\]/.test(commonPath) - ) { - commonPath = commonPath.replace(/[/\\][^/\\]*$/, ""); + _readFileTimestamp(path, callback) { + this.fs.stat(path, (err, stat) => { + if (err) { + if (err.code === "ENOENT") { + this._fileTimestamps.set(path, null); + this._cachedDeprecatedFileTimestamps = undefined; + return callback(null, null); + } + return callback(err); } - } - if (!commonPath && this.compilers[0].outputPath[0] === "/") return "/"; - return commonPath; - } + let ts; + if (stat.isDirectory()) { + ts = { + safeTime: 0, + timestamp: undefined + }; + } else { + const mtime = +stat.mtime; - get inputFileSystem() { - throw new Error("Cannot read inputFileSystem of a MultiCompiler"); - } + if (mtime) applyMtime(mtime); - get outputFileSystem() { - throw new Error("Cannot read outputFileSystem of a MultiCompiler"); - } + ts = { + safeTime: mtime ? mtime + FS_ACCURACY : Infinity, + timestamp: mtime + }; + } - get watchFileSystem() { - throw new Error("Cannot read watchFileSystem of a MultiCompiler"); - } + this._fileTimestamps.set(path, ts); + this._cachedDeprecatedFileTimestamps = undefined; - get intermediateFileSystem() { - throw new Error("Cannot read outputFileSystem of a MultiCompiler"); + callback(null, ts); + }); } - /** - * @param {InputFileSystem} value the new input file system - */ - set inputFileSystem(value) { - for (const compiler of this.compilers) { - compiler.inputFileSystem = value; - } - } + _readFileHash(path, callback) { + this.fs.readFile(path, (err, content) => { + if (err) { + if (err.code === "EISDIR") { + this._fileHashes.set(path, "directory"); + return callback(null, "directory"); + } + if (err.code === "ENOENT") { + this._fileHashes.set(path, null); + return callback(null, null); + } + if (err.code === "ERR_FS_FILE_TOO_LARGE") { + this.logger.warn(`Ignoring ${path} for hashing as it's very large`); + this._fileHashes.set(path, "too large"); + return callback(null, "too large"); + } + return callback(err); + } - /** - * @param {OutputFileSystem} value the new output file system - */ - set outputFileSystem(value) { - for (const compiler of this.compilers) { - compiler.outputFileSystem = value; - } - } + const hash = createHash(this._hashFunction); - /** - * @param {WatchFileSystem} value the new watch file system - */ - set watchFileSystem(value) { - for (const compiler of this.compilers) { - compiler.watchFileSystem = value; - } - } + hash.update(content); - /** - * @param {IntermediateFileSystem} value the new intermediate file system - */ - set intermediateFileSystem(value) { - for (const compiler of this.compilers) { - compiler.intermediateFileSystem = value; - } - } + const digest = /** @type {string} */ (hash.digest("hex")); - getInfrastructureLogger(name) { - return this.compilers[0].getInfrastructureLogger(name); - } + this._fileHashes.set(path, digest); - /** - * @param {Compiler} compiler the child compiler - * @param {string[]} dependencies its dependencies - * @returns {void} - */ - setDependencies(compiler, dependencies) { - this.dependencies.set(compiler, dependencies); + callback(null, digest); + }); } - /** - * @param {Callback} callback signals when the validation is complete - * @returns {boolean} true if the dependencies are valid - */ - validateDependencies(callback) { - /** @type {Set<{source: Compiler, target: Compiler}>} */ - const edges = new Set(); - /** @type {string[]} */ - const missing = []; - const targetFound = compiler => { - for (const edge of edges) { - if (edge.target === compiler) { - return true; - } - } - return false; - }; - const sortEdges = (e1, e2) => { - return ( - e1.source.name.localeCompare(e2.source.name) || - e1.target.name.localeCompare(e2.target.name) - ); - }; - for (const source of this.compilers) { - const dependencies = this.dependencies.get(source); - if (dependencies) { - for (const dep of dependencies) { - const target = this.compilers.find(c => c.name === dep); - if (!target) { - missing.push(dep); - } else { - edges.add({ - source, - target - }); - } + _getFileTimestampAndHash(path, callback) { + const continueWithHash = hash => { + const cache = this._fileTimestamps.get(path); + if (cache !== undefined) { + if (cache !== "ignore") { + const result = { + ...cache, + hash + }; + this._fileTshs.set(path, result); + return callback(null, result); + } else { + this._fileTshs.set(path, hash); + return callback(null, hash); } - } - } - /** @type {string[]} */ - const errors = missing.map(m => `Compiler dependency \`${m}\` not found.`); - const stack = this.compilers.filter(c => !targetFound(c)); - while (stack.length > 0) { - const current = stack.pop(); - for (const edge of edges) { - if (edge.source === current) { - edges.delete(edge); - const target = edge.target; - if (!targetFound(target)) { - stack.push(target); + } else { + this.fileTimestampQueue.add(path, (err, entry) => { + if (err) { + return callback(err); } - } + const result = { + ...entry, + hash + }; + this._fileTshs.set(path, result); + return callback(null, result); + }); } - } - if (edges.size > 0) { - /** @type {string[]} */ - const lines = Array.from(edges) - .sort(sortEdges) - .map(edge => `${edge.source.name} -> ${edge.target.name}`); - lines.unshift("Circular dependency found in compiler dependencies."); - errors.unshift(lines.join("\n")); - } - if (errors.length > 0) { - const message = errors.join("\n"); - callback(new Error(message)); - return false; - } - return true; - } + }; - // TODO webpack 6 remove - /** - * @deprecated This method should have been private - * @param {Compiler[]} compilers the child compilers - * @param {RunWithDependenciesHandler} fn a handler to run for each compiler - * @param {Callback} callback the compiler's handler - * @returns {void} - */ - runWithDependencies(compilers, fn, callback) { - const fulfilledNames = new Set(); - let remainingCompilers = compilers; - const isDependencyFulfilled = d => fulfilledNames.has(d); - const getReadyCompilers = () => { - let readyCompilers = []; - let list = remainingCompilers; - remainingCompilers = []; - for (const c of list) { - const dependencies = this.dependencies.get(c); - const ready = - !dependencies || dependencies.every(isDependencyFulfilled); - if (ready) { - readyCompilers.push(c); - } else { - remainingCompilers.push(c); + const cache = this._fileHashes.get(path); + if (cache !== undefined) { + continueWithHash(cache); + } else { + this.fileHashQueue.add(path, (err, entry) => { + if (err) { + return callback(err); } - } - return readyCompilers; - }; - const runCompilers = callback => { - if (remainingCompilers.length === 0) return callback(); - asyncLib.map( - getReadyCompilers(), - (compiler, callback) => { - fn(compiler, err => { - if (err) return callback(err); - fulfilledNames.add(compiler.name); - runCompilers(callback); - }); - }, - callback - ); - }; - runCompilers(callback); + continueWithHash(entry); + }); + } } /** - * @template SetupResult - * @param {function(Compiler, number, Callback, function(): boolean, function(): void, function(): void): SetupResult} setup setup a single compiler - * @param {function(Compiler, SetupResult, Callback): void} run run/continue a single compiler - * @param {Callback} callback callback when all compilers are done, result includes Stats of all changed compilers - * @returns {SetupResult[]} result of setup + * @template T + * @template ItemType + * @param {Object} options options + * @param {string} options.path path + * @param {function(string): ItemType} options.fromImmutablePath called when context item is an immutable path + * @param {function(string): ItemType} options.fromManagedItem called when context item is a managed path + * @param {function(string, string, function(Error=, ItemType=): void): void} options.fromSymlink called when context item is a symlink + * @param {function(string, IStats, function(Error=, ItemType=): void): void} options.fromFile called when context item is a file + * @param {function(string, IStats, function(Error=, ItemType=): void): void} options.fromDirectory called when context item is a directory + * @param {function(string[], ItemType[]): T} options.reduce called from all context items + * @param {function(Error=, (T)=): void} callback callback */ - _runGraph(setup, run, callback) { - /** @typedef {{ compiler: Compiler, setupResult: SetupResult, result: Stats, state: "pending" | "blocked" | "queued" | "starting" | "running" | "running-outdated" | "done", children: Node[], parents: Node[] }} Node */ - - // State transitions for nodes: - // -> blocked (initial) - // blocked -> starting [running++] (when all parents done) - // queued -> starting [running++] (when processing the queue) - // starting -> running (when run has been called) - // running -> done [running--] (when compilation is done) - // done -> pending (when invalidated from file change) - // pending -> blocked [add to queue] (when invalidated from aggregated changes) - // done -> blocked [add to queue] (when invalidated, from parent invalidation) - // running -> running-outdated (when invalidated, either from change or parent invalidation) - // running-outdated -> blocked [running--] (when compilation is done) - - /** @type {Node[]} */ - const nodes = this.compilers.map(compiler => ({ - compiler, - setupResult: undefined, - result: undefined, - state: "blocked", - children: [], - parents: [] - })); - /** @type {Map} */ - const compilerToNode = new Map(); - for (const node of nodes) compilerToNode.set(node.compiler.name, node); - for (const node of nodes) { - const dependencies = this.dependencies.get(node.compiler); - if (!dependencies) continue; - for (const dep of dependencies) { - const parent = compilerToNode.get(dep); - node.parents.push(parent); - parent.children.push(node); - } - } - /** @type {ArrayQueue} */ - const queue = new ArrayQueue(); - for (const node of nodes) { - if (node.parents.length === 0) { - node.state = "queued"; - queue.enqueue(node); - } - } - let errored = false; - let running = 0; - const parallelism = this._options.parallelism; - /** - * @param {Node} node node - * @param {Error=} err error - * @param {Stats=} stats result - * @returns {void} - */ - const nodeDone = (node, err, stats) => { - if (errored) return; - if (err) { - errored = true; - return asyncLib.each( - nodes, - (node, callback) => { - if (node.compiler.watching) { - node.compiler.watching.close(callback); - } else { - callback(); - } - }, - () => callback(err) - ); - } - node.result = stats; - running--; - if (node.state === "running") { - node.state = "done"; - for (const child of node.children) { - if (child.state === "blocked") queue.enqueue(child); - } - } else if (node.state === "running-outdated") { - node.state = "blocked"; - queue.enqueue(node); - } - processQueue(); - }; - /** - * @param {Node} node node - * @returns {void} - */ - const nodeInvalidFromParent = node => { - if (node.state === "done") { - node.state = "blocked"; - } else if (node.state === "running") { - node.state = "running-outdated"; - } - for (const child of node.children) { - nodeInvalidFromParent(child); - } - }; - /** - * @param {Node} node node - * @returns {void} - */ - const nodeInvalid = node => { - if (node.state === "done") { - node.state = "pending"; - } else if (node.state === "running") { - node.state = "running-outdated"; - } - for (const child of node.children) { - nodeInvalidFromParent(child); - } - }; - /** - * @param {Node} node node - * @returns {void} - */ - const nodeChange = node => { - nodeInvalid(node); - if (node.state === "pending") { - node.state = "blocked"; - } - if (node.state === "blocked") { - queue.enqueue(node); - processQueue(); - } - }; - - const setupResults = []; - nodes.forEach((node, i) => { - setupResults.push( - (node.setupResult = setup( - node.compiler, - i, - nodeDone.bind(null, node), - () => node.state !== "starting" && node.state !== "running", - () => nodeChange(node), - () => nodeInvalid(node) - )) - ); - }); - let processing = true; - const processQueue = () => { - if (processing) return; - processing = true; - process.nextTick(processQueueWorker); - }; - const processQueueWorker = () => { - while (running < parallelism && queue.length > 0 && !errored) { - const node = queue.dequeue(); - if ( - node.state === "queued" || - (node.state === "blocked" && - node.parents.every(p => p.state === "done")) - ) { - running++; - node.state = "starting"; - run(node.compiler, node.setupResult, nodeDone.bind(null, node)); - node.state = "running"; + _readContext( + { + path, + fromImmutablePath, + fromManagedItem, + fromSymlink, + fromFile, + fromDirectory, + reduce + }, + callback + ) { + this.fs.readdir(path, (err, _files) => { + if (err) { + if (err.code === "ENOENT") { + return callback(null, null); } + return callback(err); } - processing = false; - if ( - !errored && - running === 0 && - nodes.every(node => node.state === "done") - ) { - const stats = []; - for (const node of nodes) { - const result = node.result; - if (result) { - node.result = undefined; - stats.push(result); + const files = /** @type {string[]} */ (_files) + .map(file => file.normalize("NFC")) + .filter(file => !/^\./.test(file)) + .sort(); + asyncLib.map( + files, + (file, callback) => { + const child = join(this.fs, path, file); + for (const immutablePath of this.immutablePathsRegExps) { + if (immutablePath.test(path)) { + // ignore any immutable path for timestamping + return callback(null, fromImmutablePath(path)); + } } + for (const immutablePath of this.immutablePathsWithSlash) { + if (path.startsWith(immutablePath)) { + // ignore any immutable path for timestamping + return callback(null, fromImmutablePath(path)); + } + } + for (const managedPath of this.managedPathsRegExps) { + const match = managedPath.exec(path); + if (match) { + const managedItem = getManagedItem(match[1], path); + if (managedItem) { + // construct timestampHash from managed info + return this.managedItemQueue.add(managedItem, (err, info) => { + if (err) return callback(err); + return callback(null, fromManagedItem(info)); + }); + } + } + } + for (const managedPath of this.managedPathsWithSlash) { + if (path.startsWith(managedPath)) { + const managedItem = getManagedItem(managedPath, child); + if (managedItem) { + // construct timestampHash from managed info + return this.managedItemQueue.add(managedItem, (err, info) => { + if (err) return callback(err); + return callback(null, fromManagedItem(info)); + }); + } + } + } + + lstatReadlinkAbsolute(this.fs, child, (err, stat) => { + if (err) return callback(err); + + if (typeof stat === "string") { + return fromSymlink(child, stat, callback); + } + + if (stat.isFile()) { + return fromFile(child, stat, callback); + } + if (stat.isDirectory()) { + return fromDirectory(child, stat, callback); + } + callback(null, null); + }); + }, + (err, results) => { + if (err) return callback(err); + const result = reduce(files, results); + callback(null, result); } - if (stats.length > 0) { - callback(null, new MultiStats(stats)); - } - } - }; - processQueueWorker(); - return setupResults; + ); + }); } - /** - * @param {WatchOptions|WatchOptions[]} watchOptions the watcher's options - * @param {Callback} handler signals when the call finishes - * @returns {MultiWatching} a compiler watcher - */ - watch(watchOptions, handler) { - if (this.running) { - return handler(new ConcurrentCompilationError()); - } - this.running = true; + _readContextTimestamp(path, callback) { + this._readContext( + { + path, + fromImmutablePath: () => null, + fromManagedItem: info => ({ + safeTime: 0, + timestampHash: info + }), + fromSymlink: (file, target, callback) => { + callback(null, { + timestampHash: target, + symlinks: new Set([target]) + }); + }, + fromFile: (file, stat, callback) => { + // Prefer the cached value over our new stat to report consistent results + const cache = this._fileTimestamps.get(file); + if (cache !== undefined) + return callback(null, cache === "ignore" ? null : cache); - if (this.validateDependencies(handler)) { - const watchings = this._runGraph( - (compiler, idx, callback, isBlocked, setChanged, setInvalid) => { - const watching = compiler.watch( - Array.isArray(watchOptions) ? watchOptions[idx] : watchOptions, - callback - ); - if (watching) { - watching._onInvalid = setInvalid; - watching._onChange = setChanged; - watching._isBlocked = isBlocked; - } - return watching; + const mtime = +stat.mtime; + + if (mtime) applyMtime(mtime); + + const ts = { + safeTime: mtime ? mtime + FS_ACCURACY : Infinity, + timestamp: mtime + }; + + this._fileTimestamps.set(file, ts); + this._cachedDeprecatedFileTimestamps = undefined; + callback(null, ts); }, - (compiler, watching, callback) => { - if (compiler.watching !== watching) return; - if (!watching.running) watching.invalidate(); + fromDirectory: (directory, stat, callback) => { + this.contextTimestampQueue.increaseParallelism(); + this._getUnresolvedContextTimestamp(directory, (err, tsEntry) => { + this.contextTimestampQueue.decreaseParallelism(); + callback(err, tsEntry); + }); }, - handler - ); - return new MultiWatching(watchings, this); - } + reduce: (files, tsEntries) => { + let symlinks = undefined; - return new MultiWatching([], this); - } + const hash = createHash(this._hashFunction); - /** - * @param {Callback} callback signals when the call finishes - * @returns {void} - */ - run(callback) { - if (this.running) { - return callback(new ConcurrentCompilationError()); - } - this.running = true; + for (const file of files) hash.update(file); + let safeTime = 0; + for (const entry of tsEntries) { + if (!entry) { + hash.update("n"); + continue; + } + if (entry.timestamp) { + hash.update("f"); + hash.update(`${entry.timestamp}`); + } else if (entry.timestampHash) { + hash.update("d"); + hash.update(`${entry.timestampHash}`); + } + if (entry.symlinks !== undefined) { + if (symlinks === undefined) symlinks = new Set(); + addAll(entry.symlinks, symlinks); + } + if (entry.safeTime) { + safeTime = Math.max(safeTime, entry.safeTime); + } + } - if (this.validateDependencies(callback)) { - this._runGraph( - () => {}, - (compiler, setupResult, callback) => compiler.run(callback), - (err, stats) => { - this.running = false; + const digest = /** @type {string} */ (hash.digest("hex")); - if (callback !== undefined) { - return callback(err, stats); - } + const result = { + safeTime, + timestampHash: digest + }; + if (symlinks) result.symlinks = symlinks; + return result; } - ); - } - } + }, + (err, result) => { + if (err) return callback(err); + this._contextTimestamps.set(path, result); + this._cachedDeprecatedContextTimestamps = undefined; - purgeInputFileSystem() { - for (const compiler of this.compilers) { - if (compiler.inputFileSystem && compiler.inputFileSystem.purge) { - compiler.inputFileSystem.purge(); + callback(null, result); } - } + ); } /** - * @param {Callback} callback signals when the compiler closes + * @param {ContextFileSystemInfoEntry} entry entry + * @param {function(Error=, ResolvedContextFileSystemInfoEntry=): void} callback callback * @returns {void} */ - close(callback) { - asyncLib.each( - this.compilers, - (compiler, callback) => { - compiler.close(callback); + _resolveContextTimestamp(entry, callback) { + const hashes = []; + let safeTime = 0; + processAsyncTree( + entry.symlinks, + 10, + (target, push, callback) => { + this._getUnresolvedContextTimestamp(target, (err, entry) => { + if (err) return callback(err); + if (entry && entry !== "ignore") { + hashes.push(entry.timestampHash); + if (entry.safeTime) { + safeTime = Math.max(safeTime, entry.safeTime); + } + if (entry.symlinks !== undefined) { + for (const target of entry.symlinks) push(target); + } + } + callback(); + }); }, - callback + err => { + if (err) return callback(err); + const hash = createHash(this._hashFunction); + hash.update(entry.timestampHash); + if (entry.safeTime) { + safeTime = Math.max(safeTime, entry.safeTime); + } + hashes.sort(); + for (const h of hashes) { + hash.update(h); + } + callback( + null, + (entry.resolved = { + safeTime, + timestampHash: /** @type {string} */ (hash.digest("hex")) + }) + ); + } ); } -}; - - -/***/ }), - -/***/ 76396: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ - - -const identifierUtils = __webpack_require__(96236); + _readContextHash(path, callback) { + this._readContext( + { + path, + fromImmutablePath: () => "", + fromManagedItem: info => info || "", + fromSymlink: (file, target, callback) => { + callback(null, { + hash: target, + symlinks: new Set([target]) + }); + }, + fromFile: (file, stat, callback) => + this.getFileHash(file, (err, hash) => { + callback(err, hash || ""); + }), + fromDirectory: (directory, stat, callback) => { + this.contextHashQueue.increaseParallelism(); + this._getUnresolvedContextHash(directory, (err, hash) => { + this.contextHashQueue.decreaseParallelism(); + callback(err, hash || ""); + }); + }, + /** + * @param {string[]} files files + * @param {(string | ContextHash)[]} fileHashes hashes + * @returns {ContextHash} reduced hash + */ + reduce: (files, fileHashes) => { + let symlinks = undefined; + const hash = createHash(this._hashFunction); -/** @typedef {import("../declarations/WebpackOptions").StatsOptions} StatsOptions */ -/** @typedef {import("./Stats")} Stats */ -/** @typedef {import("./stats/DefaultStatsFactoryPlugin").KnownStatsCompilation} KnownStatsCompilation */ -/** @typedef {import("./stats/DefaultStatsFactoryPlugin").StatsCompilation} StatsCompilation */ + for (const file of files) hash.update(file); + for (const entry of fileHashes) { + if (typeof entry === "string") { + hash.update(entry); + } else { + hash.update(entry.hash); + if (entry.symlinks) { + if (symlinks === undefined) symlinks = new Set(); + addAll(entry.symlinks, symlinks); + } + } + } -const indent = (str, prefix) => { - const rem = str.replace(/\n([^\n])/g, "\n" + prefix + "$1"); - return prefix + rem; -}; + const result = { + hash: /** @type {string} */ (hash.digest("hex")) + }; + if (symlinks) result.symlinks = symlinks; + return result; + } + }, + (err, result) => { + if (err) return callback(err); + this._contextHashes.set(path, result); + return callback(null, result); + } + ); + } -class MultiStats { /** - * @param {Stats[]} stats the child stats + * @param {ContextHash} entry context hash + * @param {function(Error=, string=): void} callback callback + * @returns {void} */ - constructor(stats) { - this.stats = stats; + _resolveContextHash(entry, callback) { + const hashes = []; + processAsyncTree( + entry.symlinks, + 10, + (target, push, callback) => { + this._getUnresolvedContextHash(target, (err, hash) => { + if (err) return callback(err); + if (hash) { + hashes.push(hash.hash); + if (hash.symlinks !== undefined) { + for (const target of hash.symlinks) push(target); + } + } + callback(); + }); + }, + err => { + if (err) return callback(err); + const hash = createHash(this._hashFunction); + hash.update(entry.hash); + hashes.sort(); + for (const h of hashes) { + hash.update(h); + } + callback( + null, + (entry.resolved = /** @type {string} */ (hash.digest("hex"))) + ); + } + ); } - get hash() { - return this.stats.map(stat => stat.hash).join(""); - } + _readContextTimestampAndHash(path, callback) { + const finalize = (timestamp, hash) => { + const result = + timestamp === "ignore" + ? hash + : { + ...timestamp, + ...hash + }; + this._contextTshs.set(path, result); + callback(null, result); + }; + const cachedHash = this._contextHashes.get(path); + const cachedTimestamp = this._contextTimestamps.get(path); + if (cachedHash !== undefined) { + if (cachedTimestamp !== undefined) { + finalize(cachedTimestamp, cachedHash); + } else { + this.contextTimestampQueue.add(path, (err, entry) => { + if (err) return callback(err); + finalize(entry, cachedHash); + }); + } + } else { + if (cachedTimestamp !== undefined) { + this.contextHashQueue.add(path, (err, entry) => { + if (err) return callback(err); + finalize(cachedTimestamp, entry); + }); + } else { + this._readContext( + { + path, + fromImmutablePath: () => null, + fromManagedItem: info => ({ + safeTime: 0, + timestampHash: info, + hash: info || "" + }), + fromSymlink: (fle, target, callback) => { + callback(null, { + timestampHash: target, + hash: target, + symlinks: new Set([target]) + }); + }, + fromFile: (file, stat, callback) => { + this._getFileTimestampAndHash(file, callback); + }, + fromDirectory: (directory, stat, callback) => { + this.contextTshQueue.increaseParallelism(); + this.contextTshQueue.add(directory, (err, result) => { + this.contextTshQueue.decreaseParallelism(); + callback(err, result); + }); + }, + /** + * @param {string[]} files files + * @param {(Partial & Partial | string | null)[]} results results + * @returns {ContextTimestampAndHash} tsh + */ + reduce: (files, results) => { + let symlinks = undefined; - /** - * @returns {boolean} true if a child compilation encountered an error - */ - hasErrors() { - return this.stats.some(stat => stat.hasErrors()); + const tsHash = createHash(this._hashFunction); + const hash = createHash(this._hashFunction); + + for (const file of files) { + tsHash.update(file); + hash.update(file); + } + let safeTime = 0; + for (const entry of results) { + if (!entry) { + tsHash.update("n"); + continue; + } + if (typeof entry === "string") { + tsHash.update("n"); + hash.update(entry); + continue; + } + if (entry.timestamp) { + tsHash.update("f"); + tsHash.update(`${entry.timestamp}`); + } else if (entry.timestampHash) { + tsHash.update("d"); + tsHash.update(`${entry.timestampHash}`); + } + if (entry.symlinks !== undefined) { + if (symlinks === undefined) symlinks = new Set(); + addAll(entry.symlinks, symlinks); + } + if (entry.safeTime) { + safeTime = Math.max(safeTime, entry.safeTime); + } + hash.update(entry.hash); + } + + const result = { + safeTime, + timestampHash: /** @type {string} */ (tsHash.digest("hex")), + hash: /** @type {string} */ (hash.digest("hex")) + }; + if (symlinks) result.symlinks = symlinks; + return result; + } + }, + (err, result) => { + if (err) return callback(err); + this._contextTshs.set(path, result); + return callback(null, result); + } + ); + } + } } /** - * @returns {boolean} true if a child compilation had a warning + * @param {ContextTimestampAndHash} entry entry + * @param {function(Error=, ResolvedContextTimestampAndHash=): void} callback callback + * @returns {void} */ - hasWarnings() { - return this.stats.some(stat => stat.hasWarnings()); + _resolveContextTsh(entry, callback) { + const hashes = []; + const tsHashes = []; + let safeTime = 0; + processAsyncTree( + entry.symlinks, + 10, + (target, push, callback) => { + this._getUnresolvedContextTsh(target, (err, entry) => { + if (err) return callback(err); + if (entry) { + hashes.push(entry.hash); + if (entry.timestampHash) tsHashes.push(entry.timestampHash); + if (entry.safeTime) { + safeTime = Math.max(safeTime, entry.safeTime); + } + if (entry.symlinks !== undefined) { + for (const target of entry.symlinks) push(target); + } + } + callback(); + }); + }, + err => { + if (err) return callback(err); + const hash = createHash(this._hashFunction); + const tsHash = createHash(this._hashFunction); + hash.update(entry.hash); + if (entry.timestampHash) tsHash.update(entry.timestampHash); + if (entry.safeTime) { + safeTime = Math.max(safeTime, entry.safeTime); + } + hashes.sort(); + for (const h of hashes) { + hash.update(h); + } + tsHashes.sort(); + for (const h of tsHashes) { + tsHash.update(h); + } + callback( + null, + (entry.resolved = { + safeTime, + timestampHash: /** @type {string} */ (tsHash.digest("hex")), + hash: /** @type {string} */ (hash.digest("hex")) + }) + ); + } + ); } - _createChildOptions(options, context) { - if (!options) { - options = {}; - } - const { children: childrenOptions = undefined, ...baseOptions } = - typeof options === "string" ? { preset: options } : options; - const children = this.stats.map((stat, idx) => { - const childOptions = Array.isArray(childrenOptions) - ? childrenOptions[idx] - : childrenOptions; - return stat.compilation.createStatsOptions( - { - ...baseOptions, - ...(typeof childOptions === "string" - ? { preset: childOptions } - : childOptions && typeof childOptions === "object" - ? childOptions - : undefined) - }, - context + _getManagedItemDirectoryInfo(path, callback) { + this.fs.readdir(path, (err, elements) => { + if (err) { + if (err.code === "ENOENT" || err.code === "ENOTDIR") { + return callback(null, EMPTY_SET); + } + return callback(err); + } + const set = new Set( + /** @type {string[]} */ (elements).map(element => + join(this.fs, path, element) + ) ); + callback(null, set); }); - return { - version: children.every(o => o.version), - hash: children.every(o => o.hash), - errorsCount: children.every(o => o.errorsCount), - warningsCount: children.every(o => o.warningsCount), - errors: children.every(o => o.errors), - warnings: children.every(o => o.warnings), - children - }; } - /** - * @param {any} options stats options - * @returns {StatsCompilation} json output - */ - toJson(options) { - options = this._createChildOptions(options, { forToString: false }); - /** @type {KnownStatsCompilation} */ - const obj = {}; - obj.children = this.stats.map((stat, idx) => { - const obj = stat.toJson(options.children[idx]); - const compilationName = stat.compilation.name; - const name = - compilationName && - identifierUtils.makePathsRelative( - options.context, - compilationName, - stat.compilation.compiler.root - ); - obj.name = name; - return obj; - }); - if (options.version) { - obj.version = obj.children[0].version; - } - if (options.hash) { - obj.hash = obj.children.map(j => j.hash).join(""); - } - const mapError = (j, obj) => { - return { - ...obj, - compilerPath: obj.compilerPath - ? `${j.name}.${obj.compilerPath}` - : j.name - }; - }; - if (options.errors) { - obj.errors = []; - for (const j of obj.children) { - for (const i of j.errors) { - obj.errors.push(mapError(j, i)); - } - } - } - if (options.warnings) { - obj.warnings = []; - for (const j of obj.children) { - for (const i of j.warnings) { - obj.warnings.push(mapError(j, i)); - } + _getManagedItemInfo(path, callback) { + const dir = dirname(this.fs, path); + this.managedItemDirectoryQueue.add(dir, (err, elements) => { + if (err) { + return callback(err); } - } - if (options.errorsCount) { - obj.errorsCount = 0; - for (const j of obj.children) { - obj.errorsCount += j.errorsCount; + if (!elements.has(path)) { + // file or directory doesn't exist + this._managedItems.set(path, "missing"); + return callback(null, "missing"); } - } - if (options.warningsCount) { - obj.warningsCount = 0; - for (const j of obj.children) { - obj.warningsCount += j.warningsCount; + // something exists + // it may be a file or directory + if ( + path.endsWith("node_modules") && + (path.endsWith("/node_modules") || path.endsWith("\\node_modules")) + ) { + // we are only interested in existence of this special directory + this._managedItems.set(path, "exists"); + return callback(null, "exists"); } - } - return obj; - } - toString(options) { - options = this._createChildOptions(options, { forToString: true }); - const results = this.stats.map((stat, idx) => { - const str = stat.toString(options.children[idx]); - const compilationName = stat.compilation.name; - const name = - compilationName && - identifierUtils - .makePathsRelative( - options.context, - compilationName, - stat.compilation.compiler.root - ) - .replace(/\|/g, " "); - if (!str) return str; - return name ? `${name}:\n${indent(str, " ")}` : str; + // we assume it's a directory, as files shouldn't occur in managed paths + const packageJsonPath = join(this.fs, path, "package.json"); + this.fs.readFile(packageJsonPath, (err, content) => { + if (err) { + if (err.code === "ENOENT" || err.code === "ENOTDIR") { + // no package.json or path is not a directory + this.fs.readdir(path, (err, elements) => { + if ( + !err && + elements.length === 1 && + elements[0] === "node_modules" + ) { + // This is only a grouping folder e. g. used by yarn + // we are only interested in existence of this special directory + this._managedItems.set(path, "nested"); + return callback(null, "nested"); + } + this.logger.warn( + `Managed item ${path} isn't a directory or doesn't contain a package.json (see snapshot.managedPaths option)` + ); + return callback(); + }); + return; + } + return callback(err); + } + let data; + try { + data = JSON.parse(content.toString("utf-8")); + } catch (e) { + return callback(e); + } + if (!data.name) { + this.logger.warn( + `${packageJsonPath} doesn't contain a "name" property (see snapshot.managedPaths option)` + ); + return callback(); + } + const info = `${data.name || ""}@${data.version || ""}`; + this._managedItems.set(path, info); + callback(null, info); + }); }); - return results.filter(Boolean).join("\n\n"); - } -} - -module.exports = MultiStats; - - -/***/ }), - -/***/ 22831: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ - - - -const asyncLib = __webpack_require__(36386); - -/** @typedef {import("./MultiCompiler")} MultiCompiler */ -/** @typedef {import("./Watching")} Watching */ - -/** - * @template T - * @callback Callback - * @param {Error=} err - * @param {T=} result - */ - -class MultiWatching { - /** - * @param {Watching[]} watchings child compilers' watchers - * @param {MultiCompiler} compiler the compiler - */ - constructor(watchings, compiler) { - this.watchings = watchings; - this.compiler = compiler; - } - - invalidate(callback) { - if (callback) { - asyncLib.each( - this.watchings, - (watching, callback) => watching.invalidate(callback), - callback - ); - } else { - for (const watching of this.watchings) { - watching.invalidate(); - } - } } - suspend() { - for (const watching of this.watchings) { - watching.suspend(); + getDeprecatedFileTimestamps() { + if (this._cachedDeprecatedFileTimestamps !== undefined) + return this._cachedDeprecatedFileTimestamps; + const map = new Map(); + for (const [path, info] of this._fileTimestamps) { + if (info) map.set(path, typeof info === "object" ? info.safeTime : null); } + return (this._cachedDeprecatedFileTimestamps = map); } - resume() { - for (const watching of this.watchings) { - watching.resume(); + getDeprecatedContextTimestamps() { + if (this._cachedDeprecatedContextTimestamps !== undefined) + return this._cachedDeprecatedContextTimestamps; + const map = new Map(); + for (const [path, info] of this._contextTimestamps) { + if (info) map.set(path, typeof info === "object" ? info.safeTime : null); } - } - - /** - * @param {Callback} callback signals when the watcher is closed - * @returns {void} - */ - close(callback) { - asyncLib.forEach( - this.watchings, - (watching, finishedCallback) => { - watching.close(finishedCallback); - }, - err => { - this.compiler.hooks.watchClose.call(); - if (typeof callback === "function") { - this.compiler.running = false; - callback(err); - } - } - ); + return (this._cachedDeprecatedContextTimestamps = map); } } -module.exports = MultiWatching; +module.exports = FileSystemInfo; +module.exports.Snapshot = Snapshot; /***/ }), -/***/ 70760: -/***/ (function(module) { +/***/ 85310: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; /* @@ -53653,32 +47907,59 @@ module.exports = MultiWatching; +const { getEntryRuntime, mergeRuntimeOwned } = __webpack_require__(19655); + /** @typedef {import("./Compiler")} Compiler */ +/** @typedef {import("./util/runtime").RuntimeSpec} RuntimeSpec */ + +class FlagAllModulesAsUsedPlugin { + constructor(explanation) { + this.explanation = explanation; + } -class NoEmitOnErrorsPlugin { /** * Apply the plugin * @param {Compiler} compiler the compiler instance * @returns {void} */ apply(compiler) { - compiler.hooks.shouldEmit.tap("NoEmitOnErrorsPlugin", compilation => { - if (compilation.getStats().hasErrors()) return false; - }); - compiler.hooks.compilation.tap("NoEmitOnErrorsPlugin", compilation => { - compilation.hooks.shouldRecord.tap("NoEmitOnErrorsPlugin", () => { - if (compilation.getStats().hasErrors()) return false; - }); - }); + compiler.hooks.compilation.tap( + "FlagAllModulesAsUsedPlugin", + compilation => { + const moduleGraph = compilation.moduleGraph; + compilation.hooks.optimizeDependencies.tap( + "FlagAllModulesAsUsedPlugin", + modules => { + /** @type {RuntimeSpec} */ + let runtime = undefined; + for (const [name, { options }] of compilation.entries) { + runtime = mergeRuntimeOwned( + runtime, + getEntryRuntime(compilation, name, options) + ); + } + for (const module of modules) { + const exportsInfo = moduleGraph.getExportsInfo(module); + exportsInfo.setUsedInUnknownWay(runtime); + moduleGraph.addExtraReason(module, this.explanation); + if (module.factoryMeta === undefined) { + module.factoryMeta = {}; + } + module.factoryMeta.sideEffectFree = false; + } + } + ); + } + ); } } -module.exports = NoEmitOnErrorsPlugin; +module.exports = FlagAllModulesAsUsedPlugin; /***/ }), -/***/ 84991: +/***/ 395: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; @@ -53689,2783 +47970,2574 @@ module.exports = NoEmitOnErrorsPlugin; -const WebpackError = __webpack_require__(68422); - -module.exports = class NoModeWarning extends WebpackError { - constructor() { - super(); - - this.name = "NoModeWarning"; - this.message = - "configuration\n" + - "The 'mode' option has not been set, webpack will fallback to 'production' for this value.\n" + - "Set 'mode' option to 'development' or 'production' to enable defaults for each environment.\n" + - "You can also set it to 'none' to disable any default behavior. " + - "Learn more: https://webpack.js.org/configuration/mode/"; - } -}; - - -/***/ }), - -/***/ 5771: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Ivan Kopeykin @vankop -*/ - - - -const WebpackError = __webpack_require__(68422); -const makeSerializable = __webpack_require__(26522); +const asyncLib = __webpack_require__(36386); +const Queue = __webpack_require__(65753); -/** @typedef {import("./Dependency").DependencyLocation} DependencyLocation */ +/** @typedef {import("./Compiler")} Compiler */ +/** @typedef {import("./DependenciesBlock")} DependenciesBlock */ +/** @typedef {import("./Dependency")} Dependency */ +/** @typedef {import("./Dependency").ExportSpec} ExportSpec */ +/** @typedef {import("./Dependency").ExportsSpec} ExportsSpec */ +/** @typedef {import("./ExportsInfo")} ExportsInfo */ +/** @typedef {import("./Module")} Module */ -class NodeStuffInWebError extends WebpackError { +class FlagDependencyExportsPlugin { /** - * @param {DependencyLocation} loc loc - * @param {string} expression expression - * @param {string} description description + * Apply the plugin + * @param {Compiler} compiler the compiler instance + * @returns {void} */ - constructor(loc, expression, description) { - super( - `${JSON.stringify( - expression - )} has been used, it will be undefined in next major version. -${description}` - ); - - this.name = "NodeStuffInWebError"; - this.loc = loc; - } -} - -makeSerializable(NodeStuffInWebError, "webpack/lib/NodeStuffInWebError"); - -module.exports = NodeStuffInWebError; - + apply(compiler) { + compiler.hooks.compilation.tap( + "FlagDependencyExportsPlugin", + compilation => { + const moduleGraph = compilation.moduleGraph; + const cache = compilation.getCache("FlagDependencyExportsPlugin"); + compilation.hooks.finishModules.tapAsync( + "FlagDependencyExportsPlugin", + (modules, callback) => { + const logger = compilation.getLogger( + "webpack.FlagDependencyExportsPlugin" + ); + let statRestoredFromMemCache = 0; + let statRestoredFromCache = 0; + let statNoExports = 0; + let statFlaggedUncached = 0; + let statNotCached = 0; + let statQueueItemsProcessed = 0; -/***/ }), + const { moduleMemCaches } = compilation; -/***/ 14290: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + /** @type {Queue} */ + const queue = new Queue(); -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ + // Step 1: Try to restore cached provided export info from cache + logger.time("restore cached provided exports"); + asyncLib.each( + modules, + (module, callback) => { + const exportsInfo = moduleGraph.getExportsInfo(module); + if (!module.buildMeta || !module.buildMeta.exportsType) { + if (exportsInfo.otherExportsInfo.provided !== null) { + // It's a module without declared exports + statNoExports++; + exportsInfo.setHasProvideInfo(); + exportsInfo.setUnknownExportsProvided(); + return callback(); + } + } + if (typeof module.buildInfo.hash !== "string") { + statFlaggedUncached++; + // Enqueue uncacheable module for determining the exports + queue.enqueue(module); + exportsInfo.setHasProvideInfo(); + return callback(); + } + const memCache = moduleMemCaches && moduleMemCaches.get(module); + const memCacheValue = memCache && memCache.get(this); + if (memCacheValue !== undefined) { + statRestoredFromMemCache++; + exportsInfo.restoreProvided(memCacheValue); + return callback(); + } + cache.get( + module.identifier(), + module.buildInfo.hash, + (err, result) => { + if (err) return callback(err); + if (result !== undefined) { + statRestoredFromCache++; + exportsInfo.restoreProvided(result); + } else { + statNotCached++; + // Without cached info enqueue module for determining the exports + queue.enqueue(module); + exportsInfo.setHasProvideInfo(); + } + callback(); + } + ); + }, + err => { + logger.timeEnd("restore cached provided exports"); + if (err) return callback(err); + /** @type {Set} */ + const modulesToStore = new Set(); -const NodeStuffInWebError = __webpack_require__(5771); -const RuntimeGlobals = __webpack_require__(49404); -const CachedConstDependency = __webpack_require__(64177); -const ConstDependency = __webpack_require__(60864); -const { - evaluateToString, - expressionIsUnsupported -} = __webpack_require__(28723); -const { relative } = __webpack_require__(93204); -const { parseResource } = __webpack_require__(96236); + /** @type {Map>} */ + const dependencies = new Map(); -/** @typedef {import("webpack-sources").ReplaceSource} ReplaceSource */ -/** @typedef {import("./Compiler")} Compiler */ -/** @typedef {import("./Dependency")} Dependency */ -/** @typedef {import("./DependencyTemplates")} DependencyTemplates */ -/** @typedef {import("./RuntimeTemplate")} RuntimeTemplate */ + /** @type {Module} */ + let module; -class NodeStuffPlugin { - constructor(options) { - this.options = options; - } + /** @type {ExportsInfo} */ + let exportsInfo; - /** - * Apply the plugin - * @param {Compiler} compiler the compiler instance - * @returns {void} - */ - apply(compiler) { - const options = this.options; - compiler.hooks.compilation.tap( - "NodeStuffPlugin", - (compilation, { normalModuleFactory }) => { - const handler = (parser, parserOptions) => { - if (parserOptions.node === false) return; + /** @type {Map} */ + const exportsSpecsFromDependencies = new Map(); - let localOptions = options; - if (parserOptions.node) { - localOptions = { ...localOptions, ...parserOptions.node }; - } + let cacheable = true; + let changed = false; - if (localOptions.global !== false) { - const withWarning = localOptions.global === "warn"; - parser.hooks.expression - .for("global") - .tap("NodeStuffPlugin", expr => { - const dep = new ConstDependency( - RuntimeGlobals.global, - expr.range, - [RuntimeGlobals.global] - ); - dep.loc = expr.loc; - parser.state.module.addPresentationalDependency(dep); + /** + * @param {DependenciesBlock} depBlock the dependencies block + * @returns {void} + */ + const processDependenciesBlock = depBlock => { + for (const dep of depBlock.dependencies) { + processDependency(dep); + } + for (const block of depBlock.blocks) { + processDependenciesBlock(block); + } + }; - // TODO webpack 6 remove - if (withWarning) { - parser.state.module.addWarning( - new NodeStuffInWebError( - dep.loc, - "global", - "The global namespace object is Node.js feature and doesn't present in browser." - ) - ); - } - }); - } + /** + * @param {Dependency} dep the dependency + * @returns {void} + */ + const processDependency = dep => { + const exportDesc = dep.getExports(moduleGraph); + if (!exportDesc) return; + exportsSpecsFromDependencies.set(dep, exportDesc); + }; - const setModuleConstant = (expressionName, fn, warning) => { - parser.hooks.expression - .for(expressionName) - .tap("NodeStuffPlugin", expr => { - const dep = new CachedConstDependency( - JSON.stringify(fn(parser.state.module)), - expr.range, - expressionName - ); - dep.loc = expr.loc; - parser.state.module.addPresentationalDependency(dep); + /** + * @param {Dependency} dep dependency + * @param {ExportsSpec} exportDesc info + * @returns {void} + */ + const processExportsSpec = (dep, exportDesc) => { + const exports = exportDesc.exports; + const globalCanMangle = exportDesc.canMangle; + const globalFrom = exportDesc.from; + const globalPriority = exportDesc.priority; + const globalTerminalBinding = + exportDesc.terminalBinding || false; + const exportDeps = exportDesc.dependencies; + if (exportDesc.hideExports) { + for (const name of exportDesc.hideExports) { + const exportInfo = exportsInfo.getExportInfo(name); + exportInfo.unsetTarget(dep); + } + } + if (exports === true) { + // unknown exports + if ( + exportsInfo.setUnknownExportsProvided( + globalCanMangle, + exportDesc.excludeExports, + globalFrom && dep, + globalFrom, + globalPriority + ) + ) { + changed = true; + } + } else if (Array.isArray(exports)) { + /** + * merge in new exports + * @param {ExportsInfo} exportsInfo own exports info + * @param {(ExportSpec | string)[]} exports list of exports + */ + const mergeExports = (exportsInfo, exports) => { + for (const exportNameOrSpec of exports) { + let name; + let canMangle = globalCanMangle; + let terminalBinding = globalTerminalBinding; + let exports = undefined; + let from = globalFrom; + let fromExport = undefined; + let priority = globalPriority; + let hidden = false; + if (typeof exportNameOrSpec === "string") { + name = exportNameOrSpec; + } else { + name = exportNameOrSpec.name; + if (exportNameOrSpec.canMangle !== undefined) + canMangle = exportNameOrSpec.canMangle; + if (exportNameOrSpec.export !== undefined) + fromExport = exportNameOrSpec.export; + if (exportNameOrSpec.exports !== undefined) + exports = exportNameOrSpec.exports; + if (exportNameOrSpec.from !== undefined) + from = exportNameOrSpec.from; + if (exportNameOrSpec.priority !== undefined) + priority = exportNameOrSpec.priority; + if (exportNameOrSpec.terminalBinding !== undefined) + terminalBinding = exportNameOrSpec.terminalBinding; + if (exportNameOrSpec.hidden !== undefined) + hidden = exportNameOrSpec.hidden; + } + const exportInfo = exportsInfo.getExportInfo(name); - // TODO webpack 6 remove - if (warning) { - parser.state.module.addWarning( - new NodeStuffInWebError(dep.loc, expressionName, warning) - ); - } + if ( + exportInfo.provided === false || + exportInfo.provided === null + ) { + exportInfo.provided = true; + changed = true; + } - return true; - }); - }; + if ( + exportInfo.canMangleProvide !== false && + canMangle === false + ) { + exportInfo.canMangleProvide = false; + changed = true; + } - const setConstant = (expressionName, value, warning) => - setModuleConstant(expressionName, () => value, warning); + if (terminalBinding && !exportInfo.terminalBinding) { + exportInfo.terminalBinding = true; + changed = true; + } - const context = compiler.context; - if (localOptions.__filename) { - switch (localOptions.__filename) { - case "mock": - setConstant("__filename", "/index.js"); - break; - case "warn-mock": - setConstant( - "__filename", - "/index.js", - "The __filename is Node.js feature and doesn't present in browser." - ); - break; - case true: - setModuleConstant("__filename", module => - relative(compiler.inputFileSystem, context, module.resource) - ); - break; - } + if (exports) { + const nestedExportsInfo = + exportInfo.createNestedExportsInfo(); + mergeExports(nestedExportsInfo, exports); + } - parser.hooks.evaluateIdentifier - .for("__filename") - .tap("NodeStuffPlugin", expr => { - if (!parser.state.module) return; - const resource = parseResource(parser.state.module.resource); - return evaluateToString(resource.path)(expr); - }); - } - if (localOptions.__dirname) { - switch (localOptions.__dirname) { - case "mock": - setConstant("__dirname", "/"); - break; - case "warn-mock": - setConstant( - "__dirname", - "/", - "The __dirname is Node.js feature and doesn't present in browser." - ); - break; - case true: - setModuleConstant("__dirname", module => - relative(compiler.inputFileSystem, context, module.context) - ); - break; - } + if ( + from && + (hidden + ? exportInfo.unsetTarget(dep) + : exportInfo.setTarget( + dep, + from, + fromExport === undefined ? [name] : fromExport, + priority + )) + ) { + changed = true; + } - parser.hooks.evaluateIdentifier - .for("__dirname") - .tap("NodeStuffPlugin", expr => { - if (!parser.state.module) return; - return evaluateToString(parser.state.module.context)(expr); - }); - } - parser.hooks.expression - .for("require.extensions") - .tap( - "NodeStuffPlugin", - expressionIsUnsupported( - parser, - "require.extensions is not supported by webpack. Use a loader instead." - ) - ); - }; + // Recalculate target exportsInfo + const target = exportInfo.getTarget(moduleGraph); + let targetExportsInfo = undefined; + if (target) { + const targetModuleExportsInfo = + moduleGraph.getExportsInfo(target.module); + targetExportsInfo = + targetModuleExportsInfo.getNestedExportsInfo( + target.export + ); + // add dependency for this module + const set = dependencies.get(target.module); + if (set === undefined) { + dependencies.set(target.module, new Set([module])); + } else { + set.add(module); + } + } - normalModuleFactory.hooks.parser - .for("javascript/auto") - .tap("NodeStuffPlugin", handler); - normalModuleFactory.hooks.parser - .for("javascript/dynamic") - .tap("NodeStuffPlugin", handler); - } - ); - } -} + if (exportInfo.exportsInfoOwned) { + if ( + exportInfo.exportsInfo.setRedirectNamedTo( + targetExportsInfo + ) + ) { + changed = true; + } + } else if ( + exportInfo.exportsInfo !== targetExportsInfo + ) { + exportInfo.exportsInfo = targetExportsInfo; + changed = true; + } + } + }; + mergeExports(exportsInfo, exports); + } + // store dependencies + if (exportDeps) { + cacheable = false; + for (const exportDependency of exportDeps) { + // add dependency for this module + const set = dependencies.get(exportDependency); + if (set === undefined) { + dependencies.set(exportDependency, new Set([module])); + } else { + set.add(module); + } + } + } + }; -module.exports = NodeStuffPlugin; + const notifyDependencies = () => { + const deps = dependencies.get(module); + if (deps !== undefined) { + for (const dep of deps) { + queue.enqueue(dep); + } + } + }; + logger.time("figure out provided exports"); + while (queue.length > 0) { + module = queue.dequeue(); -/***/ }), + statQueueItemsProcessed++; -/***/ 11026: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + exportsInfo = moduleGraph.getExportsInfo(module); -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ + cacheable = true; + changed = false; + exportsSpecsFromDependencies.clear(); + moduleGraph.freeze(); + processDependenciesBlock(module); + moduleGraph.unfreeze(); + for (const [ + dep, + exportsSpec + ] of exportsSpecsFromDependencies) { + processExportsSpec(dep, exportsSpec); + } + if (cacheable) { + modulesToStore.add(module); + } -const parseJson = __webpack_require__(48335); -const { getContext, runLoaders } = __webpack_require__(67578); -const querystring = __webpack_require__(71191); -const { HookMap, SyncHook, AsyncSeriesBailHook } = __webpack_require__(34718); -const { - CachedSource, - OriginalSource, - RawSource, - SourceMapSource -} = __webpack_require__(96192); -const Compilation = __webpack_require__(59622); -const HookWebpackError = __webpack_require__(89935); -const Module = __webpack_require__(85887); -const ModuleBuildError = __webpack_require__(37991); -const ModuleError = __webpack_require__(11686); -const ModuleGraphConnection = __webpack_require__(94144); -const ModuleParseError = __webpack_require__(13110); -const ModuleWarning = __webpack_require__(92085); -const RuntimeGlobals = __webpack_require__(49404); -const UnhandledSchemeError = __webpack_require__(63859); -const WebpackError = __webpack_require__(68422); -const formatLocation = __webpack_require__(57261); -const LazySet = __webpack_require__(59534); -const { isSubset } = __webpack_require__(34715); -const { getScheme } = __webpack_require__(49606); -const { - compareLocations, - concatComparators, - compareSelect, - keepOriginalOrder -} = __webpack_require__(26296); -const createHash = __webpack_require__(24123); -const { createFakeHook } = __webpack_require__(2594); -const { join } = __webpack_require__(93204); -const { - contextify, - absolutify, - makePathsRelative -} = __webpack_require__(96236); -const makeSerializable = __webpack_require__(26522); -const memoize = __webpack_require__(84297); + if (changed) { + notifyDependencies(); + } + } + logger.timeEnd("figure out provided exports"); -/** @typedef {import("webpack-sources").Source} Source */ -/** @typedef {import("../declarations/LoaderContext").NormalModuleLoaderContext} NormalModuleLoaderContext */ -/** @typedef {import("../declarations/WebpackOptions").Mode} Mode */ -/** @typedef {import("../declarations/WebpackOptions").WebpackOptionsNormalized} WebpackOptions */ -/** @typedef {import("./ChunkGraph")} ChunkGraph */ -/** @typedef {import("./Compiler")} Compiler */ -/** @typedef {import("./Dependency").UpdateHashContext} UpdateHashContext */ -/** @typedef {import("./DependencyTemplates")} DependencyTemplates */ -/** @typedef {import("./Generator")} Generator */ -/** @typedef {import("./Module").CodeGenerationContext} CodeGenerationContext */ -/** @typedef {import("./Module").CodeGenerationResult} CodeGenerationResult */ -/** @typedef {import("./Module").ConcatenationBailoutReasonContext} ConcatenationBailoutReasonContext */ -/** @typedef {import("./Module").LibIdentOptions} LibIdentOptions */ -/** @typedef {import("./Module").NeedBuildContext} NeedBuildContext */ -/** @typedef {import("./ModuleGraph")} ModuleGraph */ -/** @typedef {import("./ModuleGraphConnection").ConnectionState} ConnectionState */ -/** @typedef {import("./NormalModuleFactory")} NormalModuleFactory */ -/** @typedef {import("./Parser")} Parser */ -/** @typedef {import("./RequestShortener")} RequestShortener */ -/** @typedef {import("./ResolverFactory").ResolverWithOptions} ResolverWithOptions */ -/** @typedef {import("./RuntimeTemplate")} RuntimeTemplate */ -/** @typedef {import("./logging/Logger").Logger} WebpackLogger */ -/** @typedef {import("./util/Hash")} Hash */ -/** @typedef {import("./util/fs").InputFileSystem} InputFileSystem */ -/** @typedef {import("./util/runtime").RuntimeSpec} RuntimeSpec */ + logger.log( + `${Math.round( + (100 * (statFlaggedUncached + statNotCached)) / + (statRestoredFromMemCache + + statRestoredFromCache + + statNotCached + + statFlaggedUncached + + statNoExports) + )}% of exports of modules have been determined (${statNoExports} no declared exports, ${statNotCached} not cached, ${statFlaggedUncached} flagged uncacheable, ${statRestoredFromCache} from cache, ${statRestoredFromMemCache} from mem cache, ${ + statQueueItemsProcessed - + statNotCached - + statFlaggedUncached + } additional calculations due to dependencies)` + ); -/** - * @typedef {Object} SourceMap - * @property {number} version - * @property {string[]} sources - * @property {string} mappings - * @property {string=} file - * @property {string=} sourceRoot - * @property {string[]=} sourcesContent - * @property {string[]=} names - */ + logger.time("store provided exports into cache"); + asyncLib.each( + modulesToStore, + (module, callback) => { + if (typeof module.buildInfo.hash !== "string") { + // not cacheable + return callback(); + } + const cachedData = moduleGraph + .getExportsInfo(module) + .getRestoreProvidedData(); + const memCache = + moduleMemCaches && moduleMemCaches.get(module); + if (memCache) { + memCache.set(this, cachedData); + } + cache.store( + module.identifier(), + module.buildInfo.hash, + cachedData, + callback + ); + }, + err => { + logger.timeEnd("store provided exports into cache"); + callback(err); + } + ); + } + ); + } + ); -const getInvalidDependenciesModuleWarning = memoize(() => - __webpack_require__(2822) -); -const getValidate = memoize(() => __webpack_require__(79286).validate); + /** @type {WeakMap} */ + const providedExportsCache = new WeakMap(); + compilation.hooks.rebuildModule.tap( + "FlagDependencyExportsPlugin", + module => { + providedExportsCache.set( + module, + moduleGraph.getExportsInfo(module).getRestoreProvidedData() + ); + } + ); + compilation.hooks.finishRebuildingModule.tap( + "FlagDependencyExportsPlugin", + module => { + moduleGraph + .getExportsInfo(module) + .restoreProvided(providedExportsCache.get(module)); + } + ); + } + ); + } +} -const ABSOLUTE_PATH_REGEX = /^([a-zA-Z]:\\|\\\\|\/)/; +module.exports = FlagDependencyExportsPlugin; -/** - * @typedef {Object} LoaderItem - * @property {string} loader - * @property {any} options - * @property {string?} ident - * @property {string?} type - */ -/** - * @param {string} context absolute context path - * @param {string} source a source path - * @param {Object=} associatedObjectForCache an object to which the cache will be attached - * @returns {string} new source path - */ -const contextifySourceUrl = (context, source, associatedObjectForCache) => { - if (source.startsWith("webpack://")) return source; - return `webpack://${makePathsRelative( - context, - source, - associatedObjectForCache - )}`; -}; +/***/ }), -/** - * @param {string} context absolute context path - * @param {SourceMap} sourceMap a source map - * @param {Object=} associatedObjectForCache an object to which the cache will be attached - * @returns {SourceMap} new source map - */ -const contextifySourceMap = (context, sourceMap, associatedObjectForCache) => { - if (!Array.isArray(sourceMap.sources)) return sourceMap; - const { sourceRoot } = sourceMap; - /** @type {function(string): string} */ - const mapper = !sourceRoot - ? source => source - : sourceRoot.endsWith("/") - ? source => - source.startsWith("/") - ? `${sourceRoot.slice(0, -1)}${source}` - : `${sourceRoot}${source}` - : source => - source.startsWith("/") - ? `${sourceRoot}${source}` - : `${sourceRoot}/${source}`; - const newSources = sourceMap.sources.map(source => - contextifySourceUrl(context, mapper(source), associatedObjectForCache) - ); - return { - ...sourceMap, - file: "x", - sourceRoot: undefined, - sources: newSources - }; -}; +/***/ 13104: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { -/** - * @param {string | Buffer} input the input - * @returns {string} the converted string - */ -const asString = input => { - if (Buffer.isBuffer(input)) { - return input.toString("utf-8"); - } - return input; -}; +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ -/** - * @param {string | Buffer} input the input - * @returns {Buffer} the converted buffer - */ -const asBuffer = input => { - if (!Buffer.isBuffer(input)) { - return Buffer.from(input, "utf-8"); - } - return input; -}; -class NonErrorEmittedError extends WebpackError { - constructor(error) { - super(); - this.name = "NonErrorEmittedError"; - this.message = "(Emitted value instead of an instance of Error) " + error; - } -} +const Dependency = __webpack_require__(50384); +const { UsageState } = __webpack_require__(4295); +const ModuleGraphConnection = __webpack_require__(94144); +const { STAGE_DEFAULT } = __webpack_require__(68145); +const ArrayQueue = __webpack_require__(29704); +const TupleQueue = __webpack_require__(54345); +const { getEntryRuntime, mergeRuntimeOwned } = __webpack_require__(19655); -makeSerializable( - NonErrorEmittedError, - "webpack/lib/NormalModule", - "NonErrorEmittedError" -); +/** @typedef {import("./Chunk")} Chunk */ +/** @typedef {import("./ChunkGroup")} ChunkGroup */ +/** @typedef {import("./Compiler")} Compiler */ +/** @typedef {import("./DependenciesBlock")} DependenciesBlock */ +/** @typedef {import("./Dependency").ReferencedExport} ReferencedExport */ +/** @typedef {import("./ExportsInfo")} ExportsInfo */ +/** @typedef {import("./Module")} Module */ +/** @typedef {import("./util/runtime").RuntimeSpec} RuntimeSpec */ -/** - * @typedef {Object} NormalModuleCompilationHooks - * @property {SyncHook<[object, NormalModule]>} loader - * @property {SyncHook<[LoaderItem[], NormalModule, object]>} beforeLoaders - * @property {SyncHook<[NormalModule]>} beforeParse - * @property {SyncHook<[NormalModule]>} beforeSnapshot - * @property {HookMap>} readResourceForScheme - * @property {HookMap>} readResource - * @property {AsyncSeriesBailHook<[NormalModule, NeedBuildContext], boolean>} needBuild - */ +const { NO_EXPORTS_REFERENCED, EXPORTS_OBJECT_REFERENCED } = Dependency; -/** @type {WeakMap} */ -const compilationHooksMap = new WeakMap(); +class FlagDependencyUsagePlugin { + /** + * @param {boolean} global do a global analysis instead of per runtime + */ + constructor(global) { + this.global = global; + } -class NormalModule extends Module { /** - * @param {Compilation} compilation the compilation - * @returns {NormalModuleCompilationHooks} the attached hooks + * Apply the plugin + * @param {Compiler} compiler the compiler instance + * @returns {void} */ - static getCompilationHooks(compilation) { - if (!(compilation instanceof Compilation)) { - throw new TypeError( - "The 'compilation' argument must be an instance of Compilation" - ); - } - let hooks = compilationHooksMap.get(compilation); - if (hooks === undefined) { - hooks = { - loader: new SyncHook(["loaderContext", "module"]), - beforeLoaders: new SyncHook(["loaders", "module", "loaderContext"]), - beforeParse: new SyncHook(["module"]), - beforeSnapshot: new SyncHook(["module"]), - // TODO webpack 6 deprecate - readResourceForScheme: new HookMap(scheme => { - const hook = hooks.readResource.for(scheme); - return createFakeHook( - /** @type {AsyncSeriesBailHook<[string, NormalModule], string | Buffer>} */ ({ - tap: (options, fn) => - hook.tap(options, loaderContext => - fn(loaderContext.resource, loaderContext._module) - ), - tapAsync: (options, fn) => - hook.tapAsync(options, (loaderContext, callback) => - fn(loaderContext.resource, loaderContext._module, callback) - ), - tapPromise: (options, fn) => - hook.tapPromise(options, loaderContext => - fn(loaderContext.resource, loaderContext._module) - ) - }) + apply(compiler) { + compiler.hooks.compilation.tap("FlagDependencyUsagePlugin", compilation => { + const moduleGraph = compilation.moduleGraph; + compilation.hooks.optimizeDependencies.tap( + { + name: "FlagDependencyUsagePlugin", + stage: STAGE_DEFAULT + }, + modules => { + if (compilation.moduleMemCaches) { + throw new Error( + "optimization.usedExports can't be used with cacheUnaffected as export usage is a global effect" + ); + } + + const logger = compilation.getLogger( + "webpack.FlagDependencyUsagePlugin" ); - }), - readResource: new HookMap( - () => new AsyncSeriesBailHook(["loaderContext"]) - ), - needBuild: new AsyncSeriesBailHook(["module", "context"]) - }; - compilationHooksMap.set(compilation, hooks); - } - return hooks; + /** @type {Map} */ + const exportInfoToModuleMap = new Map(); + + /** @type {TupleQueue<[Module, RuntimeSpec]>} */ + const queue = new TupleQueue(); + + /** + * @param {Module} module module to process + * @param {(string[] | ReferencedExport)[]} usedExports list of used exports + * @param {RuntimeSpec} runtime part of which runtime + * @param {boolean} forceSideEffects always apply side effects + * @returns {void} + */ + const processReferencedModule = ( + module, + usedExports, + runtime, + forceSideEffects + ) => { + const exportsInfo = moduleGraph.getExportsInfo(module); + if (usedExports.length > 0) { + if (!module.buildMeta || !module.buildMeta.exportsType) { + if (exportsInfo.setUsedWithoutInfo(runtime)) { + queue.enqueue(module, runtime); + } + return; + } + for (const usedExportInfo of usedExports) { + let usedExport; + let canMangle = true; + if (Array.isArray(usedExportInfo)) { + usedExport = usedExportInfo; + } else { + usedExport = usedExportInfo.name; + canMangle = usedExportInfo.canMangle !== false; + } + if (usedExport.length === 0) { + if (exportsInfo.setUsedInUnknownWay(runtime)) { + queue.enqueue(module, runtime); + } + } else { + let currentExportsInfo = exportsInfo; + for (let i = 0; i < usedExport.length; i++) { + const exportInfo = currentExportsInfo.getExportInfo( + usedExport[i] + ); + if (canMangle === false) { + exportInfo.canMangleUse = false; + } + const lastOne = i === usedExport.length - 1; + if (!lastOne) { + const nestedInfo = exportInfo.getNestedExportsInfo(); + if (nestedInfo) { + if ( + exportInfo.setUsedConditionally( + used => used === UsageState.Unused, + UsageState.OnlyPropertiesUsed, + runtime + ) + ) { + const currentModule = + currentExportsInfo === exportsInfo + ? module + : exportInfoToModuleMap.get(currentExportsInfo); + if (currentModule) { + queue.enqueue(currentModule, runtime); + } + } + currentExportsInfo = nestedInfo; + continue; + } + } + if ( + exportInfo.setUsedConditionally( + v => v !== UsageState.Used, + UsageState.Used, + runtime + ) + ) { + const currentModule = + currentExportsInfo === exportsInfo + ? module + : exportInfoToModuleMap.get(currentExportsInfo); + if (currentModule) { + queue.enqueue(currentModule, runtime); + } + } + break; + } + } + } + } else { + // for a module without side effects we stop tracking usage here when no export is used + // This module won't be evaluated in this case + // TODO webpack 6 remove this check + if ( + !forceSideEffects && + module.factoryMeta !== undefined && + module.factoryMeta.sideEffectFree + ) { + return; + } + if (exportsInfo.setUsedForSideEffectsOnly(runtime)) { + queue.enqueue(module, runtime); + } + } + }; + + /** + * @param {DependenciesBlock} module the module + * @param {RuntimeSpec} runtime part of which runtime + * @param {boolean} forceSideEffects always apply side effects + * @returns {void} + */ + const processModule = (module, runtime, forceSideEffects) => { + /** @type {Map>} */ + const map = new Map(); + + /** @type {ArrayQueue} */ + const queue = new ArrayQueue(); + queue.enqueue(module); + for (;;) { + const block = queue.dequeue(); + if (block === undefined) break; + for (const b of block.blocks) { + if ( + !this.global && + b.groupOptions && + b.groupOptions.entryOptions + ) { + processModule( + b, + b.groupOptions.entryOptions.runtime || undefined, + true + ); + } else { + queue.enqueue(b); + } + } + for (const dep of block.dependencies) { + const connection = moduleGraph.getConnection(dep); + if (!connection || !connection.module) { + continue; + } + const activeState = connection.getActiveState(runtime); + if (activeState === false) continue; + const { module } = connection; + if (activeState === ModuleGraphConnection.TRANSITIVE_ONLY) { + processModule(module, runtime, false); + continue; + } + const oldReferencedExports = map.get(module); + if (oldReferencedExports === EXPORTS_OBJECT_REFERENCED) { + continue; + } + const referencedExports = + compilation.getDependencyReferencedExports(dep, runtime); + if ( + oldReferencedExports === undefined || + oldReferencedExports === NO_EXPORTS_REFERENCED || + referencedExports === EXPORTS_OBJECT_REFERENCED + ) { + map.set(module, referencedExports); + } else if ( + oldReferencedExports !== undefined && + referencedExports === NO_EXPORTS_REFERENCED + ) { + continue; + } else { + let exportsMap; + if (Array.isArray(oldReferencedExports)) { + exportsMap = new Map(); + for (const item of oldReferencedExports) { + if (Array.isArray(item)) { + exportsMap.set(item.join("\n"), item); + } else { + exportsMap.set(item.name.join("\n"), item); + } + } + map.set(module, exportsMap); + } else { + exportsMap = oldReferencedExports; + } + for (const item of referencedExports) { + if (Array.isArray(item)) { + const key = item.join("\n"); + const oldItem = exportsMap.get(key); + if (oldItem === undefined) { + exportsMap.set(key, item); + } + // if oldItem is already an array we have to do nothing + // if oldItem is an ReferencedExport object, we don't have to do anything + // as canMangle defaults to true for arrays + } else { + const key = item.name.join("\n"); + const oldItem = exportsMap.get(key); + if (oldItem === undefined || Array.isArray(oldItem)) { + exportsMap.set(key, item); + } else { + exportsMap.set(key, { + name: item.name, + canMangle: item.canMangle && oldItem.canMangle + }); + } + } + } + } + } + } + + for (const [module, referencedExports] of map) { + if (Array.isArray(referencedExports)) { + processReferencedModule( + module, + referencedExports, + runtime, + forceSideEffects + ); + } else { + processReferencedModule( + module, + Array.from(referencedExports.values()), + runtime, + forceSideEffects + ); + } + } + }; + + logger.time("initialize exports usage"); + for (const module of modules) { + const exportsInfo = moduleGraph.getExportsInfo(module); + exportInfoToModuleMap.set(exportsInfo, module); + exportsInfo.setHasUseInfo(); + } + logger.timeEnd("initialize exports usage"); + + logger.time("trace exports usage in graph"); + + /** + * @param {Dependency} dep dependency + * @param {RuntimeSpec} runtime runtime + */ + const processEntryDependency = (dep, runtime) => { + const module = moduleGraph.getModule(dep); + if (module) { + processReferencedModule( + module, + NO_EXPORTS_REFERENCED, + runtime, + true + ); + } + }; + /** @type {RuntimeSpec} */ + let globalRuntime = undefined; + for (const [ + entryName, + { dependencies: deps, includeDependencies: includeDeps, options } + ] of compilation.entries) { + const runtime = this.global + ? undefined + : getEntryRuntime(compilation, entryName, options); + for (const dep of deps) { + processEntryDependency(dep, runtime); + } + for (const dep of includeDeps) { + processEntryDependency(dep, runtime); + } + globalRuntime = mergeRuntimeOwned(globalRuntime, runtime); + } + for (const dep of compilation.globalEntry.dependencies) { + processEntryDependency(dep, globalRuntime); + } + for (const dep of compilation.globalEntry.includeDependencies) { + processEntryDependency(dep, globalRuntime); + } + + while (queue.length) { + const [module, runtime] = queue.dequeue(); + processModule(module, runtime, false); + } + logger.timeEnd("trace exports usage in graph"); + } + ); + }); } +} - /** - * @param {Object} options options object - * @param {string=} options.layer an optional layer in which the module is - * @param {string} options.type module type - * @param {string} options.request request string - * @param {string} options.userRequest request intended by user (without loaders from config) - * @param {string} options.rawRequest request without resolving - * @param {LoaderItem[]} options.loaders list of loaders - * @param {string} options.resource path + query of the real resource - * @param {Record=} options.resourceResolveData resource resolve data - * @param {string} options.context context directory for resolving - * @param {string | undefined} options.matchResource path + query of the matched resource (virtual) - * @param {Parser} options.parser the parser used - * @param {object} options.parserOptions the options of the parser used - * @param {Generator} options.generator the generator used - * @param {object} options.generatorOptions the options of the generator used - * @param {Object} options.resolveOptions options used for resolving requests from this module - */ - constructor({ - layer, - type, - request, - userRequest, - rawRequest, - loaders, - resource, - resourceResolveData, - context, - matchResource, - parser, - parserOptions, - generator, - generatorOptions, - resolveOptions - }) { - super(type, context || getContext(resource), layer); +module.exports = FlagDependencyUsagePlugin; - // Info from Factory - /** @type {string} */ - this.request = request; - /** @type {string} */ - this.userRequest = userRequest; - /** @type {string} */ - this.rawRequest = rawRequest; - /** @type {boolean} */ - this.binary = /^(asset|webassembly)\b/.test(type); - /** @type {Parser} */ - this.parser = parser; - this.parserOptions = parserOptions; - /** @type {Generator} */ - this.generator = generator; - this.generatorOptions = generatorOptions; - /** @type {string} */ - this.resource = resource; - this.resourceResolveData = resourceResolveData; - /** @type {string | undefined} */ - this.matchResource = matchResource; - /** @type {LoaderItem[]} */ - this.loaders = loaders; - if (resolveOptions !== undefined) { - // already declared in super class - this.resolveOptions = resolveOptions; - } - // Info from Build - /** @type {WebpackError=} */ - this.error = null; - /** @private @type {Source=} */ - this._source = null; - /** @private @type {Map | undefined} **/ - this._sourceSizes = undefined; - /** @private @type {Set} */ - this._sourceTypes = undefined; +/***/ }), - // Cache - this._lastSuccessfulBuildMeta = {}; - this._forceBuild = true; - this._isEvaluatingSideEffects = false; - /** @type {WeakSet | undefined} */ - this._addedSideEffectsBailout = undefined; - } +/***/ 1826: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - /** - * @returns {string} a unique identifier of the module - */ - identifier() { - if (this.layer === null) { - if (this.type === "javascript/auto") { - return this.request; - } else { - return `${this.type}|${this.request}`; - } - } else { - return `${this.type}|${this.request}|${this.layer}`; - } - } +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ - /** - * @param {RequestShortener} requestShortener the request shortener - * @returns {string} a user readable identifier of the module - */ - readableIdentifier(requestShortener) { - return requestShortener.shorten(this.userRequest); - } - /** - * @param {LibIdentOptions} options options - * @returns {string | null} an identifier for library inclusion - */ - libIdent(options) { - return contextify( - options.context, - this.userRequest, - options.associatedObjectForCache - ); - } - /** - * @returns {string | null} absolute path which should be used for condition matching (usually the resource path) - */ - nameForCondition() { - const resource = this.matchResource || this.resource; - const idx = resource.indexOf("?"); - if (idx >= 0) return resource.substr(0, idx); - return resource; +/** @typedef {import("webpack-sources").Source} Source */ +/** @typedef {import("./ChunkGraph")} ChunkGraph */ +/** @typedef {import("./Compilation")} Compilation */ +/** @typedef {import("./ConcatenationScope")} ConcatenationScope */ +/** @typedef {import("./DependencyTemplate")} DependencyTemplate */ +/** @typedef {import("./DependencyTemplates")} DependencyTemplates */ +/** @typedef {import("./Module").ConcatenationBailoutReasonContext} ConcatenationBailoutReasonContext */ +/** @typedef {import("./ModuleGraph")} ModuleGraph */ +/** @typedef {import("./NormalModule")} NormalModule */ +/** @typedef {import("./RuntimeTemplate")} RuntimeTemplate */ +/** @typedef {import("./util/Hash")} Hash */ +/** @typedef {import("./util/runtime").RuntimeSpec} RuntimeSpec */ + +/** + * @typedef {Object} GenerateContext + * @property {DependencyTemplates} dependencyTemplates mapping from dependencies to templates + * @property {RuntimeTemplate} runtimeTemplate the runtime template + * @property {ModuleGraph} moduleGraph the module graph + * @property {ChunkGraph} chunkGraph the chunk graph + * @property {Set} runtimeRequirements the requirements for runtime + * @property {RuntimeSpec} runtime the runtime + * @property {ConcatenationScope=} concatenationScope when in concatenated module, information about other concatenated modules + * @property {string} type which kind of code should be generated + * @property {function(): Map=} getData get access to the code generation data + */ + +/** + * @typedef {Object} UpdateHashContext + * @property {NormalModule} module the module + * @property {ChunkGraph} chunkGraph + * @property {RuntimeSpec} runtime + */ + +/** + * + */ +class Generator { + static byType(map) { + return new ByTypeGenerator(map); } + /* istanbul ignore next */ /** - * Assuming this module is in the cache. Update the (cached) module with - * the fresh module from the factory. Usually updates internal references - * and properties. - * @param {Module} module fresh module - * @returns {void} + * @abstract + * @param {NormalModule} module fresh module + * @returns {Set} available types (do not mutate) */ - updateCacheModule(module) { - super.updateCacheModule(module); - const m = /** @type {NormalModule} */ (module); - this.binary = m.binary; - this.request = m.request; - this.userRequest = m.userRequest; - this.rawRequest = m.rawRequest; - this.parser = m.parser; - this.parserOptions = m.parserOptions; - this.generator = m.generator; - this.generatorOptions = m.generatorOptions; - this.resource = m.resource; - this.resourceResolveData = m.resourceResolveData; - this.context = m.context; - this.matchResource = m.matchResource; - this.loaders = m.loaders; + getTypes(module) { + const AbstractMethodError = __webpack_require__(570); + throw new AbstractMethodError(); } + /* istanbul ignore next */ /** - * Assuming this module is in the cache. Remove internal references to allow freeing some memory. + * @abstract + * @param {NormalModule} module the module + * @param {string=} type source type + * @returns {number} estimate size of the module */ - cleanupForCache() { - // Make sure to cache types and sizes before cleanup when this module has been built - // They are accessed by the stats and we don't want them to crash after cleanup - // TODO reconsider this for webpack 6 - if (this.buildInfo) { - if (this._sourceTypes === undefined) this.getSourceTypes(); - for (const type of this._sourceTypes) { - this.size(type); - } - } - super.cleanupForCache(); - this.parser = undefined; - this.parserOptions = undefined; - this.generator = undefined; - this.generatorOptions = undefined; + getSize(module, type) { + const AbstractMethodError = __webpack_require__(570); + throw new AbstractMethodError(); } + /* istanbul ignore next */ /** - * Module should be unsafe cached. Get data that's needed for that. - * This data will be passed to restoreFromUnsafeCache later. - * @returns {object} cached data + * @abstract + * @param {NormalModule} module module for which the code should be generated + * @param {GenerateContext} generateContext context for generate + * @returns {Source} generated code */ - getUnsafeCacheData() { - const data = super.getUnsafeCacheData(); - data.parserOptions = this.parserOptions; - data.generatorOptions = this.generatorOptions; - return data; - } - - restoreFromUnsafeCache(unsafeCacheData, normalModuleFactory) { - this._restoreFromUnsafeCache(unsafeCacheData, normalModuleFactory); + generate( + module, + { dependencyTemplates, runtimeTemplate, moduleGraph, type } + ) { + const AbstractMethodError = __webpack_require__(570); + throw new AbstractMethodError(); } /** - * restore unsafe cache data - * @param {object} unsafeCacheData data from getUnsafeCacheData - * @param {NormalModuleFactory} normalModuleFactory the normal module factory handling the unsafe caching + * @param {NormalModule} module module for which the bailout reason should be determined + * @param {ConcatenationBailoutReasonContext} context context + * @returns {string | undefined} reason why this module can't be concatenated, undefined when it can be concatenated */ - _restoreFromUnsafeCache(unsafeCacheData, normalModuleFactory) { - super._restoreFromUnsafeCache(unsafeCacheData, normalModuleFactory); - this.parserOptions = unsafeCacheData.parserOptions; - this.parser = normalModuleFactory.getParser(this.type, this.parserOptions); - this.generatorOptions = unsafeCacheData.generatorOptions; - this.generator = normalModuleFactory.getGenerator( - this.type, - this.generatorOptions - ); - // we assume the generator behaves identically and keep cached sourceTypes/Sizes + getConcatenationBailoutReason(module, context) { + return `Module Concatenation is not implemented for ${this.constructor.name}`; } /** - * @param {string} context the compilation context - * @param {string} name the asset name - * @param {string} content the content - * @param {string | TODO} sourceMap an optional source map - * @param {Object=} associatedObjectForCache object for caching - * @returns {Source} the created source + * @param {Hash} hash hash that will be modified + * @param {UpdateHashContext} updateHashContext context for updating hash */ - createSourceForAsset( - context, - name, - content, - sourceMap, - associatedObjectForCache - ) { - if (sourceMap) { - if ( - typeof sourceMap === "string" && - (this.useSourceMap || this.useSimpleSourceMap) - ) { - return new OriginalSource( - content, - contextifySourceUrl(context, sourceMap, associatedObjectForCache) - ); - } - - if (this.useSourceMap) { - return new SourceMapSource( - content, - name, - contextifySourceMap(context, sourceMap, associatedObjectForCache) - ); - } - } + updateHash(hash, { module, runtime }) { + // no nothing + } +} - return new RawSource(content); +class ByTypeGenerator extends Generator { + constructor(map) { + super(); + this.map = map; + this._types = new Set(Object.keys(map)); } /** - * @param {ResolverWithOptions} resolver a resolver - * @param {WebpackOptions} options webpack options - * @param {Compilation} compilation the compilation - * @param {InputFileSystem} fs file system from reading - * @param {NormalModuleCompilationHooks} hooks the hooks - * @returns {NormalModuleLoaderContext} loader context + * @param {NormalModule} module fresh module + * @returns {Set} available types (do not mutate) */ - _createLoaderContext(resolver, options, compilation, fs, hooks) { - const { requestShortener } = compilation.runtimeTemplate; - const getCurrentLoaderName = () => { - const currentLoader = this.getCurrentLoader(loaderContext); - if (!currentLoader) return "(not in loader scope)"; - return requestShortener.shorten(currentLoader.loader); - }; - const getResolveContext = () => { - return { - fileDependencies: { - add: d => loaderContext.addDependency(d) - }, - contextDependencies: { - add: d => loaderContext.addContextDependency(d) - }, - missingDependencies: { - add: d => loaderContext.addMissingDependency(d) - } - }; - }; - const getAbsolutify = memoize(() => - absolutify.bindCache(compilation.compiler.root) - ); - const getAbsolutifyInContext = memoize(() => - absolutify.bindContextCache(this.context, compilation.compiler.root) - ); - const getContextify = memoize(() => - contextify.bindCache(compilation.compiler.root) - ); - const getContextifyInContext = memoize(() => - contextify.bindContextCache(this.context, compilation.compiler.root) - ); - const utils = { - absolutify: (context, request) => { - return context === this.context - ? getAbsolutifyInContext()(request) - : getAbsolutify()(context, request); - }, - contextify: (context, request) => { - return context === this.context - ? getContextifyInContext()(request) - : getContextify()(context, request); - }, - createHash: type => { - return createHash(type || compilation.outputOptions.hashFunction); - } - }; - const loaderContext = { - version: 2, - getOptions: schema => { - const loader = this.getCurrentLoader(loaderContext); - - let { options } = loader; - - if (typeof options === "string") { - if (options.substr(0, 1) === "{" && options.substr(-1) === "}") { - try { - options = parseJson(options); - } catch (e) { - throw new Error(`Cannot parse string options: ${e.message}`); - } - } else { - options = querystring.parse(options, "&", "=", { - maxKeys: 0 - }); - } - } - - if (options === null || options === undefined) { - options = {}; - } - - if (schema) { - let name = "Loader"; - let baseDataPath = "options"; - let match; - if (schema.title && (match = /^(.+) (.+)$/.exec(schema.title))) { - [, name, baseDataPath] = match; - } - getValidate()(schema, options, { - name, - baseDataPath - }); - } - - return options; - }, - emitWarning: warning => { - if (!(warning instanceof Error)) { - warning = new NonErrorEmittedError(warning); - } - this.addWarning( - new ModuleWarning(warning, { - from: getCurrentLoaderName() - }) - ); - }, - emitError: error => { - if (!(error instanceof Error)) { - error = new NonErrorEmittedError(error); - } - this.addError( - new ModuleError(error, { - from: getCurrentLoaderName() - }) - ); - }, - getLogger: name => { - const currentLoader = this.getCurrentLoader(loaderContext); - return compilation.getLogger(() => - [currentLoader && currentLoader.loader, name, this.identifier()] - .filter(Boolean) - .join("|") - ); - }, - resolve(context, request, callback) { - resolver.resolve({}, context, request, getResolveContext(), callback); - }, - getResolve(options) { - const child = options ? resolver.withOptions(options) : resolver; - return (context, request, callback) => { - if (callback) { - child.resolve({}, context, request, getResolveContext(), callback); - } else { - return new Promise((resolve, reject) => { - child.resolve( - {}, - context, - request, - getResolveContext(), - (err, result) => { - if (err) reject(err); - else resolve(result); - } - ); - }); - } - }; - }, - emitFile: (name, content, sourceMap, assetInfo) => { - if (!this.buildInfo.assets) { - this.buildInfo.assets = Object.create(null); - this.buildInfo.assetsInfo = new Map(); - } - this.buildInfo.assets[name] = this.createSourceForAsset( - options.context, - name, - content, - sourceMap, - compilation.compiler.root - ); - this.buildInfo.assetsInfo.set(name, assetInfo); - }, - addBuildDependency: dep => { - if (this.buildInfo.buildDependencies === undefined) { - this.buildInfo.buildDependencies = new LazySet(); - } - this.buildInfo.buildDependencies.add(dep); - }, - utils, - rootContext: options.context, - webpack: true, - sourceMap: !!this.useSourceMap, - mode: options.mode || "production", - _module: this, - _compilation: compilation, - _compiler: compilation.compiler, - fs: fs - }; - - Object.assign(loaderContext, options.loader); - - hooks.loader.call(loaderContext, this); - - return loaderContext; - } - - getCurrentLoader(loaderContext, index = loaderContext.loaderIndex) { - if ( - this.loaders && - this.loaders.length && - index < this.loaders.length && - index >= 0 && - this.loaders[index] - ) { - return this.loaders[index]; - } - return null; + getTypes(module) { + return this._types; } /** - * @param {string} context the compilation context - * @param {string | Buffer} content the content - * @param {string | TODO} sourceMap an optional source map - * @param {Object=} associatedObjectForCache object for caching - * @returns {Source} the created source + * @param {NormalModule} module the module + * @param {string=} type source type + * @returns {number} estimate size of the module */ - createSource(context, content, sourceMap, associatedObjectForCache) { - if (Buffer.isBuffer(content)) { - return new RawSource(content); - } + getSize(module, type) { + const t = type || "javascript"; + const generator = this.map[t]; + return generator ? generator.getSize(module, t) : 0; + } - // if there is no identifier return raw source - if (!this.identifier) { - return new RawSource(content); + /** + * @param {NormalModule} module module for which the code should be generated + * @param {GenerateContext} generateContext context for generate + * @returns {Source} generated code + */ + generate(module, generateContext) { + const type = generateContext.type; + const generator = this.map[type]; + if (!generator) { + throw new Error(`Generator.byType: no generator specified for ${type}`); } + return generator.generate(module, generateContext); + } +} - // from here on we assume we have an identifier - const identifier = this.identifier(); +module.exports = Generator; - if (this.useSourceMap && sourceMap) { - return new SourceMapSource( - content, - contextifySourceUrl(context, identifier, associatedObjectForCache), - contextifySourceMap(context, sourceMap, associatedObjectForCache) - ); - } - if (this.useSourceMap || this.useSimpleSourceMap) { - return new OriginalSource( - content, - contextifySourceUrl(context, identifier, associatedObjectForCache) - ); - } +/***/ }), - return new RawSource(content); +/***/ 76652: +/***/ (function(__unused_webpack_module, exports) { + +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ + + + +/** @typedef {import("./AsyncDependenciesBlock")} AsyncDependenciesBlock */ +/** @typedef {import("./Chunk")} Chunk */ +/** @typedef {import("./ChunkGroup")} ChunkGroup */ +/** @typedef {import("./DependenciesBlock")} DependenciesBlock */ +/** @typedef {import("./Module")} Module */ + +/** + * @param {ChunkGroup} chunkGroup the ChunkGroup to connect + * @param {Chunk} chunk chunk to tie to ChunkGroup + * @returns {void} + */ +const connectChunkGroupAndChunk = (chunkGroup, chunk) => { + if (chunkGroup.pushChunk(chunk)) { + chunk.addGroup(chunkGroup); } +}; - /** - * @param {WebpackOptions} options webpack options - * @param {Compilation} compilation the compilation - * @param {ResolverWithOptions} resolver the resolver - * @param {InputFileSystem} fs the file system - * @param {NormalModuleCompilationHooks} hooks the hooks - * @param {function(WebpackError=): void} callback callback function - * @returns {void} - */ - _doBuild(options, compilation, resolver, fs, hooks, callback) { - const loaderContext = this._createLoaderContext( - resolver, - options, - compilation, - fs, - hooks - ); +/** + * @param {ChunkGroup} parent parent ChunkGroup to connect + * @param {ChunkGroup} child child ChunkGroup to connect + * @returns {void} + */ +const connectChunkGroupParentAndChild = (parent, child) => { + if (parent.addChild(child)) { + child.addParent(parent); + } +}; - const processResult = (err, result) => { - if (err) { - if (!(err instanceof Error)) { - err = new NonErrorEmittedError(err); - } - const currentLoader = this.getCurrentLoader(loaderContext); - const error = new ModuleBuildError(err, { - from: - currentLoader && - compilation.runtimeTemplate.requestShortener.shorten( - currentLoader.loader - ) - }); - return callback(error); - } +exports.connectChunkGroupAndChunk = connectChunkGroupAndChunk; +exports.connectChunkGroupParentAndChild = connectChunkGroupParentAndChild; - const source = result[0]; - const sourceMap = result.length >= 1 ? result[1] : null; - const extraInfo = result.length >= 2 ? result[2] : null; - if (!Buffer.isBuffer(source) && typeof source !== "string") { - const currentLoader = this.getCurrentLoader(loaderContext, 0); - const err = new Error( - `Final loader (${ - currentLoader - ? compilation.runtimeTemplate.requestShortener.shorten( - currentLoader.loader - ) - : "unknown" - }) didn't return a Buffer or String` - ); - const error = new ModuleBuildError(err); - return callback(error); - } +/***/ }), - this._source = this.createSource( - options.context, - this.binary ? asBuffer(source) : asString(source), - sourceMap, - compilation.compiler.root - ); - if (this._sourceSizes !== undefined) this._sourceSizes.clear(); - this._ast = - typeof extraInfo === "object" && - extraInfo !== null && - extraInfo.webpackAST !== undefined - ? extraInfo.webpackAST - : null; - return callback(); - }; +/***/ 42766: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - this.buildInfo.fileDependencies = new LazySet(); - this.buildInfo.contextDependencies = new LazySet(); - this.buildInfo.missingDependencies = new LazySet(); - this.buildInfo.cacheable = true; +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php +*/ - try { - hooks.beforeLoaders.call(this.loaders, this, loaderContext); - } catch (err) { - processResult(err); - return; - } - if (this.loaders.length > 0) { - this.buildInfo.buildDependencies = new LazySet(); - } - runLoaders( - { - resource: this.resource, - loaders: this.loaders, - context: loaderContext, - processResource: (loaderContext, resourcePath, callback) => { - const resource = loaderContext.resource; - const scheme = getScheme(resource); - hooks.readResource - .for(scheme) - .callAsync(loaderContext, (err, result) => { - if (err) return callback(err); - if (typeof result !== "string" && !result) { - return callback(new UnhandledSchemeError(scheme, resource)); - } - return callback(null, result); - }); - } - }, - (err, result) => { - // Cleanup loaderContext to avoid leaking memory in ICs - loaderContext._compilation = - loaderContext._compiler = - loaderContext._module = - loaderContext.fs = - undefined; +const WebpackError = __webpack_require__(68422); - if (!result) { - this.buildInfo.cacheable = false; - return processResult( - err || new Error("No result from loader-runner processing"), - null - ); - } - this.buildInfo.fileDependencies.addAll(result.fileDependencies); - this.buildInfo.contextDependencies.addAll(result.contextDependencies); - this.buildInfo.missingDependencies.addAll(result.missingDependencies); - for (const loader of this.loaders) { - this.buildInfo.buildDependencies.add(loader.loader); - } - this.buildInfo.cacheable = this.buildInfo.cacheable && result.cacheable; - processResult(err, result.result); - } - ); +module.exports = class HarmonyLinkingError extends WebpackError { + /** @param {string} message Error message */ + constructor(message) { + super(message); + this.name = "HarmonyLinkingError"; + this.hideStack = true; } +}; + + +/***/ }), + +/***/ 89935: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Sean Larkin @thelarkinn +*/ + + +const WebpackError = __webpack_require__(68422); + +/** @typedef {import("./Module")} Module */ + +/** + * @template T + * @callback Callback + * @param {Error=} err + * @param {T=} stats + * @returns {void} + */ + +class HookWebpackError extends WebpackError { /** - * @param {WebpackError} error the error - * @returns {void} + * Creates an instance of HookWebpackError. + * @param {Error} error inner error + * @param {string} hook name of hook */ - markModuleAsErrored(error) { - // Restore build meta from successful build to keep importing state - this.buildMeta = { ...this._lastSuccessfulBuildMeta }; + constructor(error, hook) { + super(error.message); + + this.name = "HookWebpackError"; + this.hook = hook; this.error = error; - this.addError(error); + this.hideStack = true; + this.details = `caused by plugins in ${hook}\n${error.stack}`; + + this.stack += `\n-- inner error --\n${error.stack}`; } +} - applyNoParseRule(rule, content) { - // must start with "rule" if rule is a string - if (typeof rule === "string") { - return content.startsWith(rule); +module.exports = HookWebpackError; + +/** + * @param {Error} error an error + * @param {string} hook name of the hook + * @returns {WebpackError} a webpack error + */ +const makeWebpackError = (error, hook) => { + if (error instanceof WebpackError) return error; + return new HookWebpackError(error, hook); +}; +module.exports.makeWebpackError = makeWebpackError; + +/** + * @template T + * @param {function(WebpackError=, T=): void} callback webpack error callback + * @param {string} hook name of hook + * @returns {Callback} generic callback + */ +const makeWebpackErrorCallback = (callback, hook) => { + return (err, result) => { + if (err) { + if (err instanceof WebpackError) { + callback(err); + return; + } + callback(new HookWebpackError(err, hook)); + return; } + callback(null, result); + }; +}; - if (typeof rule === "function") { - return rule(content); +module.exports.makeWebpackErrorCallback = makeWebpackErrorCallback; + +/** + * @template T + * @param {function(): T} fn function which will be wrapping in try catch + * @param {string} hook name of hook + * @returns {T} the result + */ +const tryRunOrWebpackError = (fn, hook) => { + let r; + try { + r = fn(); + } catch (err) { + if (err instanceof WebpackError) { + throw err; } - // we assume rule is a regexp - return rule.test(content); + throw new HookWebpackError(err, hook); } + return r; +}; - // check if module should not be parsed - // returns "true" if the module should !not! be parsed - // returns "false" if the module !must! be parsed - shouldPreventParsing(noParseRule, request) { - // if no noParseRule exists, return false - // the module !must! be parsed. - if (!noParseRule) { - return false; - } +module.exports.tryRunOrWebpackError = tryRunOrWebpackError; - // we only have one rule to check - if (!Array.isArray(noParseRule)) { - // returns "true" if the module is !not! to be parsed - return this.applyNoParseRule(noParseRule, request); + +/***/ }), + +/***/ 616: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ + + + +const { SyncBailHook } = __webpack_require__(34718); +const { RawSource } = __webpack_require__(96192); +const ChunkGraph = __webpack_require__(97860); +const Compilation = __webpack_require__(59622); +const HotUpdateChunk = __webpack_require__(39222); +const NormalModule = __webpack_require__(11026); +const RuntimeGlobals = __webpack_require__(49404); +const WebpackError = __webpack_require__(68422); +const ConstDependency = __webpack_require__(60864); +const ImportMetaHotAcceptDependency = __webpack_require__(58287); +const ImportMetaHotDeclineDependency = __webpack_require__(89911); +const ModuleHotAcceptDependency = __webpack_require__(90200); +const ModuleHotDeclineDependency = __webpack_require__(72986); +const HotModuleReplacementRuntimeModule = __webpack_require__(21978); +const JavascriptParser = __webpack_require__(42060); +const { + evaluateToIdentifier +} = __webpack_require__(28723); +const { find, isSubset } = __webpack_require__(34715); +const TupleSet = __webpack_require__(39322); +const { compareModulesById } = __webpack_require__(26296); +const { + getRuntimeKey, + keyToRuntime, + forEachRuntime, + mergeRuntimeOwned, + subtractRuntime, + intersectRuntime +} = __webpack_require__(19655); + +/** @typedef {import("./Chunk")} Chunk */ +/** @typedef {import("./Compilation").AssetInfo} AssetInfo */ +/** @typedef {import("./Compiler")} Compiler */ +/** @typedef {import("./Module")} Module */ +/** @typedef {import("./RuntimeModule")} RuntimeModule */ +/** @typedef {import("./util/runtime").RuntimeSpec} RuntimeSpec */ + +/** + * @typedef {Object} HMRJavascriptParserHooks + * @property {SyncBailHook<[TODO, string[]], void>} hotAcceptCallback + * @property {SyncBailHook<[TODO, string[]], void>} hotAcceptWithoutCallback + */ + +/** @type {WeakMap} */ +const parserHooksMap = new WeakMap(); + +class HotModuleReplacementPlugin { + /** + * @param {JavascriptParser} parser the parser + * @returns {HMRJavascriptParserHooks} the attached hooks + */ + static getParserHooks(parser) { + if (!(parser instanceof JavascriptParser)) { + throw new TypeError( + "The 'parser' argument must be an instance of JavascriptParser" + ); + } + let hooks = parserHooksMap.get(parser); + if (hooks === undefined) { + hooks = { + hotAcceptCallback: new SyncBailHook(["expression", "requests"]), + hotAcceptWithoutCallback: new SyncBailHook(["expression", "requests"]) + }; + parserHooksMap.set(parser, hooks); } + return hooks; + } - for (let i = 0; i < noParseRule.length; i++) { - const rule = noParseRule[i]; - // early exit on first truthy match - // this module is !not! to be parsed - if (this.applyNoParseRule(rule, request)) { + constructor(options) { + this.options = options || {}; + } + + /** + * Apply the plugin + * @param {Compiler} compiler the compiler instance + * @returns {void} + */ + apply(compiler) { + const { _backCompat: backCompat } = compiler; + if (compiler.options.output.strictModuleErrorHandling === undefined) + compiler.options.output.strictModuleErrorHandling = true; + const runtimeRequirements = [RuntimeGlobals.module]; + + const createAcceptHandler = (parser, ParamDependency) => { + const { hotAcceptCallback, hotAcceptWithoutCallback } = + HotModuleReplacementPlugin.getParserHooks(parser); + + return expr => { + const module = parser.state.module; + const dep = new ConstDependency( + `${module.moduleArgument}.hot.accept`, + expr.callee.range, + runtimeRequirements + ); + dep.loc = expr.loc; + module.addPresentationalDependency(dep); + module.buildInfo.moduleConcatenationBailout = "Hot Module Replacement"; + if (expr.arguments.length >= 1) { + const arg = parser.evaluateExpression(expr.arguments[0]); + let params = []; + let requests = []; + if (arg.isString()) { + params = [arg]; + } else if (arg.isArray()) { + params = arg.items.filter(param => param.isString()); + } + if (params.length > 0) { + params.forEach((param, idx) => { + const request = param.string; + const dep = new ParamDependency(request, param.range); + dep.optional = true; + dep.loc = Object.create(expr.loc); + dep.loc.index = idx; + module.addDependency(dep); + requests.push(request); + }); + if (expr.arguments.length > 1) { + hotAcceptCallback.call(expr.arguments[1], requests); + for (let i = 1; i < expr.arguments.length; i++) { + parser.walkExpression(expr.arguments[i]); + } + return true; + } else { + hotAcceptWithoutCallback.call(expr, requests); + return true; + } + } + } + parser.walkExpressions(expr.arguments); return true; + }; + }; + + const createDeclineHandler = (parser, ParamDependency) => expr => { + const module = parser.state.module; + const dep = new ConstDependency( + `${module.moduleArgument}.hot.decline`, + expr.callee.range, + runtimeRequirements + ); + dep.loc = expr.loc; + module.addPresentationalDependency(dep); + module.buildInfo.moduleConcatenationBailout = "Hot Module Replacement"; + if (expr.arguments.length === 1) { + const arg = parser.evaluateExpression(expr.arguments[0]); + let params = []; + if (arg.isString()) { + params = [arg]; + } else if (arg.isArray()) { + params = arg.items.filter(param => param.isString()); + } + params.forEach((param, idx) => { + const dep = new ParamDependency(param.string, param.range); + dep.optional = true; + dep.loc = Object.create(expr.loc); + dep.loc.index = idx; + module.addDependency(dep); + }); } - } - // no match found, so this module !should! be parsed - return false; - } + return true; + }; - _initBuildHash(compilation) { - const hash = createHash(compilation.outputOptions.hashFunction); - if (this._source) { - hash.update("source"); - this._source.updateHash(hash); - } - hash.update("meta"); - hash.update(JSON.stringify(this.buildMeta)); - this.buildInfo.hash = /** @type {string} */ (hash.digest("hex")); - } + const createHMRExpressionHandler = parser => expr => { + const module = parser.state.module; + const dep = new ConstDependency( + `${module.moduleArgument}.hot`, + expr.range, + runtimeRequirements + ); + dep.loc = expr.loc; + module.addPresentationalDependency(dep); + module.buildInfo.moduleConcatenationBailout = "Hot Module Replacement"; + return true; + }; - /** - * @param {WebpackOptions} options webpack options - * @param {Compilation} compilation the compilation - * @param {ResolverWithOptions} resolver the resolver - * @param {InputFileSystem} fs the file system - * @param {function(WebpackError=): void} callback callback function - * @returns {void} - */ - build(options, compilation, resolver, fs, callback) { - this._forceBuild = false; - this._source = null; - if (this._sourceSizes !== undefined) this._sourceSizes.clear(); - this._sourceTypes = undefined; - this._ast = null; - this.error = null; - this.clearWarningsAndErrors(); - this.clearDependenciesAndBlocks(); - this.buildMeta = {}; - this.buildInfo = { - cacheable: false, - parsed: true, - fileDependencies: undefined, - contextDependencies: undefined, - missingDependencies: undefined, - buildDependencies: undefined, - valueDependencies: undefined, - hash: undefined, - assets: undefined, - assetsInfo: undefined + const applyModuleHot = parser => { + parser.hooks.evaluateIdentifier.for("module.hot").tap( + { + name: "HotModuleReplacementPlugin", + before: "NodeStuffPlugin" + }, + expr => { + return evaluateToIdentifier( + "module.hot", + "module", + () => ["hot"], + true + )(expr); + } + ); + parser.hooks.call + .for("module.hot.accept") + .tap( + "HotModuleReplacementPlugin", + createAcceptHandler(parser, ModuleHotAcceptDependency) + ); + parser.hooks.call + .for("module.hot.decline") + .tap( + "HotModuleReplacementPlugin", + createDeclineHandler(parser, ModuleHotDeclineDependency) + ); + parser.hooks.expression + .for("module.hot") + .tap("HotModuleReplacementPlugin", createHMRExpressionHandler(parser)); }; - const startTime = compilation.compiler.fsStartTime || Date.now(); + const applyImportMetaHot = parser => { + parser.hooks.evaluateIdentifier + .for("import.meta.webpackHot") + .tap("HotModuleReplacementPlugin", expr => { + return evaluateToIdentifier( + "import.meta.webpackHot", + "import.meta", + () => ["webpackHot"], + true + )(expr); + }); + parser.hooks.call + .for("import.meta.webpackHot.accept") + .tap( + "HotModuleReplacementPlugin", + createAcceptHandler(parser, ImportMetaHotAcceptDependency) + ); + parser.hooks.call + .for("import.meta.webpackHot.decline") + .tap( + "HotModuleReplacementPlugin", + createDeclineHandler(parser, ImportMetaHotDeclineDependency) + ); + parser.hooks.expression + .for("import.meta.webpackHot") + .tap("HotModuleReplacementPlugin", createHMRExpressionHandler(parser)); + }; - const hooks = NormalModule.getCompilationHooks(compilation); + compiler.hooks.compilation.tap( + "HotModuleReplacementPlugin", + (compilation, { normalModuleFactory }) => { + // This applies the HMR plugin only to the targeted compiler + // It should not affect child compilations + if (compilation.compiler !== compiler) return; - return this._doBuild(options, compilation, resolver, fs, hooks, err => { - // if we have an error mark module as failed and exit - if (err) { - this.markModuleAsErrored(err); - this._initBuildHash(compilation); - return callback(); - } + //#region module.hot.* API + compilation.dependencyFactories.set( + ModuleHotAcceptDependency, + normalModuleFactory + ); + compilation.dependencyTemplates.set( + ModuleHotAcceptDependency, + new ModuleHotAcceptDependency.Template() + ); + compilation.dependencyFactories.set( + ModuleHotDeclineDependency, + normalModuleFactory + ); + compilation.dependencyTemplates.set( + ModuleHotDeclineDependency, + new ModuleHotDeclineDependency.Template() + ); + //#endregion - const handleParseError = e => { - const source = this._source.source(); - const loaders = this.loaders.map(item => - contextify(options.context, item.loader, compilation.compiler.root) + //#region import.meta.webpackHot.* API + compilation.dependencyFactories.set( + ImportMetaHotAcceptDependency, + normalModuleFactory ); - const error = new ModuleParseError(source, e, loaders, this.type); - this.markModuleAsErrored(error); - this._initBuildHash(compilation); - return callback(); - }; + compilation.dependencyTemplates.set( + ImportMetaHotAcceptDependency, + new ImportMetaHotAcceptDependency.Template() + ); + compilation.dependencyFactories.set( + ImportMetaHotDeclineDependency, + normalModuleFactory + ); + compilation.dependencyTemplates.set( + ImportMetaHotDeclineDependency, + new ImportMetaHotDeclineDependency.Template() + ); + //#endregion - const handleParseResult = result => { - this.dependencies.sort( - concatComparators( - compareSelect(a => a.loc, compareLocations), - keepOriginalOrder(this.dependencies) - ) + let hotIndex = 0; + const fullHashChunkModuleHashes = {}; + const chunkModuleHashes = {}; + + compilation.hooks.record.tap( + "HotModuleReplacementPlugin", + (compilation, records) => { + if (records.hash === compilation.hash) return; + const chunkGraph = compilation.chunkGraph; + records.hash = compilation.hash; + records.hotIndex = hotIndex; + records.fullHashChunkModuleHashes = fullHashChunkModuleHashes; + records.chunkModuleHashes = chunkModuleHashes; + records.chunkHashes = {}; + records.chunkRuntime = {}; + for (const chunk of compilation.chunks) { + records.chunkHashes[chunk.id] = chunk.hash; + records.chunkRuntime[chunk.id] = getRuntimeKey(chunk.runtime); + } + records.chunkModuleIds = {}; + for (const chunk of compilation.chunks) { + records.chunkModuleIds[chunk.id] = Array.from( + chunkGraph.getOrderedChunkModulesIterable( + chunk, + compareModulesById(chunkGraph) + ), + m => chunkGraph.getModuleId(m) + ); + } + } ); - this._initBuildHash(compilation); - this._lastSuccessfulBuildMeta = this.buildMeta; - return handleBuildDone(); - }; + /** @type {TupleSet<[Module, Chunk]>} */ + const updatedModules = new TupleSet(); + /** @type {TupleSet<[Module, Chunk]>} */ + const fullHashModules = new TupleSet(); + /** @type {TupleSet<[Module, RuntimeSpec]>} */ + const nonCodeGeneratedModules = new TupleSet(); + compilation.hooks.fullHash.tap("HotModuleReplacementPlugin", hash => { + const chunkGraph = compilation.chunkGraph; + const records = compilation.records; + for (const chunk of compilation.chunks) { + const getModuleHash = module => { + if ( + compilation.codeGenerationResults.has(module, chunk.runtime) + ) { + return compilation.codeGenerationResults.getHash( + module, + chunk.runtime + ); + } else { + nonCodeGeneratedModules.add(module, chunk.runtime); + return chunkGraph.getModuleHash(module, chunk.runtime); + } + }; + const fullHashModulesInThisChunk = + chunkGraph.getChunkFullHashModulesSet(chunk); + if (fullHashModulesInThisChunk !== undefined) { + for (const module of fullHashModulesInThisChunk) { + fullHashModules.add(module, chunk); + } + } + const modules = chunkGraph.getChunkModulesIterable(chunk); + if (modules !== undefined) { + if (records.chunkModuleHashes) { + if (fullHashModulesInThisChunk !== undefined) { + for (const module of modules) { + const key = `${chunk.id}|${module.identifier()}`; + const hash = getModuleHash(module); + if ( + fullHashModulesInThisChunk.has( + /** @type {RuntimeModule} */ (module) + ) + ) { + if (records.fullHashChunkModuleHashes[key] !== hash) { + updatedModules.add(module, chunk); + } + fullHashChunkModuleHashes[key] = hash; + } else { + if (records.chunkModuleHashes[key] !== hash) { + updatedModules.add(module, chunk); + } + chunkModuleHashes[key] = hash; + } + } + } else { + for (const module of modules) { + const key = `${chunk.id}|${module.identifier()}`; + const hash = getModuleHash(module); + if (records.chunkModuleHashes[key] !== hash) { + updatedModules.add(module, chunk); + } + chunkModuleHashes[key] = hash; + } + } + } else { + if (fullHashModulesInThisChunk !== undefined) { + for (const module of modules) { + const key = `${chunk.id}|${module.identifier()}`; + const hash = getModuleHash(module); + if ( + fullHashModulesInThisChunk.has( + /** @type {RuntimeModule} */ (module) + ) + ) { + fullHashChunkModuleHashes[key] = hash; + } else { + chunkModuleHashes[key] = hash; + } + } + } else { + for (const module of modules) { + const key = `${chunk.id}|${module.identifier()}`; + const hash = getModuleHash(module); + chunkModuleHashes[key] = hash; + } + } + } + } + } - const handleBuildDone = () => { - try { - hooks.beforeSnapshot.call(this); - } catch (err) { - this.markModuleAsErrored(err); - return callback(); - } + hotIndex = records.hotIndex || 0; + if (updatedModules.size > 0) hotIndex++; - const snapshotOptions = compilation.options.snapshot.module; - if (!this.buildInfo.cacheable || !snapshotOptions) { - return callback(); - } - // add warning for all non-absolute paths in fileDependencies, etc - // This makes it easier to find problems with watching and/or caching - let nonAbsoluteDependencies = undefined; - const checkDependencies = deps => { - for (const dep of deps) { - if (!ABSOLUTE_PATH_REGEX.test(dep)) { - if (nonAbsoluteDependencies === undefined) - nonAbsoluteDependencies = new Set(); - nonAbsoluteDependencies.add(dep); - deps.delete(dep); - try { - const depWithoutGlob = dep.replace(/[\\/]?\*.*$/, ""); - const absolute = join( - compilation.fileSystemInfo.fs, - this.context, - depWithoutGlob + hash.update(`${hotIndex}`); + }); + compilation.hooks.processAssets.tap( + { + name: "HotModuleReplacementPlugin", + stage: Compilation.PROCESS_ASSETS_STAGE_ADDITIONAL + }, + () => { + const chunkGraph = compilation.chunkGraph; + const records = compilation.records; + if (records.hash === compilation.hash) return; + if ( + !records.chunkModuleHashes || + !records.chunkHashes || + !records.chunkModuleIds + ) { + return; + } + for (const [module, chunk] of fullHashModules) { + const key = `${chunk.id}|${module.identifier()}`; + const hash = nonCodeGeneratedModules.has(module, chunk.runtime) + ? chunkGraph.getModuleHash(module, chunk.runtime) + : compilation.codeGenerationResults.getHash( + module, + chunk.runtime + ); + if (records.chunkModuleHashes[key] !== hash) { + updatedModules.add(module, chunk); + } + chunkModuleHashes[key] = hash; + } + + /** @type {Map, removedChunkIds: Set, removedModules: Set, filename: string, assetInfo: AssetInfo }>} */ + const hotUpdateMainContentByRuntime = new Map(); + let allOldRuntime; + for (const key of Object.keys(records.chunkRuntime)) { + const runtime = keyToRuntime(records.chunkRuntime[key]); + allOldRuntime = mergeRuntimeOwned(allOldRuntime, runtime); + } + forEachRuntime(allOldRuntime, runtime => { + const { path: filename, info: assetInfo } = + compilation.getPathWithInfo( + compilation.outputOptions.hotUpdateMainFilename, + { + hash: records.hash, + runtime + } + ); + hotUpdateMainContentByRuntime.set(runtime, { + updatedChunkIds: new Set(), + removedChunkIds: new Set(), + removedModules: new Set(), + filename, + assetInfo + }); + }); + if (hotUpdateMainContentByRuntime.size === 0) return; + + // Create a list of all active modules to verify which modules are removed completely + /** @type {Map} */ + const allModules = new Map(); + for (const module of compilation.modules) { + const id = chunkGraph.getModuleId(module); + allModules.set(id, module); + } + + // List of completely removed modules + /** @type {Set} */ + const completelyRemovedModules = new Set(); + + for (const key of Object.keys(records.chunkHashes)) { + const oldRuntime = keyToRuntime(records.chunkRuntime[key]); + /** @type {Module[]} */ + const remainingModules = []; + // Check which modules are removed + for (const id of records.chunkModuleIds[key]) { + const module = allModules.get(id); + if (module === undefined) { + completelyRemovedModules.add(id); + } else { + remainingModules.push(module); + } + } + + let chunkId; + let newModules; + let newRuntimeModules; + let newFullHashModules; + let newDependentHashModules; + let newRuntime; + let removedFromRuntime; + const currentChunk = find( + compilation.chunks, + chunk => `${chunk.id}` === key + ); + if (currentChunk) { + chunkId = currentChunk.id; + newRuntime = intersectRuntime( + currentChunk.runtime, + allOldRuntime + ); + if (newRuntime === undefined) continue; + newModules = chunkGraph + .getChunkModules(currentChunk) + .filter(module => updatedModules.has(module, currentChunk)); + newRuntimeModules = Array.from( + chunkGraph.getChunkRuntimeModulesIterable(currentChunk) + ).filter(module => updatedModules.has(module, currentChunk)); + const fullHashModules = + chunkGraph.getChunkFullHashModulesIterable(currentChunk); + newFullHashModules = + fullHashModules && + Array.from(fullHashModules).filter(module => + updatedModules.has(module, currentChunk) + ); + const dependentHashModules = + chunkGraph.getChunkDependentHashModulesIterable(currentChunk); + newDependentHashModules = + dependentHashModules && + Array.from(dependentHashModules).filter(module => + updatedModules.has(module, currentChunk) + ); + removedFromRuntime = subtractRuntime(oldRuntime, newRuntime); + } else { + // chunk has completely removed + chunkId = `${+key}` === key ? +key : key; + removedFromRuntime = oldRuntime; + newRuntime = oldRuntime; + } + if (removedFromRuntime) { + // chunk was removed from some runtimes + forEachRuntime(removedFromRuntime, runtime => { + hotUpdateMainContentByRuntime + .get(runtime) + .removedChunkIds.add(chunkId); + }); + // dispose modules from the chunk in these runtimes + // where they are no longer in this runtime + for (const module of remainingModules) { + const moduleKey = `${key}|${module.identifier()}`; + const oldHash = records.chunkModuleHashes[moduleKey]; + const runtimes = chunkGraph.getModuleRuntimes(module); + if (oldRuntime === newRuntime && runtimes.has(newRuntime)) { + // Module is still in the same runtime combination + const hash = nonCodeGeneratedModules.has(module, newRuntime) + ? chunkGraph.getModuleHash(module, newRuntime) + : compilation.codeGenerationResults.getHash( + module, + newRuntime + ); + if (hash !== oldHash) { + if (module.type === "runtime") { + newRuntimeModules = newRuntimeModules || []; + newRuntimeModules.push( + /** @type {RuntimeModule} */ (module) + ); + } else { + newModules = newModules || []; + newModules.push(module); + } + } + } else { + // module is no longer in this runtime combination + // We (incorrectly) assume that it's not in an overlapping runtime combination + // and dispose it from the main runtimes the chunk was removed from + forEachRuntime(removedFromRuntime, runtime => { + // If the module is still used in this runtime, do not dispose it + // This could create a bad runtime state where the module is still loaded, + // but no chunk which contains it. This means we don't receive further HMR updates + // to this module and that's bad. + // TODO force load one of the chunks which contains the module + for (const moduleRuntime of runtimes) { + if (typeof moduleRuntime === "string") { + if (moduleRuntime === runtime) return; + } else if (moduleRuntime !== undefined) { + if (moduleRuntime.has(runtime)) return; + } + } + hotUpdateMainContentByRuntime + .get(runtime) + .removedModules.add(module); + }); + } + } + } + if ( + (newModules && newModules.length > 0) || + (newRuntimeModules && newRuntimeModules.length > 0) + ) { + const hotUpdateChunk = new HotUpdateChunk(); + if (backCompat) + ChunkGraph.setChunkGraphForChunk(hotUpdateChunk, chunkGraph); + hotUpdateChunk.id = chunkId; + hotUpdateChunk.runtime = newRuntime; + if (currentChunk) { + for (const group of currentChunk.groupsIterable) + hotUpdateChunk.addGroup(group); + } + chunkGraph.attachModules(hotUpdateChunk, newModules || []); + chunkGraph.attachRuntimeModules( + hotUpdateChunk, + newRuntimeModules || [] ); - if (absolute !== dep && ABSOLUTE_PATH_REGEX.test(absolute)) { - (depWithoutGlob !== dep - ? this.buildInfo.contextDependencies - : deps - ).add(absolute); + if (newFullHashModules) { + chunkGraph.attachFullHashModules( + hotUpdateChunk, + newFullHashModules + ); } - } catch (e) { - // ignore + if (newDependentHashModules) { + chunkGraph.attachDependentHashModules( + hotUpdateChunk, + newDependentHashModules + ); + } + const renderManifest = compilation.getRenderManifest({ + chunk: hotUpdateChunk, + hash: records.hash, + fullHash: records.hash, + outputOptions: compilation.outputOptions, + moduleTemplates: compilation.moduleTemplates, + dependencyTemplates: compilation.dependencyTemplates, + codeGenerationResults: compilation.codeGenerationResults, + runtimeTemplate: compilation.runtimeTemplate, + moduleGraph: compilation.moduleGraph, + chunkGraph + }); + for (const entry of renderManifest) { + /** @type {string} */ + let filename; + /** @type {AssetInfo} */ + let assetInfo; + if ("filename" in entry) { + filename = entry.filename; + assetInfo = entry.info; + } else { + ({ path: filename, info: assetInfo } = + compilation.getPathWithInfo( + entry.filenameTemplate, + entry.pathOptions + )); + } + const source = entry.render(); + compilation.additionalChunkAssets.push(filename); + compilation.emitAsset(filename, source, { + hotModuleReplacement: true, + ...assetInfo + }); + if (currentChunk) { + currentChunk.files.add(filename); + compilation.hooks.chunkAsset.call(currentChunk, filename); + } + } + forEachRuntime(newRuntime, runtime => { + hotUpdateMainContentByRuntime + .get(runtime) + .updatedChunkIds.add(chunkId); + }); } } - } - }; - checkDependencies(this.buildInfo.fileDependencies); - checkDependencies(this.buildInfo.missingDependencies); - checkDependencies(this.buildInfo.contextDependencies); - if (nonAbsoluteDependencies !== undefined) { - const InvalidDependenciesModuleWarning = - getInvalidDependenciesModuleWarning(); - this.addWarning( - new InvalidDependenciesModuleWarning(this, nonAbsoluteDependencies) - ); - } - // convert file/context/missingDependencies into filesystem snapshot - compilation.fileSystemInfo.createSnapshot( - startTime, - this.buildInfo.fileDependencies, - this.buildInfo.contextDependencies, - this.buildInfo.missingDependencies, - snapshotOptions, - (err, snapshot) => { - if (err) { - this.markModuleAsErrored(err); - return; + const completelyRemovedModulesArray = Array.from( + completelyRemovedModules + ); + const hotUpdateMainContentByFilename = new Map(); + for (const { + removedChunkIds, + removedModules, + updatedChunkIds, + filename, + assetInfo + } of hotUpdateMainContentByRuntime.values()) { + const old = hotUpdateMainContentByFilename.get(filename); + if ( + old && + (!isSubset(old.removedChunkIds, removedChunkIds) || + !isSubset(old.removedModules, removedModules) || + !isSubset(old.updatedChunkIds, updatedChunkIds)) + ) { + compilation.warnings.push( + new WebpackError(`HotModuleReplacementPlugin +The configured output.hotUpdateMainFilename doesn't lead to unique filenames per runtime and HMR update differs between runtimes. +This might lead to incorrect runtime behavior of the applied update. +To fix this, make sure to include [runtime] in the output.hotUpdateMainFilename option, or use the default config.`) + ); + for (const chunkId of removedChunkIds) + old.removedChunkIds.add(chunkId); + for (const chunkId of removedModules) + old.removedModules.add(chunkId); + for (const chunkId of updatedChunkIds) + old.updatedChunkIds.add(chunkId); + continue; + } + hotUpdateMainContentByFilename.set(filename, { + removedChunkIds, + removedModules, + updatedChunkIds, + assetInfo + }); + } + for (const [ + filename, + { removedChunkIds, removedModules, updatedChunkIds, assetInfo } + ] of hotUpdateMainContentByFilename) { + const hotUpdateMainJson = { + c: Array.from(updatedChunkIds), + r: Array.from(removedChunkIds), + m: + removedModules.size === 0 + ? completelyRemovedModulesArray + : completelyRemovedModulesArray.concat( + Array.from(removedModules, m => + chunkGraph.getModuleId(m) + ) + ) + }; + + const source = new RawSource(JSON.stringify(hotUpdateMainJson)); + compilation.emitAsset(filename, source, { + hotModuleReplacement: true, + ...assetInfo + }); } - this.buildInfo.fileDependencies = undefined; - this.buildInfo.contextDependencies = undefined; - this.buildInfo.missingDependencies = undefined; - this.buildInfo.snapshot = snapshot; - return callback(); } ); - }; - - try { - hooks.beforeParse.call(this); - } catch (err) { - this.markModuleAsErrored(err); - this._initBuildHash(compilation); - return callback(); - } - - // check if this module should !not! be parsed. - // if so, exit here; - const noParseRule = options.module && options.module.noParse; - if (this.shouldPreventParsing(noParseRule, this.request)) { - // We assume that we need module and exports - this.buildInfo.parsed = false; - this._initBuildHash(compilation); - return handleBuildDone(); - } - - let result; - try { - const source = this._source.source(); - result = this.parser.parse(this._ast || source, { - source, - current: this, - module: this, - compilation: compilation, - options: options - }); - } catch (e) { - handleParseError(e); - return; - } - handleParseResult(result); - }); - } - - /** - * @param {ConcatenationBailoutReasonContext} context context - * @returns {string | undefined} reason why this module can't be concatenated, undefined when it can be concatenated - */ - getConcatenationBailoutReason(context) { - return this.generator.getConcatenationBailoutReason(this, context); - } - /** - * @param {ModuleGraph} moduleGraph the module graph - * @returns {ConnectionState} how this module should be connected to referencing modules when consumed for side-effects only - */ - getSideEffectsConnectionState(moduleGraph) { - if (this.factoryMeta !== undefined) { - if (this.factoryMeta.sideEffectFree) return false; - if (this.factoryMeta.sideEffectFree === false) return true; - } - if (this.buildMeta !== undefined && this.buildMeta.sideEffectFree) { - if (this._isEvaluatingSideEffects) - return ModuleGraphConnection.CIRCULAR_CONNECTION; - this._isEvaluatingSideEffects = true; - /** @type {ConnectionState} */ - let current = false; - for (const dep of this.dependencies) { - const state = dep.getModuleEvaluationSideEffectsState(moduleGraph); - if (state === true) { - if ( - this._addedSideEffectsBailout === undefined - ? ((this._addedSideEffectsBailout = new WeakSet()), true) - : !this._addedSideEffectsBailout.has(moduleGraph) - ) { - this._addedSideEffectsBailout.add(moduleGraph); - moduleGraph - .getOptimizationBailout(this) - .push( - () => - `Dependency (${ - dep.type - }) with side effects at ${formatLocation(dep.loc)}` - ); + compilation.hooks.additionalTreeRuntimeRequirements.tap( + "HotModuleReplacementPlugin", + (chunk, runtimeRequirements) => { + runtimeRequirements.add(RuntimeGlobals.hmrDownloadManifest); + runtimeRequirements.add(RuntimeGlobals.hmrDownloadUpdateHandlers); + runtimeRequirements.add(RuntimeGlobals.interceptModuleExecution); + runtimeRequirements.add(RuntimeGlobals.moduleCache); + compilation.addRuntimeModule( + chunk, + new HotModuleReplacementRuntimeModule() + ); } - this._isEvaluatingSideEffects = false; - return true; - } else if (state !== ModuleGraphConnection.CIRCULAR_CONNECTION) { - current = ModuleGraphConnection.addConnectionStates(current, state); - } - } - this._isEvaluatingSideEffects = false; - // When caching is implemented here, make sure to not cache when - // at least one circular connection was in the loop above - return current; - } else { - return true; - } - } - - /** - * @returns {Set} types available (do not mutate) - */ - getSourceTypes() { - if (this._sourceTypes === undefined) { - this._sourceTypes = this.generator.getTypes(this); - } - return this._sourceTypes; - } - - /** - * @param {CodeGenerationContext} context context for code generation - * @returns {CodeGenerationResult} result - */ - codeGeneration({ - dependencyTemplates, - runtimeTemplate, - moduleGraph, - chunkGraph, - runtime, - concatenationScope - }) { - /** @type {Set} */ - const runtimeRequirements = new Set(); - - if (!this.buildInfo.parsed) { - runtimeRequirements.add(RuntimeGlobals.module); - runtimeRequirements.add(RuntimeGlobals.exports); - runtimeRequirements.add(RuntimeGlobals.thisAsExports); - } - - /** @type {Map} */ - let data; - const getData = () => { - if (data === undefined) data = new Map(); - return data; - }; - - const sources = new Map(); - for (const type of this.generator.getTypes(this)) { - const source = this.error - ? new RawSource( - "throw new Error(" + JSON.stringify(this.error.message) + ");" - ) - : this.generator.generate(this, { - dependencyTemplates, - runtimeTemplate, - moduleGraph, - chunkGraph, - runtimeRequirements, - runtime, - concatenationScope, - getData, - type - }); - - if (source) { - sources.set(type, new CachedSource(source)); - } - } - - /** @type {CodeGenerationResult} */ - const resultEntry = { - sources, - runtimeRequirements, - data - }; - return resultEntry; - } - - /** - * @returns {Source | null} the original source for the module before webpack transformation - */ - originalSource() { - return this._source; - } - - /** - * @returns {void} - */ - invalidateBuild() { - this._forceBuild = true; - } - - /** - * @param {NeedBuildContext} context context info - * @param {function(WebpackError=, boolean=): void} callback callback function, returns true, if the module needs a rebuild - * @returns {void} - */ - needBuild(context, callback) { - const { fileSystemInfo, compilation, valueCacheVersions } = context; - // build if enforced - if (this._forceBuild) return callback(null, true); - - // always try to build in case of an error - if (this.error) return callback(null, true); - - // always build when module is not cacheable - if (!this.buildInfo.cacheable) return callback(null, true); + ); - // build when there is no snapshot to check - if (!this.buildInfo.snapshot) return callback(null, true); + normalModuleFactory.hooks.parser + .for("javascript/auto") + .tap("HotModuleReplacementPlugin", parser => { + applyModuleHot(parser); + applyImportMetaHot(parser); + }); + normalModuleFactory.hooks.parser + .for("javascript/dynamic") + .tap("HotModuleReplacementPlugin", parser => { + applyModuleHot(parser); + }); + normalModuleFactory.hooks.parser + .for("javascript/esm") + .tap("HotModuleReplacementPlugin", parser => { + applyImportMetaHot(parser); + }); - // build when valueDependencies have changed - /** @type {Map>} */ - const valueDependencies = this.buildInfo.valueDependencies; - if (valueDependencies) { - if (!valueCacheVersions) return callback(null, true); - for (const [key, value] of valueDependencies) { - if (value === undefined) return callback(null, true); - const current = valueCacheVersions.get(key); - if ( - value !== current && - (typeof value === "string" || - typeof current === "string" || - current === undefined || - !isSubset(value, current)) - ) { - return callback(null, true); - } + NormalModule.getCompilationHooks(compilation).loader.tap( + "HotModuleReplacementPlugin", + context => { + context.hot = true; + } + ); } - } - - // check snapshot for validity - fileSystemInfo.checkSnapshotValid(this.buildInfo.snapshot, (err, valid) => { - if (err) return callback(err); - if (!valid) return callback(null, true); - const hooks = NormalModule.getCompilationHooks(compilation); - hooks.needBuild.callAsync(this, context, (err, needBuild) => { - if (err) { - return callback( - HookWebpackError.makeWebpackError( - err, - "NormalModule.getCompilationHooks().needBuild" - ) - ); - } - callback(null, !!needBuild); - }); - }); - } - - /** - * @param {string=} type the source type for which the size should be estimated - * @returns {number} the estimated size of the module (must be non-zero) - */ - size(type) { - const cachedSize = - this._sourceSizes === undefined ? undefined : this._sourceSizes.get(type); - if (cachedSize !== undefined) { - return cachedSize; - } - const size = Math.max(1, this.generator.getSize(this, type)); - if (this._sourceSizes === undefined) { - this._sourceSizes = new Map(); - } - this._sourceSizes.set(type, size); - return size; - } - - /** - * @param {LazySet} fileDependencies set where file dependencies are added to - * @param {LazySet} contextDependencies set where context dependencies are added to - * @param {LazySet} missingDependencies set where missing dependencies are added to - * @param {LazySet} buildDependencies set where build dependencies are added to - */ - addCacheDependencies( - fileDependencies, - contextDependencies, - missingDependencies, - buildDependencies - ) { - const { snapshot, buildDependencies: buildDeps } = this.buildInfo; - if (snapshot) { - fileDependencies.addAll(snapshot.getFileIterable()); - contextDependencies.addAll(snapshot.getContextIterable()); - missingDependencies.addAll(snapshot.getMissingIterable()); - } else { - const { - fileDependencies: fileDeps, - contextDependencies: contextDeps, - missingDependencies: missingDeps - } = this.buildInfo; - if (fileDeps !== undefined) fileDependencies.addAll(fileDeps); - if (contextDeps !== undefined) contextDependencies.addAll(contextDeps); - if (missingDeps !== undefined) missingDependencies.addAll(missingDeps); - } - if (buildDeps !== undefined) { - buildDependencies.addAll(buildDeps); - } - } - - /** - * @param {Hash} hash the hash used to track dependencies - * @param {UpdateHashContext} context context - * @returns {void} - */ - updateHash(hash, context) { - hash.update(this.buildInfo.hash); - this.generator.updateHash(hash, { - module: this, - ...context - }); - super.updateHash(hash, context); - } - - serialize(context) { - const { write } = context; - // deserialize - write(this._source); - write(this.error); - write(this._lastSuccessfulBuildMeta); - write(this._forceBuild); - super.serialize(context); + ); } +} - static deserialize(context) { - const obj = new NormalModule({ - // will be deserialized by Module - layer: null, - type: "", - // will be filled by updateCacheModule - resource: "", - context: "", - request: null, - userRequest: null, - rawRequest: null, - loaders: null, - matchResource: null, - parser: null, - parserOptions: null, - generator: null, - generatorOptions: null, - resolveOptions: null - }); - obj.deserialize(context); - return obj; - } +module.exports = HotModuleReplacementPlugin; - deserialize(context) { - const { read } = context; - this._source = read(); - this.error = read(); - this._lastSuccessfulBuildMeta = read(); - this._forceBuild = read(); - super.deserialize(context); + +/***/ }), + +/***/ 39222: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ + + + +const Chunk = __webpack_require__(65574); + +/** @typedef {import("./ChunkGraph")} ChunkGraph */ +/** @typedef {import("./util/Hash")} Hash */ + +class HotUpdateChunk extends Chunk { + constructor() { + super(); } } -makeSerializable(NormalModule, "webpack/lib/NormalModule"); - -module.exports = NormalModule; +module.exports = HotUpdateChunk; /***/ }), -/***/ 99063: +/***/ 91471: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; /* MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra + Author Ivan Kopeykin @vankop */ -const { getContext } = __webpack_require__(67578); -const asyncLib = __webpack_require__(36386); -const { - AsyncSeriesBailHook, - SyncWaterfallHook, - SyncBailHook, - SyncHook, - HookMap -} = __webpack_require__(34718); -const ChunkGraph = __webpack_require__(97860); -const Module = __webpack_require__(85887); const ModuleFactory = __webpack_require__(61574); -const ModuleGraph = __webpack_require__(20258); -const NormalModule = __webpack_require__(11026); -const BasicEffectRulePlugin = __webpack_require__(70119); -const BasicMatcherRulePlugin = __webpack_require__(99083); -const ObjectMatcherRulePlugin = __webpack_require__(61166); -const RuleSetCompiler = __webpack_require__(23246); -const UseEffectRulePlugin = __webpack_require__(42541); -const LazySet = __webpack_require__(59534); -const { getScheme } = __webpack_require__(49606); -const { cachedCleverMerge, cachedSetProperty } = __webpack_require__(11217); -const { join } = __webpack_require__(93204); -const { parseResource } = __webpack_require__(96236); -/** @typedef {import("../declarations/WebpackOptions").ModuleOptionsNormalized} ModuleOptions */ -/** @typedef {import("./Generator")} Generator */ /** @typedef {import("./ModuleFactory").ModuleFactoryCreateData} ModuleFactoryCreateData */ /** @typedef {import("./ModuleFactory").ModuleFactoryResult} ModuleFactoryResult */ -/** @typedef {import("./Parser")} Parser */ -/** @typedef {import("./ResolverFactory")} ResolverFactory */ -/** @typedef {import("./dependencies/ModuleDependency")} ModuleDependency */ -/** @typedef {import("./util/fs").InputFileSystem} InputFileSystem */ +/** @typedef {import("./NormalModuleFactory")} NormalModuleFactory */ /** - * @typedef {Object} ResolveData - * @property {ModuleFactoryCreateData["contextInfo"]} contextInfo - * @property {ModuleFactoryCreateData["resolveOptions"]} resolveOptions - * @property {string} context - * @property {string} request - * @property {Record | undefined} assertions - * @property {ModuleDependency[]} dependencies - * @property {string} dependencyType - * @property {Object} createData - * @property {LazySet} fileDependencies - * @property {LazySet} missingDependencies - * @property {LazySet} contextDependencies - * @property {boolean} cacheable allow to use the unsafe cache + * Ignores error when module is unresolved */ +class IgnoreErrorModuleFactory extends ModuleFactory { + /** + * @param {NormalModuleFactory} normalModuleFactory normalModuleFactory instance + */ + constructor(normalModuleFactory) { + super(); -/** - * @typedef {Object} ResourceData - * @property {string} resource - * @property {string} path - * @property {string} query - * @property {string} fragment - * @property {string=} context - */ + this.normalModuleFactory = normalModuleFactory; + } -/** @typedef {ResourceData & { data: Record }} ResourceDataWithData */ + /** + * @param {ModuleFactoryCreateData} data data object + * @param {function(Error=, ModuleFactoryResult=): void} callback callback + * @returns {void} + */ + create(data, callback) { + this.normalModuleFactory.create(data, (err, result) => { + return callback(null, result); + }); + } +} -const EMPTY_RESOLVE_OPTIONS = {}; -const EMPTY_PARSER_OPTIONS = {}; -const EMPTY_GENERATOR_OPTIONS = {}; -const EMPTY_ELEMENTS = []; +module.exports = IgnoreErrorModuleFactory; -const MATCH_RESOURCE_REGEX = /^([^!]+)!=!/; -const loaderToIdent = data => { - if (!data.options) { - return data.loader; - } - if (typeof data.options === "string") { - return data.loader + "?" + data.options; - } - if (typeof data.options !== "object") { - throw new Error("loader options must be string or object"); - } - if (data.ident) { - return data.loader + "??" + data.ident; - } - return data.loader + "?" + JSON.stringify(data.options); -}; +/***/ }), -const stringifyLoadersAndResource = (loaders, resource) => { - let str = ""; - for (const loader of loaders) { - str += loaderToIdent(loader) + "!"; +/***/ 8098: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ + + + +const createSchemaValidation = __webpack_require__(77695); + +/** @typedef {import("../declarations/plugins/IgnorePlugin").IgnorePluginOptions} IgnorePluginOptions */ +/** @typedef {import("./Compiler")} Compiler */ +/** @typedef {import("./NormalModuleFactory").ResolveData} ResolveData */ + +const validate = createSchemaValidation( + __webpack_require__(21420), + () => __webpack_require__(51856), + { + name: "Ignore Plugin", + baseDataPath: "options" } - return str + resource; -}; +); -/** - * @param {string} resultString resultString - * @returns {{loader: string, options: string|undefined}} parsed loader request - */ -const identToLoaderRequest = resultString => { - const idx = resultString.indexOf("?"); - if (idx >= 0) { - const loader = resultString.substr(0, idx); - const options = resultString.substr(idx + 1); - return { - loader, - options - }; - } else { - return { - loader: resultString, - options: undefined - }; +class IgnorePlugin { + /** + * @param {IgnorePluginOptions} options IgnorePlugin options + */ + constructor(options) { + validate(options); + this.options = options; + + /** @private @type {Function} */ + this.checkIgnore = this.checkIgnore.bind(this); } -}; -const needCalls = (times, callback) => { - return err => { - if (--times === 0) { - return callback(err); - } - if (err && times > 0) { - times = NaN; - return callback(err); + /** + * Note that if "contextRegExp" is given, both the "resourceRegExp" + * and "contextRegExp" have to match. + * + * @param {ResolveData} resolveData resolve data + * @returns {false|undefined} returns false when the request should be ignored, otherwise undefined + */ + checkIgnore(resolveData) { + if ( + "checkResource" in this.options && + this.options.checkResource && + this.options.checkResource(resolveData.request, resolveData.context) + ) { + return false; } - }; -}; -const mergeGlobalOptions = (globalOptions, type, localOptions) => { - const parts = type.split("/"); - let result; - let current = ""; - for (const part of parts) { - current = current ? `${current}/${part}` : part; - const options = globalOptions[current]; - if (typeof options === "object") { - if (result === undefined) { - result = options; + if ( + "resourceRegExp" in this.options && + this.options.resourceRegExp && + this.options.resourceRegExp.test(resolveData.request) + ) { + if ("contextRegExp" in this.options && this.options.contextRegExp) { + // if "contextRegExp" is given, + // both the "resourceRegExp" and "contextRegExp" have to match. + if (this.options.contextRegExp.test(resolveData.context)) { + return false; + } } else { - result = cachedCleverMerge(result, options); + return false; } } } - if (result === undefined) { - return localOptions; - } else { - return cachedCleverMerge(result, localOptions); + + /** + * Apply the plugin + * @param {Compiler} compiler the compiler instance + * @returns {void} + */ + apply(compiler) { + compiler.hooks.normalModuleFactory.tap("IgnorePlugin", nmf => { + nmf.hooks.beforeResolve.tap("IgnorePlugin", this.checkIgnore); + }); + compiler.hooks.contextModuleFactory.tap("IgnorePlugin", cmf => { + cmf.hooks.beforeResolve.tap("IgnorePlugin", this.checkIgnore); + }); } -}; +} -// TODO webpack 6 remove -const deprecationChangedHookMessage = (name, hook) => { - const names = hook.taps - .map(tapped => { - return tapped.name; - }) - .join(", "); +module.exports = IgnorePlugin; - return ( - `NormalModuleFactory.${name} (${names}) is no longer a waterfall hook, but a bailing hook instead. ` + - "Do not return the passed object, but modify it instead. " + - "Returning false will ignore the request and results in no module created." - ); -}; -const ruleSetCompiler = new RuleSetCompiler([ - new BasicMatcherRulePlugin("test", "resource"), - new BasicMatcherRulePlugin("scheme"), - new BasicMatcherRulePlugin("mimetype"), - new BasicMatcherRulePlugin("dependency"), - new BasicMatcherRulePlugin("include", "resource"), - new BasicMatcherRulePlugin("exclude", "resource", true), - new BasicMatcherRulePlugin("resource"), - new BasicMatcherRulePlugin("resourceQuery"), - new BasicMatcherRulePlugin("resourceFragment"), - new BasicMatcherRulePlugin("realResource"), - new BasicMatcherRulePlugin("issuer"), - new BasicMatcherRulePlugin("compiler"), - new BasicMatcherRulePlugin("issuerLayer"), - new ObjectMatcherRulePlugin("assert", "assertions"), - new ObjectMatcherRulePlugin("descriptionData"), - new BasicEffectRulePlugin("type"), - new BasicEffectRulePlugin("sideEffects"), - new BasicEffectRulePlugin("parser"), - new BasicEffectRulePlugin("resolve"), - new BasicEffectRulePlugin("generator"), - new BasicEffectRulePlugin("layer"), - new UseEffectRulePlugin() -]); +/***/ }), -class NormalModuleFactory extends ModuleFactory { +/***/ 18913: +/***/ (function(module) { + +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ + + + +/** @typedef {import("../declarations/WebpackOptions").IgnoreWarningsNormalized} IgnoreWarningsNormalized */ +/** @typedef {import("./Compiler")} Compiler */ + +class IgnoreWarningsPlugin { /** - * @param {Object} param params - * @param {string=} param.context context - * @param {InputFileSystem} param.fs file system - * @param {ResolverFactory} param.resolverFactory resolverFactory - * @param {ModuleOptions} param.options options - * @param {Object=} param.associatedObjectForCache an object to which the cache will be attached - * @param {boolean=} param.layers enable layers + * @param {IgnoreWarningsNormalized} ignoreWarnings conditions to ignore warnings */ - constructor({ - context, - fs, - resolverFactory, - options, - associatedObjectForCache, - layers = false - }) { - super(); - this.hooks = Object.freeze({ - /** @type {AsyncSeriesBailHook<[ResolveData], TODO>} */ - resolve: new AsyncSeriesBailHook(["resolveData"]), - /** @type {HookMap>} */ - resolveForScheme: new HookMap( - () => new AsyncSeriesBailHook(["resourceData", "resolveData"]) - ), - /** @type {HookMap>} */ - resolveInScheme: new HookMap( - () => new AsyncSeriesBailHook(["resourceData", "resolveData"]) - ), - /** @type {AsyncSeriesBailHook<[ResolveData], TODO>} */ - factorize: new AsyncSeriesBailHook(["resolveData"]), - /** @type {AsyncSeriesBailHook<[ResolveData], TODO>} */ - beforeResolve: new AsyncSeriesBailHook(["resolveData"]), - /** @type {AsyncSeriesBailHook<[ResolveData], TODO>} */ - afterResolve: new AsyncSeriesBailHook(["resolveData"]), - /** @type {AsyncSeriesBailHook<[ResolveData["createData"], ResolveData], TODO>} */ - createModule: new AsyncSeriesBailHook(["createData", "resolveData"]), - /** @type {SyncWaterfallHook<[Module, ResolveData["createData"], ResolveData], TODO>} */ - module: new SyncWaterfallHook(["module", "createData", "resolveData"]), - createParser: new HookMap(() => new SyncBailHook(["parserOptions"])), - parser: new HookMap(() => new SyncHook(["parser", "parserOptions"])), - createGenerator: new HookMap( - () => new SyncBailHook(["generatorOptions"]) - ), - generator: new HookMap( - () => new SyncHook(["generator", "generatorOptions"]) - ) + constructor(ignoreWarnings) { + this._ignoreWarnings = ignoreWarnings; + } + /** + * Apply the plugin + * @param {Compiler} compiler the compiler instance + * @returns {void} + */ + apply(compiler) { + compiler.hooks.compilation.tap("IgnoreWarningsPlugin", compilation => { + compilation.hooks.processWarnings.tap( + "IgnoreWarningsPlugin", + warnings => { + return warnings.filter(warning => { + return !this._ignoreWarnings.some(ignore => + ignore(warning, compilation) + ); + }); + } + ); }); - this.resolverFactory = resolverFactory; - this.ruleSet = ruleSetCompiler.compile([ - { - rules: options.defaultRules - }, - { - rules: options.rules - } - ]); - this.context = context || ""; - this.fs = fs; - this._globalParserOptions = options.parser; - this._globalGeneratorOptions = options.generator; - /** @type {Map>} */ - this.parserCache = new Map(); - /** @type {Map>} */ - this.generatorCache = new Map(); - /** @type {Set} */ - this._restoredUnsafeCacheEntries = new Set(); + } +} - const cacheParseResource = parseResource.bindCache( - associatedObjectForCache - ); +module.exports = IgnoreWarningsPlugin; - this.hooks.factorize.tapAsync( - { - name: "NormalModuleFactory", - stage: 100 - }, - (resolveData, callback) => { - this.hooks.resolve.callAsync(resolveData, (err, result) => { - if (err) return callback(err); - // Ignored - if (result === false) return callback(); +/***/ }), - // direct module - if (result instanceof Module) return callback(null, result); +/***/ 51739: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - if (typeof result === "object") - throw new Error( - deprecationChangedHookMessage("resolve", this.hooks.resolve) + - " Returning a Module object will result in this module used as result." - ); +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Florent Cailhol @ooflorent +*/ - this.hooks.afterResolve.callAsync(resolveData, (err, result) => { - if (err) return callback(err); - if (typeof result === "object") - throw new Error( - deprecationChangedHookMessage( - "afterResolve", - this.hooks.afterResolve - ) - ); - // Ignored - if (result === false) return callback(); +const { ConcatSource } = __webpack_require__(96192); +const makeSerializable = __webpack_require__(26522); - const createData = resolveData.createData; +/** @typedef {import("webpack-sources").Source} Source */ +/** @typedef {import("./Generator").GenerateContext} GenerateContext */ - this.hooks.createModule.callAsync( - createData, - resolveData, - (err, createdModule) => { - if (!createdModule) { - if (!resolveData.request) { - return callback(new Error("Empty dependency (no request)")); - } +/** + * @param {InitFragment} fragment the init fragment + * @param {number} index index + * @returns {[InitFragment, number]} tuple with both + */ +const extractFragmentIndex = (fragment, index) => [fragment, index]; - createdModule = new NormalModule(createData); - } +/** + * @param {[InitFragment, number]} a first pair + * @param {[InitFragment, number]} b second pair + * @returns {number} sort value + */ +const sortFragmentWithIndex = ([a, i], [b, j]) => { + const stageCmp = a.stage - b.stage; + if (stageCmp !== 0) return stageCmp; + const positionCmp = a.position - b.position; + if (positionCmp !== 0) return positionCmp; + return i - j; +}; - createdModule = this.hooks.module.call( - createdModule, - createData, - resolveData - ); +/** + * @template Context + */ +class InitFragment { + /** + * @param {string|Source} content the source code that will be included as initialization code + * @param {number} stage category of initialization code (contribute to order) + * @param {number} position position in the category (contribute to order) + * @param {string=} key unique key to avoid emitting the same initialization code twice + * @param {string|Source=} endContent the source code that will be included at the end of the module + */ + constructor(content, stage, position, key, endContent) { + this.content = content; + this.stage = stage; + this.position = position; + this.key = key; + this.endContent = endContent; + } - return callback(null, createdModule); - } - ); - }); - }); - } - ); - this.hooks.resolve.tapAsync( - { - name: "NormalModuleFactory", - stage: 100 - }, - (data, callback) => { - const { - contextInfo, - context, - dependencies, - dependencyType, - request, - assertions, - resolveOptions, - fileDependencies, - missingDependencies, - contextDependencies - } = data; - const loaderResolver = this.getResolver("loader"); + /** + * @param {Context} context context + * @returns {string|Source} the source code that will be included as initialization code + */ + getContent(context) { + return this.content; + } - /** @type {ResourceData | undefined} */ - let matchResourceData = undefined; - /** @type {string} */ - let unresolvedResource; - /** @type {{loader: string, options: string|undefined}[]} */ - let elements; - let noPreAutoLoaders = false; - let noAutoLoaders = false; - let noPrePostAutoLoaders = false; + /** + * @param {Context} context context + * @returns {string|Source=} the source code that will be included at the end of the module + */ + getEndContent(context) { + return this.endContent; + } - const contextScheme = getScheme(context); - /** @type {string | undefined} */ - let scheme = getScheme(request); + static addToSource(source, initFragments, context) { + if (initFragments.length > 0) { + // Sort fragments by position. If 2 fragments have the same position, + // use their index. + const sortedFragments = initFragments + .map(extractFragmentIndex) + .sort(sortFragmentWithIndex); - if (!scheme) { - /** @type {string} */ - let requestWithoutMatchResource = request; - const matchResourceMatch = MATCH_RESOURCE_REGEX.exec(request); - if (matchResourceMatch) { - let matchResource = matchResourceMatch[1]; - if (matchResource.charCodeAt(0) === 46) { - // 46 === ".", 47 === "/" - const secondChar = matchResource.charCodeAt(1); - if ( - secondChar === 47 || - (secondChar === 46 && matchResource.charCodeAt(2) === 47) - ) { - // if matchResources startsWith ../ or ./ - matchResource = join(this.fs, context, matchResource); - } - } - matchResourceData = { - resource: matchResource, - ...cacheParseResource(matchResource) - }; - requestWithoutMatchResource = request.substr( - matchResourceMatch[0].length + // Deduplicate fragments. If a fragment has no key, it is always included. + const keyedFragments = new Map(); + for (const [fragment] of sortedFragments) { + if (typeof fragment.mergeAll === "function") { + if (!fragment.key) { + throw new Error( + `InitFragment with mergeAll function must have a valid key: ${fragment.constructor.name}` ); } - - scheme = getScheme(requestWithoutMatchResource); - - if (!scheme && !contextScheme) { - const firstChar = requestWithoutMatchResource.charCodeAt(0); - const secondChar = requestWithoutMatchResource.charCodeAt(1); - noPreAutoLoaders = firstChar === 45 && secondChar === 33; // startsWith "-!" - noAutoLoaders = noPreAutoLoaders || firstChar === 33; // startsWith "!" - noPrePostAutoLoaders = firstChar === 33 && secondChar === 33; // startsWith "!!"; - const rawElements = requestWithoutMatchResource - .slice( - noPreAutoLoaders || noPrePostAutoLoaders - ? 2 - : noAutoLoaders - ? 1 - : 0 - ) - .split(/!+/); - unresolvedResource = rawElements.pop(); - elements = rawElements.map(identToLoaderRequest); - scheme = getScheme(unresolvedResource); + const oldValue = keyedFragments.get(fragment.key); + if (oldValue === undefined) { + keyedFragments.set(fragment.key, fragment); + } else if (Array.isArray(oldValue)) { + oldValue.push(fragment); } else { - unresolvedResource = requestWithoutMatchResource; - elements = EMPTY_ELEMENTS; + keyedFragments.set(fragment.key, [oldValue, fragment]); + } + continue; + } else if (typeof fragment.merge === "function") { + const oldValue = keyedFragments.get(fragment.key); + if (oldValue !== undefined) { + keyedFragments.set(fragment.key, fragment.merge(oldValue)); + continue; } - } else { - unresolvedResource = request; - elements = EMPTY_ELEMENTS; } + keyedFragments.set(fragment.key || Symbol(), fragment); + } - const resolveContext = { - fileDependencies, - missingDependencies, - contextDependencies - }; + const concatSource = new ConcatSource(); + const endContents = []; + for (let fragment of keyedFragments.values()) { + if (Array.isArray(fragment)) { + fragment = fragment[0].mergeAll(fragment); + } + concatSource.add(fragment.getContent(context)); + const endContent = fragment.getEndContent(context); + if (endContent) { + endContents.push(endContent); + } + } - /** @type {ResourceDataWithData} */ - let resourceData; + concatSource.add(source); + for (const content of endContents.reverse()) { + concatSource.add(content); + } + return concatSource; + } else { + return source; + } + } - let loaders; + serialize(context) { + const { write } = context; - const continueCallback = needCalls(2, err => { - if (err) return callback(err); + write(this.content); + write(this.stage); + write(this.position); + write(this.key); + write(this.endContent); + } - // translate option idents - try { - for (const item of loaders) { - if (typeof item.options === "string" && item.options[0] === "?") { - const ident = item.options.substr(1); - if (ident === "[[missing ident]]") { - throw new Error( - "No ident is provided by referenced loader. " + - "When using a function for Rule.use in config you need to " + - "provide an 'ident' property for referenced loader options." - ); - } - item.options = this.ruleSet.references.get(ident); - if (item.options === undefined) { - throw new Error( - "Invalid ident is provided by referenced loader" - ); - } - item.ident = ident; - } - } - } catch (e) { - return callback(e); - } + deserialize(context) { + const { read } = context; - if (!resourceData) { - // ignored - return callback(null, dependencies[0].createIgnoredModule(context)); - } + this.content = read(); + this.stage = read(); + this.position = read(); + this.key = read(); + this.endContent = read(); + } +} - const userRequest = - (matchResourceData !== undefined - ? `${matchResourceData.resource}!=!` - : "") + - stringifyLoadersAndResource(loaders, resourceData.resource); +makeSerializable(InitFragment, "webpack/lib/InitFragment"); - const settings = {}; - const useLoadersPost = []; - const useLoaders = []; - const useLoadersPre = []; +InitFragment.prototype.merge = undefined; - // handle .webpack[] suffix - let resource; - let match; - if ( - matchResourceData && - typeof (resource = matchResourceData.resource) === "string" && - (match = /\.webpack\[([^\]]+)\]$/.exec(resource)) - ) { - settings.type = match[1]; - matchResourceData.resource = matchResourceData.resource.slice( - 0, - -settings.type.length - 10 - ); - } else { - settings.type = "javascript/auto"; - const resourceDataForRules = matchResourceData || resourceData; - const result = this.ruleSet.exec({ - resource: resourceDataForRules.path, - realResource: resourceData.path, - resourceQuery: resourceDataForRules.query, - resourceFragment: resourceDataForRules.fragment, - scheme, - assertions, - mimetype: matchResourceData - ? "" - : resourceData.data.mimetype || "", - dependency: dependencyType, - descriptionData: matchResourceData - ? undefined - : resourceData.data.descriptionFileData, - issuer: contextInfo.issuer, - compiler: contextInfo.compiler, - issuerLayer: contextInfo.issuerLayer || "" - }); - for (const r of result) { - if (r.type === "use") { - if (!noAutoLoaders && !noPrePostAutoLoaders) { - useLoaders.push(r.value); - } - } else if (r.type === "use-post") { - if (!noPrePostAutoLoaders) { - useLoadersPost.push(r.value); - } - } else if (r.type === "use-pre") { - if (!noPreAutoLoaders && !noPrePostAutoLoaders) { - useLoadersPre.push(r.value); - } - } else if ( - typeof r.value === "object" && - r.value !== null && - typeof settings[r.type] === "object" && - settings[r.type] !== null - ) { - settings[r.type] = cachedCleverMerge(settings[r.type], r.value); - } else { - settings[r.type] = r.value; - } - } - } +InitFragment.STAGE_CONSTANTS = 10; +InitFragment.STAGE_ASYNC_BOUNDARY = 20; +InitFragment.STAGE_HARMONY_EXPORTS = 30; +InitFragment.STAGE_HARMONY_IMPORTS = 40; +InitFragment.STAGE_PROVIDES = 50; +InitFragment.STAGE_ASYNC_DEPENDENCIES = 60; +InitFragment.STAGE_ASYNC_HARMONY_IMPORTS = 70; - let postLoaders, normalLoaders, preLoaders; +module.exports = InitFragment; - const continueCallback = needCalls(3, err => { - if (err) { - return callback(err); - } - const allLoaders = postLoaders; - if (matchResourceData === undefined) { - for (const loader of loaders) allLoaders.push(loader); - for (const loader of normalLoaders) allLoaders.push(loader); - } else { - for (const loader of normalLoaders) allLoaders.push(loader); - for (const loader of loaders) allLoaders.push(loader); - } - for (const loader of preLoaders) allLoaders.push(loader); - let type = settings.type; - const resolveOptions = settings.resolve; - const layer = settings.layer; - if (layer !== undefined && !layers) { - return callback( - new Error( - "'Rule.layer' is only allowed when 'experiments.layers' is enabled" - ) - ); - } - try { - Object.assign(data.createData, { - layer: - layer === undefined ? contextInfo.issuerLayer || null : layer, - request: stringifyLoadersAndResource( - allLoaders, - resourceData.resource - ), - userRequest, - rawRequest: request, - loaders: allLoaders, - resource: resourceData.resource, - context: - resourceData.context || getContext(resourceData.resource), - matchResource: matchResourceData - ? matchResourceData.resource - : undefined, - resourceResolveData: resourceData.data, - settings, - type, - parser: this.getParser(type, settings.parser), - parserOptions: settings.parser, - generator: this.getGenerator(type, settings.generator), - generatorOptions: settings.generator, - resolveOptions - }); - } catch (e) { - return callback(e); - } - callback(); - }); - this.resolveRequestArray( - contextInfo, - this.context, - useLoadersPost, - loaderResolver, - resolveContext, - (err, result) => { - postLoaders = result; - continueCallback(err); - } - ); - this.resolveRequestArray( - contextInfo, - this.context, - useLoaders, - loaderResolver, - resolveContext, - (err, result) => { - normalLoaders = result; - continueCallback(err); - } - ); - this.resolveRequestArray( - contextInfo, - this.context, - useLoadersPre, - loaderResolver, - resolveContext, - (err, result) => { - preLoaders = result; - continueCallback(err); - } - ); - }); - this.resolveRequestArray( - contextInfo, - contextScheme ? this.context : context, - elements, - loaderResolver, - resolveContext, - (err, result) => { - if (err) return continueCallback(err); - loaders = result; - continueCallback(); - } - ); +/***/ }), - const defaultResolve = context => { - if (/^($|\?)/.test(unresolvedResource)) { - resourceData = { - resource: unresolvedResource, - data: {}, - ...cacheParseResource(unresolvedResource) - }; - continueCallback(); - } +/***/ 2822: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - // resource without scheme and with path - else { - const normalResolver = this.getResolver( - "normal", - dependencyType - ? cachedSetProperty( - resolveOptions || EMPTY_RESOLVE_OPTIONS, - "dependencyType", - dependencyType - ) - : resolveOptions - ); - this.resolveResource( - contextInfo, - context, - unresolvedResource, - normalResolver, - resolveContext, - (err, resolvedResource, resolvedResourceResolveData) => { - if (err) return continueCallback(err); - if (resolvedResource !== false) { - resourceData = { - resource: resolvedResource, - data: resolvedResourceResolveData, - ...cacheParseResource(resolvedResource) - }; - } - continueCallback(); - } - ); - } - }; +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ - // resource with scheme - if (scheme) { - resourceData = { - resource: unresolvedResource, - data: {}, - path: undefined, - query: undefined, - fragment: undefined, - context: undefined - }; - this.hooks.resolveForScheme - .for(scheme) - .callAsync(resourceData, data, err => { - if (err) return continueCallback(err); - continueCallback(); - }); - } - // resource within scheme - else if (contextScheme) { - resourceData = { - resource: unresolvedResource, - data: {}, - path: undefined, - query: undefined, - fragment: undefined, - context: undefined - }; - this.hooks.resolveInScheme - .for(contextScheme) - .callAsync(resourceData, data, (err, handled) => { - if (err) return continueCallback(err); - if (!handled) return defaultResolve(this.context); - continueCallback(); - }); - } - // resource without scheme and without path - else defaultResolve(context); - } - ); - } +const WebpackError = __webpack_require__(68422); +const makeSerializable = __webpack_require__(26522); - cleanupForCache() { - for (const module of this._restoredUnsafeCacheEntries) { - ChunkGraph.clearChunkGraphForModule(module); - ModuleGraph.clearModuleGraphForModule(module); - module.cleanupForCache(); - } +/** @typedef {import("./Dependency").DependencyLocation} DependencyLocation */ +/** @typedef {import("./Module")} Module */ + +class InvalidDependenciesModuleWarning extends WebpackError { + /** + * @param {Module} module module tied to dependency + * @param {Iterable} deps invalid dependencies + */ + constructor(module, deps) { + const orderedDeps = deps ? Array.from(deps).sort() : []; + const depsList = orderedDeps.map(dep => ` * ${JSON.stringify(dep)}`); + super(`Invalid dependencies have been reported by plugins or loaders for this module. All reported dependencies need to be absolute paths. +Invalid dependencies may lead to broken watching and caching. +As best effort we try to convert all invalid values to absolute paths and converting globs into context dependencies, but this is deprecated behavior. +Loaders: Pass absolute paths to this.addDependency (existing files), this.addMissingDependency (not existing files), and this.addContextDependency (directories). +Plugins: Pass absolute paths to fileDependencies (existing files), missingDependencies (not existing files), and contextDependencies (directories). +Globs: They are not supported. Pass absolute path to the directory as context dependencies. +The following invalid values have been reported: +${depsList.slice(0, 3).join("\n")}${ + depsList.length > 3 ? "\n * and more ..." : "" + }`); + + this.name = "InvalidDependenciesModuleWarning"; + this.details = depsList.slice(3).join("\n"); + this.module = module; } +} - /** - * @param {ModuleFactoryCreateData} data data object - * @param {function(Error=, ModuleFactoryResult=): void} callback callback - * @returns {void} - */ - create(data, callback) { - const dependencies = /** @type {ModuleDependency[]} */ (data.dependencies); - const context = data.context || this.context; - const resolveOptions = data.resolveOptions || EMPTY_RESOLVE_OPTIONS; - const dependency = dependencies[0]; - const request = dependency.request; - const assertions = dependency.assertions; - const contextInfo = data.contextInfo; - const fileDependencies = new LazySet(); - const missingDependencies = new LazySet(); - const contextDependencies = new LazySet(); - const dependencyType = - (dependencies.length > 0 && dependencies[0].category) || ""; - /** @type {ResolveData} */ - const resolveData = { - contextInfo, - resolveOptions, - context, - request, - assertions, - dependencies, - dependencyType, - fileDependencies, - missingDependencies, - contextDependencies, - createData: {}, - cacheable: true - }; - this.hooks.beforeResolve.callAsync(resolveData, (err, result) => { - if (err) { - return callback(err, { - fileDependencies, - missingDependencies, - contextDependencies, - cacheable: false - }); - } +makeSerializable( + InvalidDependenciesModuleWarning, + "webpack/lib/InvalidDependenciesModuleWarning" +); - // Ignored - if (result === false) { - return callback(null, { - fileDependencies, - missingDependencies, - contextDependencies, - cacheable: resolveData.cacheable - }); - } +module.exports = InvalidDependenciesModuleWarning; - if (typeof result === "object") - throw new Error( - deprecationChangedHookMessage( - "beforeResolve", - this.hooks.beforeResolve - ) - ); - this.hooks.factorize.callAsync(resolveData, (err, module) => { - if (err) { - return callback(err, { - fileDependencies, - missingDependencies, - contextDependencies, - cacheable: false - }); - } +/***/ }), - const factoryResult = { - module, - fileDependencies, - missingDependencies, - contextDependencies, - cacheable: resolveData.cacheable - }; +/***/ 38197: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - callback(null, factoryResult); - }); - }); - } +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Sergey Melyukov @smelukov +*/ - resolveResource( - contextInfo, - context, - unresolvedResource, - resolver, - resolveContext, - callback - ) { - resolver.resolve( - contextInfo, - context, - unresolvedResource, - resolveContext, - (err, resolvedResource, resolvedResourceResolveData) => { - if (err) { - return this._resolveResourceErrorHints( - err, - contextInfo, - context, - unresolvedResource, - resolver, - resolveContext, - (err2, hints) => { - if (err2) { - err.message += ` -An fatal error happened during resolving additional hints for this error: ${err2.message}`; - err.stack += ` -An fatal error happened during resolving additional hints for this error: -${err2.stack}`; - return callback(err); - } - if (hints && hints.length > 0) { - err.message += ` -${hints.join("\n\n")}`; - } - callback(err); - } - ); - } - callback(err, resolvedResource, resolvedResourceResolveData); - } - ); - } - _resolveResourceErrorHints( - error, - contextInfo, - context, - unresolvedResource, - resolver, - resolveContext, - callback - ) { - asyncLib.parallel( - [ - callback => { - if (!resolver.options.fullySpecified) return callback(); - resolver - .withOptions({ - fullySpecified: false - }) - .resolve( - contextInfo, - context, - unresolvedResource, - resolveContext, - (err, resolvedResource) => { - if (!err && resolvedResource) { - const resource = parseResource(resolvedResource).path.replace( - /^.*[\\/]/, - "" - ); - return callback( - null, - `Did you mean '${resource}'? -BREAKING CHANGE: The request '${unresolvedResource}' failed to resolve only because it was resolved as fully specified -(probably because the origin is strict EcmaScript Module, e. g. a module with javascript mimetype, a '*.mjs' file, or a '*.js' file where the package.json contains '"type": "module"'). -The extension in the request is mandatory for it to be fully specified. -Add the extension to the request.` - ); - } - callback(); - } - ); - }, - callback => { - if (!resolver.options.enforceExtension) return callback(); - resolver - .withOptions({ - enforceExtension: false, - extensions: [] - }) - .resolve( - contextInfo, - context, - unresolvedResource, - resolveContext, - (err, resolvedResource) => { - if (!err && resolvedResource) { - let hint = ""; - const match = /(\.[^.]+)(\?|$)/.exec(unresolvedResource); - if (match) { - const fixedRequest = unresolvedResource.replace( - /(\.[^.]+)(\?|$)/, - "$2" - ); - if (resolver.options.extensions.has(match[1])) { - hint = `Did you mean '${fixedRequest}'?`; - } else { - hint = `Did you mean '${fixedRequest}'? Also note that '${match[1]}' is not in 'resolve.extensions' yet and need to be added for this to work?`; - } - } else { - hint = `Did you mean to omit the extension or to remove 'resolve.enforceExtension'?`; - } - return callback( - null, - `The request '${unresolvedResource}' failed to resolve only because 'resolve.enforceExtension' was specified. -${hint} -Including the extension in the request is no longer possible. Did you mean to enforce including the extension in requests with 'resolve.extensions: []' instead?` - ); - } - callback(); +const InnerGraph = __webpack_require__(92886); + +/** @typedef {import("./Compiler")} Compiler */ +/** @typedef {import("./javascript/JavascriptParser")} JavascriptParser */ + +class JavascriptMetaInfoPlugin { + /** + * Apply the plugin + * @param {Compiler} compiler the compiler instance + * @returns {void} + */ + apply(compiler) { + compiler.hooks.compilation.tap( + "JavascriptMetaInfoPlugin", + (compilation, { normalModuleFactory }) => { + /** + * @param {JavascriptParser} parser the parser + * @returns {void} + */ + const handler = parser => { + parser.hooks.call.for("eval").tap("JavascriptMetaInfoPlugin", () => { + parser.state.module.buildInfo.moduleConcatenationBailout = "eval()"; + parser.state.module.buildInfo.usingEval = true; + const currentSymbol = InnerGraph.getTopLevelSymbol(parser.state); + if (currentSymbol) { + InnerGraph.addUsage(parser.state, null, currentSymbol); + } else { + InnerGraph.bailout(parser.state); + } + }); + parser.hooks.finish.tap("JavascriptMetaInfoPlugin", () => { + let topLevelDeclarations = + parser.state.module.buildInfo.topLevelDeclarations; + if (topLevelDeclarations === undefined) { + topLevelDeclarations = + parser.state.module.buildInfo.topLevelDeclarations = new Set(); + } + for (const name of parser.scope.definitions.asSet()) { + const freeInfo = parser.getFreeInfoFromVariable(name); + if (freeInfo === undefined) { + topLevelDeclarations.add(name); } - ); - }, - callback => { - if ( - /^\.\.?\//.test(unresolvedResource) || - resolver.options.preferRelative - ) { - return callback(); - } - resolver.resolve( - contextInfo, - context, - `./${unresolvedResource}`, - resolveContext, - (err, resolvedResource) => { - if (err || !resolvedResource) return callback(); - const moduleDirectories = resolver.options.modules - .map(m => (Array.isArray(m) ? m.join(", ") : m)) - .join(", "); - callback( - null, - `Did you mean './${unresolvedResource}'? -Requests that should resolve in the current directory need to start with './'. -Requests that start with a name are treated as module requests and resolve within module directories (${moduleDirectories}). -If changing the source code is not an option there is also a resolve options called 'preferRelative' which tries to resolve these kind of requests in the current directory too.` - ); } - ); - } - ], - (err, hints) => { - if (err) return callback(err); - callback(null, hints.filter(Boolean)); + }); + }; + + normalModuleFactory.hooks.parser + .for("javascript/auto") + .tap("JavascriptMetaInfoPlugin", handler); + normalModuleFactory.hooks.parser + .for("javascript/dynamic") + .tap("JavascriptMetaInfoPlugin", handler); + normalModuleFactory.hooks.parser + .for("javascript/esm") + .tap("JavascriptMetaInfoPlugin", handler); } ); } +} - resolveRequestArray( - contextInfo, - context, - array, - resolver, - resolveContext, - callback - ) { - if (array.length === 0) return callback(null, array); - asyncLib.map( - array, - (item, callback) => { - resolver.resolve( - contextInfo, - context, - item.loader, - resolveContext, - (err, result) => { - if ( - err && - /^[^/]*$/.test(item.loader) && - !/-loader$/.test(item.loader) - ) { - return resolver.resolve( - contextInfo, - context, - item.loader + "-loader", - resolveContext, - err2 => { - if (!err2) { - err.message = - err.message + - "\n" + - "BREAKING CHANGE: It's no longer allowed to omit the '-loader' suffix when using loaders.\n" + - ` You need to specify '${item.loader}-loader' instead of '${item.loader}',\n` + - " see https://webpack.js.org/migrate/3/#automatic-loader-module-name-extension-removed"; - } - callback(err); - } - ); - } - if (err) return callback(err); +module.exports = JavascriptMetaInfoPlugin; - const parsedResult = identToLoaderRequest(result); - const resolved = { - loader: parsedResult.loader, - options: - item.options === undefined - ? parsedResult.options - : item.options, - ident: item.options === undefined ? undefined : item.ident - }; - return callback(null, resolved); - } - ); - }, - callback - ); - } - getParser(type, parserOptions = EMPTY_PARSER_OPTIONS) { - let cache = this.parserCache.get(type); +/***/ }), - if (cache === undefined) { - cache = new WeakMap(); - this.parserCache.set(type, cache); - } +/***/ 30711: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - let parser = cache.get(parserOptions); +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ - if (parser === undefined) { - parser = this.createParser(type, parserOptions); - cache.set(parserOptions, parser); - } - return parser; + +const asyncLib = __webpack_require__(36386); +const EntryDependency = __webpack_require__(41075); +const { someInIterable } = __webpack_require__(31065); +const { compareModulesById } = __webpack_require__(26296); +const { dirname, mkdirp } = __webpack_require__(93204); + +/** @typedef {import("./Compiler")} Compiler */ + +/** + * @typedef {Object} ManifestModuleData + * @property {string | number} id + * @property {Object} buildMeta + * @property {boolean | string[]} exports + */ + +class LibManifestPlugin { + constructor(options) { + this.options = options; } /** - * @param {string} type type - * @param {{[k: string]: any}} parserOptions parser options - * @returns {Parser} parser + * Apply the plugin + * @param {Compiler} compiler the compiler instance + * @returns {void} */ - createParser(type, parserOptions = {}) { - parserOptions = mergeGlobalOptions( - this._globalParserOptions, - type, - parserOptions + apply(compiler) { + compiler.hooks.emit.tapAsync( + "LibManifestPlugin", + (compilation, callback) => { + const moduleGraph = compilation.moduleGraph; + asyncLib.forEach( + Array.from(compilation.chunks), + (chunk, callback) => { + if (!chunk.canBeInitial()) { + callback(); + return; + } + const chunkGraph = compilation.chunkGraph; + const targetPath = compilation.getPath(this.options.path, { + chunk + }); + const name = + this.options.name && + compilation.getPath(this.options.name, { + chunk + }); + const content = Object.create(null); + for (const module of chunkGraph.getOrderedChunkModulesIterable( + chunk, + compareModulesById(chunkGraph) + )) { + if ( + this.options.entryOnly && + !someInIterable( + moduleGraph.getIncomingConnections(module), + c => c.dependency instanceof EntryDependency + ) + ) { + continue; + } + const ident = module.libIdent({ + context: this.options.context || compiler.options.context, + associatedObjectForCache: compiler.root + }); + if (ident) { + const exportsInfo = moduleGraph.getExportsInfo(module); + const providedExports = exportsInfo.getProvidedExports(); + /** @type {ManifestModuleData} */ + const data = { + id: chunkGraph.getModuleId(module), + buildMeta: module.buildMeta, + exports: Array.isArray(providedExports) + ? providedExports + : undefined + }; + content[ident] = data; + } + } + const manifest = { + name, + type: this.options.type, + content + }; + // Apply formatting to content if format flag is true; + const manifestContent = this.options.format + ? JSON.stringify(manifest, null, 2) + : JSON.stringify(manifest); + const buffer = Buffer.from(manifestContent, "utf8"); + mkdirp( + compiler.intermediateFileSystem, + dirname(compiler.intermediateFileSystem, targetPath), + err => { + if (err) return callback(err); + compiler.intermediateFileSystem.writeFile( + targetPath, + buffer, + callback + ); + } + ); + }, + callback + ); + } ); - const parser = this.hooks.createParser.for(type).call(parserOptions); - if (!parser) { - throw new Error(`No parser registered for ${type}`); - } - this.hooks.parser.for(type).call(parser, parserOptions); - return parser; } +} +module.exports = LibManifestPlugin; - getGenerator(type, generatorOptions = EMPTY_GENERATOR_OPTIONS) { - let cache = this.generatorCache.get(type); - if (cache === undefined) { - cache = new WeakMap(); - this.generatorCache.set(type, cache); - } +/***/ }), + +/***/ 81735: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ - let generator = cache.get(generatorOptions); - if (generator === undefined) { - generator = this.createGenerator(type, generatorOptions); - cache.set(generatorOptions, generator); - } - return generator; - } +const EnableLibraryPlugin = __webpack_require__(35613); - createGenerator(type, generatorOptions = {}) { - generatorOptions = mergeGlobalOptions( - this._globalGeneratorOptions, - type, - generatorOptions - ); - const generator = this.hooks.createGenerator - .for(type) - .call(generatorOptions); - if (!generator) { - throw new Error(`No generator registered for ${type}`); - } - this.hooks.generator.for(type).call(generator, generatorOptions); - return generator; +/** @typedef {import("../declarations/WebpackOptions").AuxiliaryComment} AuxiliaryComment */ +/** @typedef {import("../declarations/WebpackOptions").LibraryExport} LibraryExport */ +/** @typedef {import("../declarations/WebpackOptions").LibraryName} LibraryName */ +/** @typedef {import("../declarations/WebpackOptions").LibraryType} LibraryType */ +/** @typedef {import("../declarations/WebpackOptions").UmdNamedDefine} UmdNamedDefine */ +/** @typedef {import("./Compiler")} Compiler */ + +// TODO webpack 6 remove +class LibraryTemplatePlugin { + /** + * @param {LibraryName} name name of library + * @param {LibraryType} target type of library + * @param {UmdNamedDefine} umdNamedDefine setting this to true will name the UMD module + * @param {AuxiliaryComment} auxiliaryComment comment in the UMD wrapper + * @param {LibraryExport} exportProperty which export should be exposed as library + */ + constructor(name, target, umdNamedDefine, auxiliaryComment, exportProperty) { + this.library = { + type: target || "var", + name, + umdNamedDefine, + auxiliaryComment, + export: exportProperty + }; } - getResolver(type, resolveOptions) { - return this.resolverFactory.get(type, resolveOptions); + /** + * Apply the plugin + * @param {Compiler} compiler the compiler instance + * @returns {void} + */ + apply(compiler) { + const { output } = compiler.options; + output.library = this.library; + new EnableLibraryPlugin(this.library.type).apply(compiler); } } -module.exports = NormalModuleFactory; +module.exports = LibraryTemplatePlugin; /***/ }), -/***/ 12747: +/***/ 73047: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; @@ -56476,20 +50548,34 @@ module.exports = NormalModuleFactory; -const { join, dirname } = __webpack_require__(93204); +const ModuleFilenameHelpers = __webpack_require__(80295); +const NormalModule = __webpack_require__(11026); +const createSchemaValidation = __webpack_require__(77695); +/** @typedef {import("../declarations/plugins/LoaderOptionsPlugin").LoaderOptionsPluginOptions} LoaderOptionsPluginOptions */ /** @typedef {import("./Compiler")} Compiler */ -/** @typedef {function(TODO): void} ModuleReplacer */ -class NormalModuleReplacementPlugin { +const validate = createSchemaValidation( + __webpack_require__(36012), + () => __webpack_require__(56086), + { + name: "Loader Options Plugin", + baseDataPath: "options" + } +); +class LoaderOptionsPlugin { /** - * Create an instance of the plugin - * @param {RegExp} resourceRegExp the resource matcher - * @param {string|ModuleReplacer} newResource the resource replacement + * @param {LoaderOptionsPluginOptions} options options object */ - constructor(resourceRegExp, newResource) { - this.resourceRegExp = resourceRegExp; - this.newResource = newResource; + constructor(options = {}) { + validate(options); + if (typeof options !== "object") options = {}; + if (!options.test) { + options.test = { + test: () => true + }; + } + this.options = options; } /** @@ -56498,72 +50584,85 @@ class NormalModuleReplacementPlugin { * @returns {void} */ apply(compiler) { - const resourceRegExp = this.resourceRegExp; - const newResource = this.newResource; - compiler.hooks.normalModuleFactory.tap( - "NormalModuleReplacementPlugin", - nmf => { - nmf.hooks.beforeResolve.tap("NormalModuleReplacementPlugin", result => { - if (resourceRegExp.test(result.request)) { - if (typeof newResource === "function") { - newResource(result); - } else { - result.request = newResource; - } - } - }); - nmf.hooks.afterResolve.tap("NormalModuleReplacementPlugin", result => { - const createData = result.createData; - if (resourceRegExp.test(createData.resource)) { - if (typeof newResource === "function") { - newResource(result); - } else { - const fs = compiler.inputFileSystem; - if ( - newResource.startsWith("/") || - (newResource.length > 1 && newResource[1] === ":") - ) { - createData.resource = newResource; - } else { - createData.resource = join( - fs, - dirname(fs, createData.resource), - newResource - ); + const options = this.options; + compiler.hooks.compilation.tap("LoaderOptionsPlugin", compilation => { + NormalModule.getCompilationHooks(compilation).loader.tap( + "LoaderOptionsPlugin", + (context, module) => { + const resource = module.resource; + if (!resource) return; + const i = resource.indexOf("?"); + if ( + ModuleFilenameHelpers.matchObject( + options, + i < 0 ? resource : resource.substr(0, i) + ) + ) { + for (const key of Object.keys(options)) { + if (key === "include" || key === "exclude" || key === "test") { + continue; } + context[key] = options[key]; } } - }); - } - ); + } + ); + }); } } -module.exports = NormalModuleReplacementPlugin; +module.exports = LoaderOptionsPlugin; /***/ }), -/***/ 68145: -/***/ (function(__unused_webpack_module, exports) { +/***/ 94834: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; /* MIT License http://www.opensource.org/licenses/mit-license.php - Author Florent Cailhol @ooflorent + Author Tobias Koppers @sokra */ -exports.STAGE_BASIC = -10; -exports.STAGE_DEFAULT = 0; -exports.STAGE_ADVANCED = 10; +const NormalModule = __webpack_require__(11026); + +/** @typedef {import("./Compiler")} Compiler */ + +class LoaderTargetPlugin { + /** + * @param {string} target the target + */ + constructor(target) { + this.target = target; + } + + /** + * Apply the plugin + * @param {Compiler} compiler the compiler instance + * @returns {void} + */ + apply(compiler) { + compiler.hooks.compilation.tap("LoaderTargetPlugin", compilation => { + NormalModule.getCompilationHooks(compilation).loader.tap( + "LoaderTargetPlugin", + loaderContext => { + loaderContext.target = this.target; + } + ); + }); + } +} + +module.exports = LoaderTargetPlugin; /***/ }), -/***/ 88104: -/***/ (function(module) { +/***/ 30518: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; /* @@ -56573,15 +50672,333 @@ exports.STAGE_ADVANCED = 10; -class OptionsApply { - process(options, compiler) {} -} -module.exports = OptionsApply; +const { SyncWaterfallHook } = __webpack_require__(34718); +const util = __webpack_require__(31669); +const RuntimeGlobals = __webpack_require__(49404); +const memoize = __webpack_require__(84297); + +/** @typedef {import("webpack-sources").ConcatSource} ConcatSource */ +/** @typedef {import("webpack-sources").Source} Source */ +/** @typedef {import("../declarations/WebpackOptions").Output} OutputOptions */ +/** @typedef {import("./ModuleTemplate")} ModuleTemplate */ +/** @typedef {import("./Chunk")} Chunk */ +/** @typedef {import("./Compilation")} Compilation */ +/** @typedef {import("./Compilation").AssetInfo} AssetInfo */ +/** @typedef {import("./Module")} Module} */ +/** @typedef {import("./util/Hash")} Hash} */ +/** @typedef {import("./DependencyTemplates")} DependencyTemplates} */ +/** @typedef {import("./javascript/JavascriptModulesPlugin").RenderContext} RenderContext} */ +/** @typedef {import("./RuntimeTemplate")} RuntimeTemplate} */ +/** @typedef {import("./ModuleGraph")} ModuleGraph} */ +/** @typedef {import("./ChunkGraph")} ChunkGraph} */ +/** @typedef {import("./Template").RenderManifestOptions} RenderManifestOptions} */ +/** @typedef {import("./Template").RenderManifestEntry} RenderManifestEntry} */ + +const getJavascriptModulesPlugin = memoize(() => + __webpack_require__(76767) +); +const getJsonpTemplatePlugin = memoize(() => + __webpack_require__(45968) +); +const getLoadScriptRuntimeModule = memoize(() => + __webpack_require__(80647) +); + +// TODO webpack 6 remove this class +class MainTemplate { + /** + * + * @param {OutputOptions} outputOptions output options for the MainTemplate + * @param {Compilation} compilation the compilation + */ + constructor(outputOptions, compilation) { + /** @type {OutputOptions} */ + this._outputOptions = outputOptions || {}; + this.hooks = Object.freeze({ + renderManifest: { + tap: util.deprecate( + (options, fn) => { + compilation.hooks.renderManifest.tap( + options, + (entries, options) => { + if (!options.chunk.hasRuntime()) return entries; + return fn(entries, options); + } + ); + }, + "MainTemplate.hooks.renderManifest is deprecated (use Compilation.hooks.renderManifest instead)", + "DEP_WEBPACK_MAIN_TEMPLATE_RENDER_MANIFEST" + ) + }, + modules: { + tap: () => { + throw new Error( + "MainTemplate.hooks.modules has been removed (there is no replacement, please create an issue to request that)" + ); + } + }, + moduleObj: { + tap: () => { + throw new Error( + "MainTemplate.hooks.moduleObj has been removed (there is no replacement, please create an issue to request that)" + ); + } + }, + require: { + tap: util.deprecate( + (options, fn) => { + getJavascriptModulesPlugin() + .getCompilationHooks(compilation) + .renderRequire.tap(options, fn); + }, + "MainTemplate.hooks.require is deprecated (use JavascriptModulesPlugin.getCompilationHooks().renderRequire instead)", + "DEP_WEBPACK_MAIN_TEMPLATE_REQUIRE" + ) + }, + beforeStartup: { + tap: () => { + throw new Error( + "MainTemplate.hooks.beforeStartup has been removed (use RuntimeGlobals.startupOnlyBefore instead)" + ); + } + }, + startup: { + tap: () => { + throw new Error( + "MainTemplate.hooks.startup has been removed (use RuntimeGlobals.startup instead)" + ); + } + }, + afterStartup: { + tap: () => { + throw new Error( + "MainTemplate.hooks.afterStartup has been removed (use RuntimeGlobals.startupOnlyAfter instead)" + ); + } + }, + render: { + tap: util.deprecate( + (options, fn) => { + getJavascriptModulesPlugin() + .getCompilationHooks(compilation) + .render.tap(options, (source, renderContext) => { + if ( + renderContext.chunkGraph.getNumberOfEntryModules( + renderContext.chunk + ) === 0 || + !renderContext.chunk.hasRuntime() + ) { + return source; + } + return fn( + source, + renderContext.chunk, + compilation.hash, + compilation.moduleTemplates.javascript, + compilation.dependencyTemplates + ); + }); + }, + "MainTemplate.hooks.render is deprecated (use JavascriptModulesPlugin.getCompilationHooks().render instead)", + "DEP_WEBPACK_MAIN_TEMPLATE_RENDER" + ) + }, + renderWithEntry: { + tap: util.deprecate( + (options, fn) => { + getJavascriptModulesPlugin() + .getCompilationHooks(compilation) + .render.tap(options, (source, renderContext) => { + if ( + renderContext.chunkGraph.getNumberOfEntryModules( + renderContext.chunk + ) === 0 || + !renderContext.chunk.hasRuntime() + ) { + return source; + } + return fn(source, renderContext.chunk, compilation.hash); + }); + }, + "MainTemplate.hooks.renderWithEntry is deprecated (use JavascriptModulesPlugin.getCompilationHooks().render instead)", + "DEP_WEBPACK_MAIN_TEMPLATE_RENDER_WITH_ENTRY" + ) + }, + assetPath: { + tap: util.deprecate( + (options, fn) => { + compilation.hooks.assetPath.tap(options, fn); + }, + "MainTemplate.hooks.assetPath is deprecated (use Compilation.hooks.assetPath instead)", + "DEP_WEBPACK_MAIN_TEMPLATE_ASSET_PATH" + ), + call: util.deprecate( + (filename, options) => { + return compilation.getAssetPath(filename, options); + }, + "MainTemplate.hooks.assetPath is deprecated (use Compilation.hooks.assetPath instead)", + "DEP_WEBPACK_MAIN_TEMPLATE_ASSET_PATH" + ) + }, + hash: { + tap: util.deprecate( + (options, fn) => { + compilation.hooks.fullHash.tap(options, fn); + }, + "MainTemplate.hooks.hash is deprecated (use Compilation.hooks.fullHash instead)", + "DEP_WEBPACK_MAIN_TEMPLATE_HASH" + ) + }, + hashForChunk: { + tap: util.deprecate( + (options, fn) => { + getJavascriptModulesPlugin() + .getCompilationHooks(compilation) + .chunkHash.tap(options, (chunk, hash) => { + if (!chunk.hasRuntime()) return; + return fn(hash, chunk); + }); + }, + "MainTemplate.hooks.hashForChunk is deprecated (use JavascriptModulesPlugin.getCompilationHooks().chunkHash instead)", + "DEP_WEBPACK_MAIN_TEMPLATE_HASH_FOR_CHUNK" + ) + }, + globalHashPaths: { + tap: util.deprecate( + () => {}, + "MainTemplate.hooks.globalHashPaths has been removed (it's no longer needed)", + "DEP_WEBPACK_MAIN_TEMPLATE_HASH_FOR_CHUNK" + ) + }, + globalHash: { + tap: util.deprecate( + () => {}, + "MainTemplate.hooks.globalHash has been removed (it's no longer needed)", + "DEP_WEBPACK_MAIN_TEMPLATE_HASH_FOR_CHUNK" + ) + }, + hotBootstrap: { + tap: () => { + throw new Error( + "MainTemplate.hooks.hotBootstrap has been removed (use your own RuntimeModule instead)" + ); + } + }, + + // for compatibility: + /** @type {SyncWaterfallHook<[string, Chunk, string, ModuleTemplate, DependencyTemplates]>} */ + bootstrap: new SyncWaterfallHook([ + "source", + "chunk", + "hash", + "moduleTemplate", + "dependencyTemplates" + ]), + /** @type {SyncWaterfallHook<[string, Chunk, string]>} */ + localVars: new SyncWaterfallHook(["source", "chunk", "hash"]), + /** @type {SyncWaterfallHook<[string, Chunk, string]>} */ + requireExtensions: new SyncWaterfallHook(["source", "chunk", "hash"]), + /** @type {SyncWaterfallHook<[string, Chunk, string, string]>} */ + requireEnsure: new SyncWaterfallHook([ + "source", + "chunk", + "hash", + "chunkIdExpression" + ]), + get jsonpScript() { + const hooks = + getLoadScriptRuntimeModule().getCompilationHooks(compilation); + return hooks.createScript; + }, + get linkPrefetch() { + const hooks = getJsonpTemplatePlugin().getCompilationHooks(compilation); + return hooks.linkPrefetch; + }, + get linkPreload() { + const hooks = getJsonpTemplatePlugin().getCompilationHooks(compilation); + return hooks.linkPreload; + } + }); + + this.renderCurrentHashCode = util.deprecate( + /** + * @deprecated + * @param {string} hash the hash + * @param {number=} length length of the hash + * @returns {string} generated code + */ (hash, length) => { + if (length) { + return `${RuntimeGlobals.getFullHash} ? ${ + RuntimeGlobals.getFullHash + }().slice(0, ${length}) : ${hash.slice(0, length)}`; + } + return `${RuntimeGlobals.getFullHash} ? ${RuntimeGlobals.getFullHash}() : ${hash}`; + }, + "MainTemplate.renderCurrentHashCode is deprecated (use RuntimeGlobals.getFullHash runtime function instead)", + "DEP_WEBPACK_MAIN_TEMPLATE_RENDER_CURRENT_HASH_CODE" + ); + + this.getPublicPath = util.deprecate( + /** + * + * @param {object} options get public path options + * @returns {string} hook call + */ options => { + return compilation.getAssetPath( + compilation.outputOptions.publicPath, + options + ); + }, + "MainTemplate.getPublicPath is deprecated (use Compilation.getAssetPath(compilation.outputOptions.publicPath, options) instead)", + "DEP_WEBPACK_MAIN_TEMPLATE_GET_PUBLIC_PATH" + ); + + this.getAssetPath = util.deprecate( + (path, options) => { + return compilation.getAssetPath(path, options); + }, + "MainTemplate.getAssetPath is deprecated (use Compilation.getAssetPath instead)", + "DEP_WEBPACK_MAIN_TEMPLATE_GET_ASSET_PATH" + ); + + this.getAssetPathWithInfo = util.deprecate( + (path, options) => { + return compilation.getAssetPathWithInfo(path, options); + }, + "MainTemplate.getAssetPathWithInfo is deprecated (use Compilation.getAssetPath instead)", + "DEP_WEBPACK_MAIN_TEMPLATE_GET_ASSET_PATH_WITH_INFO" + ); + } +} + +Object.defineProperty(MainTemplate.prototype, "requireFn", { + get: util.deprecate( + () => "__webpack_require__", + 'MainTemplate.requireFn is deprecated (use "__webpack_require__")', + "DEP_WEBPACK_MAIN_TEMPLATE_REQUIRE_FN" + ) +}); + +Object.defineProperty(MainTemplate.prototype, "outputOptions", { + get: util.deprecate( + /** + * @this {MainTemplate} + * @returns {OutputOptions} output options + */ + function () { + return this._outputOptions; + }, + "MainTemplate.outputOptions is deprecated (use Compilation.outputOptions instead)", + "DEP_WEBPACK_MAIN_TEMPLATE_OUTPUT_OPTIONS" + ) +}); + +module.exports = MainTemplate; /***/ }), -/***/ 68214: +/***/ 85887: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; @@ -56592,945 +51009,1138 @@ module.exports = OptionsApply; +const util = __webpack_require__(31669); +const ChunkGraph = __webpack_require__(97860); +const DependenciesBlock = __webpack_require__(21484); +const ModuleGraph = __webpack_require__(20258); +const RuntimeGlobals = __webpack_require__(49404); +const { first } = __webpack_require__(34715); +const { compareChunksById } = __webpack_require__(26296); +const makeSerializable = __webpack_require__(26522); + +/** @typedef {import("webpack-sources").Source} Source */ +/** @typedef {import("../declarations/WebpackOptions").ResolveOptions} ResolveOptions */ +/** @typedef {import("../declarations/WebpackOptions").WebpackOptionsNormalized} WebpackOptions */ +/** @typedef {import("./Chunk")} Chunk */ +/** @typedef {import("./ChunkGroup")} ChunkGroup */ /** @typedef {import("./Compilation")} Compilation */ -/** @typedef {import("./NormalModule")} NormalModule */ +/** @typedef {import("./ConcatenationScope")} ConcatenationScope */ +/** @typedef {import("./Dependency")} Dependency */ +/** @typedef {import("./Dependency").UpdateHashContext} UpdateHashContext */ +/** @typedef {import("./DependencyTemplates")} DependencyTemplates */ +/** @typedef {import("./ExportsInfo").UsageStateType} UsageStateType */ +/** @typedef {import("./FileSystemInfo")} FileSystemInfo */ +/** @typedef {import("./ModuleGraphConnection").ConnectionState} ConnectionState */ +/** @typedef {import("./NormalModuleFactory")} NormalModuleFactory */ +/** @typedef {import("./RequestShortener")} RequestShortener */ +/** @typedef {import("./ResolverFactory").ResolverWithOptions} ResolverWithOptions */ +/** @typedef {import("./RuntimeTemplate")} RuntimeTemplate */ +/** @typedef {import("./WebpackError")} WebpackError */ +/** @typedef {import("./util/Hash")} Hash */ +/** @template T @typedef {import("./util/LazySet")} LazySet */ +/** @template T @typedef {import("./util/SortableSet")} SortableSet */ +/** @typedef {import("./util/fs").InputFileSystem} InputFileSystem */ +/** @typedef {import("./util/runtime").RuntimeSpec} RuntimeSpec */ -/** @typedef {Record} PreparsedAst */ +/** + * @typedef {Object} SourceContext + * @property {DependencyTemplates} dependencyTemplates the dependency templates + * @property {RuntimeTemplate} runtimeTemplate the runtime template + * @property {ModuleGraph} moduleGraph the module graph + * @property {ChunkGraph} chunkGraph the chunk graph + * @property {RuntimeSpec} runtime the runtimes code should be generated for + * @property {string=} type the type of source that should be generated + */ /** - * @typedef {Object} ParserStateBase - * @property {string | Buffer} source - * @property {NormalModule} current - * @property {NormalModule} module + * @typedef {Object} CodeGenerationContext + * @property {DependencyTemplates} dependencyTemplates the dependency templates + * @property {RuntimeTemplate} runtimeTemplate the runtime template + * @property {ModuleGraph} moduleGraph the module graph + * @property {ChunkGraph} chunkGraph the chunk graph + * @property {RuntimeSpec} runtime the runtimes code should be generated for + * @property {ConcatenationScope=} concatenationScope when in concatenated module, information about other concatenated modules + */ + +/** + * @typedef {Object} ConcatenationBailoutReasonContext + * @property {ModuleGraph} moduleGraph the module graph + * @property {ChunkGraph} chunkGraph the chunk graph + */ + +/** + * @typedef {Object} CodeGenerationResult + * @property {Map} sources the resulting sources for all source types + * @property {Map=} data the resulting data for all source types + * @property {ReadonlySet} runtimeRequirements the runtime requirements + * @property {string=} hash a hash of the code generation result (will be automatically calculated from sources and runtimeRequirements if not provided) + */ + +/** + * @typedef {Object} LibIdentOptions + * @property {string} context absolute context path to which lib ident is relative to + * @property {Object=} associatedObjectForCache object for caching + */ + +/** + * @typedef {Object} KnownBuildMeta + * @property {string=} moduleArgument + * @property {string=} exportsArgument + * @property {boolean=} strict + * @property {string=} moduleConcatenationBailout + * @property {("default" | "namespace" | "flagged" | "dynamic")=} exportsType + * @property {(false | "redirect" | "redirect-warn")=} defaultObject + * @property {boolean=} strictHarmonyModule + * @property {boolean=} async + * @property {boolean=} sideEffectFree + */ + +/** + * @typedef {Object} NeedBuildContext * @property {Compilation} compilation - * @property {{[k: string]: any}} options + * @property {FileSystemInfo} fileSystemInfo + * @property {Map>} valueCacheVersions */ -/** @typedef {Record & ParserStateBase} ParserState */ +/** @typedef {KnownBuildMeta & Record} BuildMeta */ -class Parser { - /* istanbul ignore next */ - /** - * @abstract - * @param {string | Buffer | PreparsedAst} source the source to parse - * @param {ParserState} state the parser state - * @returns {ParserState} the parser state - */ - parse(source, state) { - const AbstractMethodError = __webpack_require__(570); - throw new AbstractMethodError(); - } -} +const EMPTY_RESOLVE_OPTIONS = {}; -module.exports = Parser; +let debugId = 1000; +const DEFAULT_TYPES_UNKNOWN = new Set(["unknown"]); +const DEFAULT_TYPES_JS = new Set(["javascript"]); -/***/ }), +const deprecatedNeedRebuild = util.deprecate( + (module, context) => { + return module.needRebuild( + context.fileSystemInfo.getDeprecatedFileTimestamps(), + context.fileSystemInfo.getDeprecatedContextTimestamps() + ); + }, + "Module.needRebuild is deprecated in favor of Module.needBuild", + "DEP_WEBPACK_MODULE_NEED_REBUILD" +); -/***/ 34652: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { +/** @typedef {(requestShortener: RequestShortener) => string} OptimizationBailoutFunction */ -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ +class Module extends DependenciesBlock { + /** + * @param {string} type the module type + * @param {string=} context an optional context + * @param {string=} layer an optional layer in which the module is + */ + constructor(type, context = null, layer = null) { + super(); + /** @type {string} */ + this.type = type; + /** @type {string | null} */ + this.context = context; + /** @type {string | null} */ + this.layer = layer; + /** @type {boolean} */ + this.needId = true; + // Unique Id + /** @type {number} */ + this.debugId = debugId++; -const PrefetchDependency = __webpack_require__(39986); + // Info from Factory + /** @type {ResolveOptions} */ + this.resolveOptions = EMPTY_RESOLVE_OPTIONS; + /** @type {object | undefined} */ + this.factoryMeta = undefined; + // TODO refactor this -> options object filled from Factory + // TODO webpack 6: use an enum + /** @type {boolean} */ + this.useSourceMap = false; + /** @type {boolean} */ + this.useSimpleSourceMap = false; -/** @typedef {import("./Compiler")} Compiler */ + // Info from Build + /** @type {WebpackError[] | undefined} */ + this._warnings = undefined; + /** @type {WebpackError[] | undefined} */ + this._errors = undefined; + /** @type {BuildMeta} */ + this.buildMeta = undefined; + /** @type {Record} */ + this.buildInfo = undefined; + /** @type {Dependency[] | undefined} */ + this.presentationalDependencies = undefined; + } -class PrefetchPlugin { - constructor(context, request) { - if (request) { - this.context = context; - this.request = request; - } else { - this.context = null; - this.request = context; + // TODO remove in webpack 6 + // BACKWARD-COMPAT START + get id() { + return ChunkGraph.getChunkGraphForModule( + this, + "Module.id", + "DEP_WEBPACK_MODULE_ID" + ).getModuleId(this); + } + + set id(value) { + if (value === "") { + this.needId = false; + return; } + ChunkGraph.getChunkGraphForModule( + this, + "Module.id", + "DEP_WEBPACK_MODULE_ID" + ).setModuleId(this, value); } /** - * Apply the plugin - * @param {Compiler} compiler the compiler instance - * @returns {void} + * @returns {string} the hash of the module */ - apply(compiler) { - compiler.hooks.compilation.tap( - "PrefetchPlugin", - (compilation, { normalModuleFactory }) => { - compilation.dependencyFactories.set( - PrefetchDependency, - normalModuleFactory - ); - } - ); - compiler.hooks.make.tapAsync("PrefetchPlugin", (compilation, callback) => { - compilation.addModuleChain( - this.context || compiler.context, - new PrefetchDependency(this.request), - err => { - callback(err); - } - ); - }); + get hash() { + return ChunkGraph.getChunkGraphForModule( + this, + "Module.hash", + "DEP_WEBPACK_MODULE_HASH" + ).getModuleHash(this, undefined); } -} -module.exports = PrefetchPlugin; + /** + * @returns {string} the shortened hash of the module + */ + get renderedHash() { + return ChunkGraph.getChunkGraphForModule( + this, + "Module.renderedHash", + "DEP_WEBPACK_MODULE_RENDERED_HASH" + ).getRenderedModuleHash(this, undefined); + } + + get profile() { + return ModuleGraph.getModuleGraphForModule( + this, + "Module.profile", + "DEP_WEBPACK_MODULE_PROFILE" + ).getProfile(this); + } + set profile(value) { + ModuleGraph.getModuleGraphForModule( + this, + "Module.profile", + "DEP_WEBPACK_MODULE_PROFILE" + ).setProfile(this, value); + } -/***/ }), + get index() { + return ModuleGraph.getModuleGraphForModule( + this, + "Module.index", + "DEP_WEBPACK_MODULE_INDEX" + ).getPreOrderIndex(this); + } -/***/ 41306: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + set index(value) { + ModuleGraph.getModuleGraphForModule( + this, + "Module.index", + "DEP_WEBPACK_MODULE_INDEX" + ).setPreOrderIndex(this, value); + } -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ + get index2() { + return ModuleGraph.getModuleGraphForModule( + this, + "Module.index2", + "DEP_WEBPACK_MODULE_INDEX2" + ).getPostOrderIndex(this); + } + set index2(value) { + ModuleGraph.getModuleGraphForModule( + this, + "Module.index2", + "DEP_WEBPACK_MODULE_INDEX2" + ).setPostOrderIndex(this, value); + } + get depth() { + return ModuleGraph.getModuleGraphForModule( + this, + "Module.depth", + "DEP_WEBPACK_MODULE_DEPTH" + ).getDepth(this); + } -const Compiler = __webpack_require__(11777); -const MultiCompiler = __webpack_require__(73663); -const NormalModule = __webpack_require__(11026); -const createSchemaValidation = __webpack_require__(77695); -const { contextify } = __webpack_require__(96236); + set depth(value) { + ModuleGraph.getModuleGraphForModule( + this, + "Module.depth", + "DEP_WEBPACK_MODULE_DEPTH" + ).setDepth(this, value); + } -/** @typedef {import("../declarations/plugins/ProgressPlugin").HandlerFunction} HandlerFunction */ -/** @typedef {import("../declarations/plugins/ProgressPlugin").ProgressPluginArgument} ProgressPluginArgument */ -/** @typedef {import("../declarations/plugins/ProgressPlugin").ProgressPluginOptions} ProgressPluginOptions */ + get issuer() { + return ModuleGraph.getModuleGraphForModule( + this, + "Module.issuer", + "DEP_WEBPACK_MODULE_ISSUER" + ).getIssuer(this); + } -const validate = createSchemaValidation( - __webpack_require__(67916), - () => __webpack_require__(98777), - { - name: "Progress Plugin", - baseDataPath: "options" + set issuer(value) { + ModuleGraph.getModuleGraphForModule( + this, + "Module.issuer", + "DEP_WEBPACK_MODULE_ISSUER" + ).setIssuer(this, value); } -); -const median3 = (a, b, c) => { - return a + b + c - Math.max(a, b, c) - Math.min(a, b, c); -}; -const createDefaultHandler = (profile, logger) => { - /** @type {{ value: string, time: number }[]} */ - const lastStateInfo = []; + get usedExports() { + return ModuleGraph.getModuleGraphForModule( + this, + "Module.usedExports", + "DEP_WEBPACK_MODULE_USED_EXPORTS" + ).getUsedExports(this, undefined); + } - const defaultHandler = (percentage, msg, ...args) => { - if (profile) { - if (percentage === 0) { - lastStateInfo.length = 0; - } - const fullState = [msg, ...args]; - const state = fullState.map(s => s.replace(/\d+\/\d+ /g, "")); - const now = Date.now(); - const len = Math.max(state.length, lastStateInfo.length); - for (let i = len; i >= 0; i--) { - const stateItem = i < state.length ? state[i] : undefined; - const lastStateItem = - i < lastStateInfo.length ? lastStateInfo[i] : undefined; - if (lastStateItem) { - if (stateItem !== lastStateItem.value) { - const diff = now - lastStateItem.time; - if (lastStateItem.value) { - let reportState = lastStateItem.value; - if (i > 0) { - reportState = lastStateInfo[i - 1].value + " > " + reportState; - } - const stateMsg = `${" | ".repeat(i)}${diff} ms ${reportState}`; - const d = diff; - // This depends on timing so we ignore it for coverage - /* istanbul ignore next */ - { - if (d > 10000) { - logger.error(stateMsg); - } else if (d > 1000) { - logger.warn(stateMsg); - } else if (d > 10) { - logger.info(stateMsg); - } else if (d > 5) { - logger.log(stateMsg); - } else { - logger.debug(stateMsg); - } - } - } - if (stateItem === undefined) { - lastStateInfo.length = i; - } else { - lastStateItem.value = stateItem; - lastStateItem.time = now; - lastStateInfo.length = i + 1; - } - } - } else { - lastStateInfo[i] = { - value: stateItem, - time: now - }; - } - } - } - logger.status(`${Math.floor(percentage * 100)}%`, msg, ...args); - if (percentage === 1 || (!msg && args.length === 0)) logger.status(); - }; + /** + * @deprecated + * @returns {(string | OptimizationBailoutFunction)[]} list + */ + get optimizationBailout() { + return ModuleGraph.getModuleGraphForModule( + this, + "Module.optimizationBailout", + "DEP_WEBPACK_MODULE_OPTIMIZATION_BAILOUT" + ).getOptimizationBailout(this); + } - return defaultHandler; -}; + get optional() { + return this.isOptional( + ModuleGraph.getModuleGraphForModule( + this, + "Module.optional", + "DEP_WEBPACK_MODULE_OPTIONAL" + ) + ); + } -/** - * @callback ReportProgress - * @param {number} p - * @param {...string[]} [args] - * @returns {void} - */ + addChunk(chunk) { + const chunkGraph = ChunkGraph.getChunkGraphForModule( + this, + "Module.addChunk", + "DEP_WEBPACK_MODULE_ADD_CHUNK" + ); + if (chunkGraph.isModuleInChunk(this, chunk)) return false; + chunkGraph.connectChunkAndModule(chunk, this); + return true; + } -/** @type {WeakMap} */ -const progressReporters = new WeakMap(); + removeChunk(chunk) { + return ChunkGraph.getChunkGraphForModule( + this, + "Module.removeChunk", + "DEP_WEBPACK_MODULE_REMOVE_CHUNK" + ).disconnectChunkAndModule(chunk, this); + } -class ProgressPlugin { - /** - * @param {Compiler} compiler the current compiler - * @returns {ReportProgress} a progress reporter, if any - */ - static getReporter(compiler) { - return progressReporters.get(compiler); + isInChunk(chunk) { + return ChunkGraph.getChunkGraphForModule( + this, + "Module.isInChunk", + "DEP_WEBPACK_MODULE_IS_IN_CHUNK" + ).isModuleInChunk(this, chunk); } - /** - * @param {ProgressPluginArgument} options options - */ - constructor(options = {}) { - if (typeof options === "function") { - options = { - handler: options - }; - } + isEntryModule() { + return ChunkGraph.getChunkGraphForModule( + this, + "Module.isEntryModule", + "DEP_WEBPACK_MODULE_IS_ENTRY_MODULE" + ).isEntryModule(this); + } - validate(options); - options = { ...ProgressPlugin.defaultOptions, ...options }; + getChunks() { + return ChunkGraph.getChunkGraphForModule( + this, + "Module.getChunks", + "DEP_WEBPACK_MODULE_GET_CHUNKS" + ).getModuleChunks(this); + } + + getNumberOfChunks() { + return ChunkGraph.getChunkGraphForModule( + this, + "Module.getNumberOfChunks", + "DEP_WEBPACK_MODULE_GET_NUMBER_OF_CHUNKS" + ).getNumberOfModuleChunks(this); + } - this.profile = options.profile; - this.handler = options.handler; - this.modulesCount = options.modulesCount; - this.dependenciesCount = options.dependenciesCount; - this.showEntries = options.entries; - this.showModules = options.modules; - this.showDependencies = options.dependencies; - this.showActiveModules = options.activeModules; - this.percentBy = options.percentBy; + get chunksIterable() { + return ChunkGraph.getChunkGraphForModule( + this, + "Module.chunksIterable", + "DEP_WEBPACK_MODULE_CHUNKS_ITERABLE" + ).getOrderedModuleChunksIterable(this, compareChunksById); } /** - * @param {Compiler | MultiCompiler} compiler webpack compiler - * @returns {void} + * @param {string} exportName a name of an export + * @returns {boolean | null} true, if the export is provided why the module. + * null, if it's unknown. + * false, if it's not provided. */ - apply(compiler) { - const handler = - this.handler || - createDefaultHandler( - this.profile, - compiler.getInfrastructureLogger("webpack.Progress") - ); - if (compiler instanceof MultiCompiler) { - this._applyOnMultiCompiler(compiler, handler); - } else if (compiler instanceof Compiler) { - this._applyOnCompiler(compiler, handler); - } + isProvided(exportName) { + return ModuleGraph.getModuleGraphForModule( + this, + "Module.usedExports", + "DEP_WEBPACK_MODULE_USED_EXPORTS" + ).isExportProvided(this, exportName); } + // BACKWARD-COMPAT END /** - * @param {MultiCompiler} compiler webpack multi-compiler - * @param {HandlerFunction} handler function that executes for every progress step - * @returns {void} + * @deprecated moved to .buildInfo.exportsArgument + * @returns {string} name of the exports argument */ - _applyOnMultiCompiler(compiler, handler) { - const states = compiler.compilers.map( - () => /** @type {[number, ...string[]]} */ ([0]) - ); - compiler.compilers.forEach((compiler, idx) => { - new ProgressPlugin((p, msg, ...args) => { - states[idx] = [p, msg, ...args]; - let sum = 0; - for (const [p] of states) sum += p; - handler(sum / states.length, `[${idx}] ${msg}`, ...args); - }).apply(compiler); - }); + get exportsArgument() { + return (this.buildInfo && this.buildInfo.exportsArgument) || "exports"; } /** - * @param {Compiler} compiler webpack compiler - * @param {HandlerFunction} handler function that executes for every progress step - * @returns {void} + * @deprecated moved to .buildInfo.moduleArgument + * @returns {string} name of the module argument */ - _applyOnCompiler(compiler, handler) { - const showEntries = this.showEntries; - const showModules = this.showModules; - const showDependencies = this.showDependencies; - const showActiveModules = this.showActiveModules; - let lastActiveModule = ""; - let currentLoader = ""; - let lastModulesCount = 0; - let lastDependenciesCount = 0; - let lastEntriesCount = 0; - let modulesCount = 0; - let dependenciesCount = 0; - let entriesCount = 1; - let doneModules = 0; - let doneDependencies = 0; - let doneEntries = 0; - const activeModules = new Set(); - let lastUpdate = 0; - - const updateThrottled = () => { - if (lastUpdate + 500 < Date.now()) update(); - }; - - const update = () => { - /** @type {string[]} */ - const items = []; - const percentByModules = - doneModules / - Math.max(lastModulesCount || this.modulesCount || 1, modulesCount); - const percentByEntries = - doneEntries / - Math.max(lastEntriesCount || this.dependenciesCount || 1, entriesCount); - const percentByDependencies = - doneDependencies / - Math.max(lastDependenciesCount || 1, dependenciesCount); - let percentageFactor; - - switch (this.percentBy) { - case "entries": - percentageFactor = percentByEntries; - break; - case "dependencies": - percentageFactor = percentByDependencies; - break; - case "modules": - percentageFactor = percentByModules; - break; - default: - percentageFactor = median3( - percentByModules, - percentByEntries, - percentByDependencies - ); - } - - const percentage = 0.1 + percentageFactor * 0.55; - - if (currentLoader) { - items.push( - `import loader ${contextify( - compiler.context, - currentLoader, - compiler.root - )}` - ); - } else { - const statItems = []; - if (showEntries) { - statItems.push(`${doneEntries}/${entriesCount} entries`); - } - if (showDependencies) { - statItems.push( - `${doneDependencies}/${dependenciesCount} dependencies` - ); - } - if (showModules) { - statItems.push(`${doneModules}/${modulesCount} modules`); - } - if (showActiveModules) { - statItems.push(`${activeModules.size} active`); - } - if (statItems.length > 0) { - items.push(statItems.join(" ")); - } - if (showActiveModules) { - items.push(lastActiveModule); - } - } - handler(percentage, "building", ...items); - lastUpdate = Date.now(); - }; - - const factorizeAdd = () => { - dependenciesCount++; - if (dependenciesCount < 50 || dependenciesCount % 100 === 0) - updateThrottled(); - }; - - const factorizeDone = () => { - doneDependencies++; - if (doneDependencies < 50 || doneDependencies % 100 === 0) - updateThrottled(); - }; - - const moduleAdd = () => { - modulesCount++; - if (modulesCount < 50 || modulesCount % 100 === 0) updateThrottled(); - }; - - // only used when showActiveModules is set - const moduleBuild = module => { - const ident = module.identifier(); - if (ident) { - activeModules.add(ident); - lastActiveModule = ident; - update(); - } - }; - - const entryAdd = (entry, options) => { - entriesCount++; - if (entriesCount < 5 || entriesCount % 10 === 0) updateThrottled(); - }; + get moduleArgument() { + return (this.buildInfo && this.buildInfo.moduleArgument) || "module"; + } - const moduleDone = module => { - doneModules++; - if (showActiveModules) { - const ident = module.identifier(); - if (ident) { - activeModules.delete(ident); - if (lastActiveModule === ident) { - lastActiveModule = ""; - for (const m of activeModules) { - lastActiveModule = m; - } - update(); - return; - } + /** + * @param {ModuleGraph} moduleGraph the module graph + * @param {boolean} strict the importing module is strict + * @returns {"namespace" | "default-only" | "default-with-named" | "dynamic"} export type + * "namespace": Exports is already a namespace object. namespace = exports. + * "dynamic": Check at runtime if __esModule is set. When set: namespace = { ...exports, default: exports }. When not set: namespace = { default: exports }. + * "default-only": Provide a namespace object with only default export. namespace = { default: exports } + * "default-with-named": Provide a namespace object with named and default export. namespace = { ...exports, default: exports } + */ + getExportsType(moduleGraph, strict) { + switch (this.buildMeta && this.buildMeta.exportsType) { + case "flagged": + return strict ? "default-with-named" : "namespace"; + case "namespace": + return "namespace"; + case "default": + switch (this.buildMeta.defaultObject) { + case "redirect": + return "default-with-named"; + case "redirect-warn": + return strict ? "default-only" : "default-with-named"; + default: + return "default-only"; } - } - if (doneModules < 50 || doneModules % 100 === 0) updateThrottled(); - }; - - const entryDone = (entry, options) => { - doneEntries++; - update(); - }; - - const cache = compiler - .getCache("ProgressPlugin") - .getItemCache("counts", null); - - let cacheGetPromise; - - compiler.hooks.beforeCompile.tap("ProgressPlugin", () => { - if (!cacheGetPromise) { - cacheGetPromise = cache.getPromise().then( - data => { - if (data) { - lastModulesCount = lastModulesCount || data.modulesCount; - lastDependenciesCount = - lastDependenciesCount || data.dependenciesCount; - } - return data; - }, - err => { - // Ignore error + case "dynamic": { + if (strict) return "default-with-named"; + // Try to figure out value of __esModule by following reexports + const handleDefault = () => { + switch (this.buildMeta.defaultObject) { + case "redirect": + case "redirect-warn": + return "default-with-named"; + default: + return "default-only"; } + }; + const exportInfo = moduleGraph.getReadOnlyExportInfo( + this, + "__esModule" ); - } - }); - - compiler.hooks.afterCompile.tapPromise("ProgressPlugin", compilation => { - if (compilation.compiler.isChild()) return Promise.resolve(); - return cacheGetPromise.then(async oldData => { + if (exportInfo.provided === false) { + return handleDefault(); + } + const target = exportInfo.getTarget(moduleGraph); if ( - !oldData || - oldData.modulesCount !== modulesCount || - oldData.dependenciesCount !== dependenciesCount + !target || + !target.export || + target.export.length !== 1 || + target.export[0] !== "__esModule" ) { - await cache.storePromise({ modulesCount, dependenciesCount }); + return "dynamic"; } - }); - }); - - compiler.hooks.compilation.tap("ProgressPlugin", compilation => { - if (compilation.compiler.isChild()) return; - lastModulesCount = modulesCount; - lastEntriesCount = entriesCount; - lastDependenciesCount = dependenciesCount; - modulesCount = dependenciesCount = entriesCount = 0; - doneModules = doneDependencies = doneEntries = 0; - - compilation.factorizeQueue.hooks.added.tap( - "ProgressPlugin", - factorizeAdd - ); - compilation.factorizeQueue.hooks.result.tap( - "ProgressPlugin", - factorizeDone - ); - - compilation.addModuleQueue.hooks.added.tap("ProgressPlugin", moduleAdd); - compilation.processDependenciesQueue.hooks.result.tap( - "ProgressPlugin", - moduleDone - ); - - if (showActiveModules) { - compilation.hooks.buildModule.tap("ProgressPlugin", moduleBuild); - } - - compilation.hooks.addEntry.tap("ProgressPlugin", entryAdd); - compilation.hooks.failedEntry.tap("ProgressPlugin", entryDone); - compilation.hooks.succeedEntry.tap("ProgressPlugin", entryDone); - - // avoid dynamic require if bundled with webpack - // @ts-expect-error - if (false) {} - - const hooks = { - finishModules: "finish module graph", - seal: "plugins", - optimizeDependencies: "dependencies optimization", - afterOptimizeDependencies: "after dependencies optimization", - beforeChunks: "chunk graph", - afterChunks: "after chunk graph", - optimize: "optimizing", - optimizeModules: "module optimization", - afterOptimizeModules: "after module optimization", - optimizeChunks: "chunk optimization", - afterOptimizeChunks: "after chunk optimization", - optimizeTree: "module and chunk tree optimization", - afterOptimizeTree: "after module and chunk tree optimization", - optimizeChunkModules: "chunk modules optimization", - afterOptimizeChunkModules: "after chunk modules optimization", - reviveModules: "module reviving", - beforeModuleIds: "before module ids", - moduleIds: "module ids", - optimizeModuleIds: "module id optimization", - afterOptimizeModuleIds: "module id optimization", - reviveChunks: "chunk reviving", - beforeChunkIds: "before chunk ids", - chunkIds: "chunk ids", - optimizeChunkIds: "chunk id optimization", - afterOptimizeChunkIds: "after chunk id optimization", - recordModules: "record modules", - recordChunks: "record chunks", - beforeModuleHash: "module hashing", - beforeCodeGeneration: "code generation", - beforeRuntimeRequirements: "runtime requirements", - beforeHash: "hashing", - afterHash: "after hashing", - recordHash: "record hash", - beforeModuleAssets: "module assets processing", - beforeChunkAssets: "chunk assets processing", - processAssets: "asset processing", - afterProcessAssets: "after asset optimization", - record: "recording", - afterSeal: "after seal" - }; - const numberOfHooks = Object.keys(hooks).length; - Object.keys(hooks).forEach((name, idx) => { - const title = hooks[name]; - const percentage = (idx / numberOfHooks) * 0.25 + 0.7; - compilation.hooks[name].intercept({ - name: "ProgressPlugin", - call() { - handler(percentage, "sealing", title); - }, - done() { - progressReporters.set(compiler, undefined); - handler(percentage, "sealing", title); - }, - result() { - handler(percentage, "sealing", title); - }, - error() { - handler(percentage, "sealing", title); - }, - tap(tap) { - // p is percentage from 0 to 1 - // args is any number of messages in a hierarchical matter - progressReporters.set(compilation.compiler, (p, ...args) => { - handler(percentage, "sealing", title, tap.name, ...args); - }); - handler(percentage, "sealing", title, tap.name); - } - }); - }); - }); - compiler.hooks.make.intercept({ - name: "ProgressPlugin", - call() { - handler(0.1, "building"); - }, - done() { - handler(0.65, "building"); - } - }); - const interceptHook = (hook, progress, category, name) => { - hook.intercept({ - name: "ProgressPlugin", - call() { - handler(progress, category, name); - }, - done() { - progressReporters.set(compiler, undefined); - handler(progress, category, name); - }, - result() { - handler(progress, category, name); - }, - error() { - handler(progress, category, name); - }, - tap(tap) { - progressReporters.set(compiler, (p, ...args) => { - handler(progress, category, name, tap.name, ...args); - }); - handler(progress, category, name, tap.name); + switch ( + target.module.buildMeta && + target.module.buildMeta.exportsType + ) { + case "flagged": + case "namespace": + return "namespace"; + case "default": + return handleDefault(); + default: + return "dynamic"; } - }); - }; - compiler.cache.hooks.endIdle.intercept({ - name: "ProgressPlugin", - call() { - handler(0, ""); - } - }); - interceptHook(compiler.cache.hooks.endIdle, 0.01, "cache", "end idle"); - compiler.hooks.initialize.intercept({ - name: "ProgressPlugin", - call() { - handler(0, ""); - } - }); - interceptHook(compiler.hooks.initialize, 0.01, "setup", "initialize"); - interceptHook(compiler.hooks.beforeRun, 0.02, "setup", "before run"); - interceptHook(compiler.hooks.run, 0.03, "setup", "run"); - interceptHook(compiler.hooks.watchRun, 0.03, "setup", "watch run"); - interceptHook( - compiler.hooks.normalModuleFactory, - 0.04, - "setup", - "normal module factory" - ); - interceptHook( - compiler.hooks.contextModuleFactory, - 0.05, - "setup", - "context module factory" - ); - interceptHook( - compiler.hooks.beforeCompile, - 0.06, - "setup", - "before compile" - ); - interceptHook(compiler.hooks.compile, 0.07, "setup", "compile"); - interceptHook(compiler.hooks.thisCompilation, 0.08, "setup", "compilation"); - interceptHook(compiler.hooks.compilation, 0.09, "setup", "compilation"); - interceptHook(compiler.hooks.finishMake, 0.69, "building", "finish"); - interceptHook(compiler.hooks.emit, 0.95, "emitting", "emit"); - interceptHook(compiler.hooks.afterEmit, 0.98, "emitting", "after emit"); - interceptHook(compiler.hooks.done, 0.99, "done", "plugins"); - compiler.hooks.done.intercept({ - name: "ProgressPlugin", - done() { - handler(0.99, ""); - } - }); - interceptHook( - compiler.cache.hooks.storeBuildDependencies, - 0.99, - "cache", - "store build dependencies" - ); - interceptHook(compiler.cache.hooks.shutdown, 0.99, "cache", "shutdown"); - interceptHook(compiler.cache.hooks.beginIdle, 0.99, "cache", "begin idle"); - interceptHook( - compiler.hooks.watchClose, - 0.99, - "end", - "closing watch compilation" - ); - compiler.cache.hooks.beginIdle.intercept({ - name: "ProgressPlugin", - done() { - handler(1, ""); - } - }); - compiler.cache.hooks.shutdown.intercept({ - name: "ProgressPlugin", - done() { - handler(1, ""); } - }); + default: + return strict ? "default-with-named" : "dynamic"; + } } -} -ProgressPlugin.defaultOptions = { - profile: false, - modulesCount: 5000, - dependenciesCount: 10000, - modules: true, - dependencies: true, - activeModules: false, - entries: true -}; + /** + * @param {Dependency} presentationalDependency dependency being tied to module. + * This is a Dependency without edge in the module graph. It's only for presentation. + * @returns {void} + */ + addPresentationalDependency(presentationalDependency) { + if (this.presentationalDependencies === undefined) { + this.presentationalDependencies = []; + } + this.presentationalDependencies.push(presentationalDependency); + } -module.exports = ProgressPlugin; + /** + * Removes all dependencies and blocks + * @returns {void} + */ + clearDependenciesAndBlocks() { + if (this.presentationalDependencies !== undefined) { + this.presentationalDependencies.length = 0; + } + super.clearDependenciesAndBlocks(); + } + /** + * @param {WebpackError} warning the warning + * @returns {void} + */ + addWarning(warning) { + if (this._warnings === undefined) { + this._warnings = []; + } + this._warnings.push(warning); + } -/***/ }), + /** + * @returns {Iterable | undefined} list of warnings if any + */ + getWarnings() { + return this._warnings; + } -/***/ 18067: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + /** + * @returns {number} number of warnings + */ + getNumberOfWarnings() { + return this._warnings !== undefined ? this._warnings.length : 0; + } -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ + /** + * @param {WebpackError} error the error + * @returns {void} + */ + addError(error) { + if (this._errors === undefined) { + this._errors = []; + } + this._errors.push(error); + } + /** + * @returns {Iterable | undefined} list of errors if any + */ + getErrors() { + return this._errors; + } + /** + * @returns {number} number of errors + */ + getNumberOfErrors() { + return this._errors !== undefined ? this._errors.length : 0; + } -const ConstDependency = __webpack_require__(60864); -const ProvidedDependency = __webpack_require__(88915); -const { approve } = __webpack_require__(28723); + /** + * removes all warnings and errors + * @returns {void} + */ + clearWarningsAndErrors() { + if (this._warnings !== undefined) { + this._warnings.length = 0; + } + if (this._errors !== undefined) { + this._errors.length = 0; + } + } -/** @typedef {import("./Compiler")} Compiler */ + /** + * @param {ModuleGraph} moduleGraph the module graph + * @returns {boolean} true, if the module is optional + */ + isOptional(moduleGraph) { + let hasConnections = false; + for (const r of moduleGraph.getIncomingConnections(this)) { + if ( + !r.dependency || + !r.dependency.optional || + !r.isTargetActive(undefined) + ) { + return false; + } + hasConnections = true; + } + return hasConnections; + } -class ProvidePlugin { /** - * @param {Record} definitions the provided identifiers + * @param {ChunkGraph} chunkGraph the chunk graph + * @param {Chunk} chunk a chunk + * @param {Chunk=} ignoreChunk chunk to be ignored + * @returns {boolean} true, if the module is accessible from "chunk" when ignoring "ignoreChunk" */ - constructor(definitions) { - this.definitions = definitions; + isAccessibleInChunk(chunkGraph, chunk, ignoreChunk) { + // Check if module is accessible in ALL chunk groups + for (const chunkGroup of chunk.groupsIterable) { + if (!this.isAccessibleInChunkGroup(chunkGraph, chunkGroup)) return false; + } + return true; } /** - * Apply the plugin - * @param {Compiler} compiler the compiler instance - * @returns {void} + * @param {ChunkGraph} chunkGraph the chunk graph + * @param {ChunkGroup} chunkGroup a chunk group + * @param {Chunk=} ignoreChunk chunk to be ignored + * @returns {boolean} true, if the module is accessible from "chunkGroup" when ignoring "ignoreChunk" */ - apply(compiler) { - const definitions = this.definitions; - compiler.hooks.compilation.tap( - "ProvidePlugin", - (compilation, { normalModuleFactory }) => { - compilation.dependencyTemplates.set( - ConstDependency, - new ConstDependency.Template() - ); - compilation.dependencyFactories.set( - ProvidedDependency, - normalModuleFactory - ); - compilation.dependencyTemplates.set( - ProvidedDependency, - new ProvidedDependency.Template() - ); - const handler = (parser, parserOptions) => { - Object.keys(definitions).forEach(name => { - const request = [].concat(definitions[name]); - const splittedName = name.split("."); - if (splittedName.length > 0) { - splittedName.slice(1).forEach((_, i) => { - const name = splittedName.slice(0, i + 1).join("."); - parser.hooks.canRename.for(name).tap("ProvidePlugin", approve); - }); - } + isAccessibleInChunkGroup(chunkGraph, chunkGroup, ignoreChunk) { + const queue = new Set([chunkGroup]); - parser.hooks.expression.for(name).tap("ProvidePlugin", expr => { - const nameIdentifier = name.includes(".") - ? `__webpack_provided_${name.replace(/\./g, "_dot_")}` - : name; - const dep = new ProvidedDependency( - request[0], - nameIdentifier, - request.slice(1), - expr.range - ); - dep.loc = expr.loc; - parser.state.module.addDependency(dep); - return true; - }); + // Check if module is accessible from all items of the queue + queueFor: for (const cg of queue) { + // 1. If module is in one of the chunks of the group we can continue checking the next items + // because it's accessible. + for (const chunk of cg.chunks) { + if (chunk !== ignoreChunk && chunkGraph.isModuleInChunk(this, chunk)) + continue queueFor; + } + // 2. If the chunk group is initial, we can break here because it's not accessible. + if (chunkGroup.isInitial()) return false; + // 3. Enqueue all parents because it must be accessible from ALL parents + for (const parent of chunkGroup.parentsIterable) queue.add(parent); + } + // When we processed through the whole list and we didn't bailout, the module is accessible + return true; + } - parser.hooks.call.for(name).tap("ProvidePlugin", expr => { - const nameIdentifier = name.includes(".") - ? `__webpack_provided_${name.replace(/\./g, "_dot_")}` - : name; - const dep = new ProvidedDependency( - request[0], - nameIdentifier, - request.slice(1), - expr.callee.range - ); - dep.loc = expr.callee.loc; - parser.state.module.addDependency(dep); - parser.walkExpressions(expr.arguments); - return true; - }); - }); - }; - normalModuleFactory.hooks.parser - .for("javascript/auto") - .tap("ProvidePlugin", handler); - normalModuleFactory.hooks.parser - .for("javascript/dynamic") - .tap("ProvidePlugin", handler); - normalModuleFactory.hooks.parser - .for("javascript/esm") - .tap("ProvidePlugin", handler); + /** + * @param {Chunk} chunk a chunk + * @param {ModuleGraph} moduleGraph the module graph + * @param {ChunkGraph} chunkGraph the chunk graph + * @returns {boolean} true, if the module has any reason why "chunk" should be included + */ + hasReasonForChunk(chunk, moduleGraph, chunkGraph) { + // check for each reason if we need the chunk + for (const [ + fromModule, + connections + ] of moduleGraph.getIncomingConnectionsByOriginModule(this)) { + if (!connections.some(c => c.isTargetActive(chunk.runtime))) continue; + for (const originChunk of chunkGraph.getModuleChunksIterable( + fromModule + )) { + // return true if module this is not reachable from originChunk when ignoring chunk + if (!this.isAccessibleInChunk(chunkGraph, originChunk, chunk)) + return true; } + } + return false; + } + + /** + * @param {ModuleGraph} moduleGraph the module graph + * @param {RuntimeSpec} runtime the runtime + * @returns {boolean} true if at least one other module depends on this module + */ + hasReasons(moduleGraph, runtime) { + for (const c of moduleGraph.getIncomingConnections(this)) { + if (c.isTargetActive(runtime)) return true; + } + return false; + } + + /** + * @returns {string} for debugging + */ + toString() { + return `Module[${this.debugId}: ${this.identifier()}]`; + } + + /** + * @param {NeedBuildContext} context context info + * @param {function(WebpackError=, boolean=): void} callback callback function, returns true, if the module needs a rebuild + * @returns {void} + */ + needBuild(context, callback) { + callback( + null, + !this.buildMeta || + this.needRebuild === Module.prototype.needRebuild || + deprecatedNeedRebuild(this, context) ); } -} -module.exports = ProvidePlugin; + /** + * @deprecated Use needBuild instead + * @param {Map} fileTimestamps timestamps of files + * @param {Map} contextTimestamps timestamps of directories + * @returns {boolean} true, if the module needs a rebuild + */ + needRebuild(fileTimestamps, contextTimestamps) { + return true; + } + /** + * @param {Hash} hash the hash used to track dependencies + * @param {UpdateHashContext} context context + * @returns {void} + */ + updateHash( + hash, + context = { + chunkGraph: ChunkGraph.getChunkGraphForModule( + this, + "Module.updateHash", + "DEP_WEBPACK_MODULE_UPDATE_HASH" + ), + runtime: undefined + } + ) { + const { chunkGraph, runtime } = context; + hash.update(chunkGraph.getModuleGraphHash(this, runtime)); + if (this.presentationalDependencies !== undefined) { + for (const dep of this.presentationalDependencies) { + dep.updateHash(hash, context); + } + } + super.updateHash(hash, context); + } -/***/ }), + /** + * @returns {void} + */ + invalidateBuild() { + // should be overridden to support this feature + } -/***/ 82329: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + /* istanbul ignore next */ + /** + * @abstract + * @returns {string} a unique identifier of the module + */ + identifier() { + const AbstractMethodError = __webpack_require__(570); + throw new AbstractMethodError(); + } -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ + /* istanbul ignore next */ + /** + * @abstract + * @param {RequestShortener} requestShortener the request shortener + * @returns {string} a user readable identifier of the module + */ + readableIdentifier(requestShortener) { + const AbstractMethodError = __webpack_require__(570); + throw new AbstractMethodError(); + } + /* istanbul ignore next */ + /** + * @abstract + * @param {WebpackOptions} options webpack options + * @param {Compilation} compilation the compilation + * @param {ResolverWithOptions} resolver the resolver + * @param {InputFileSystem} fs the file system + * @param {function(WebpackError=): void} callback callback function + * @returns {void} + */ + build(options, compilation, resolver, fs, callback) { + const AbstractMethodError = __webpack_require__(570); + throw new AbstractMethodError(); + } + /** + * @abstract + * @returns {Set} types available (do not mutate) + */ + getSourceTypes() { + // Better override this method to return the correct types + if (this.source === Module.prototype.source) { + return DEFAULT_TYPES_UNKNOWN; + } else { + return DEFAULT_TYPES_JS; + } + } -const { OriginalSource, RawSource } = __webpack_require__(96192); -const Module = __webpack_require__(85887); -const makeSerializable = __webpack_require__(26522); + /** + * @abstract + * @deprecated Use codeGeneration() instead + * @param {DependencyTemplates} dependencyTemplates the dependency templates + * @param {RuntimeTemplate} runtimeTemplate the runtime template + * @param {string=} type the type of source that should be generated + * @returns {Source} generated source + */ + source(dependencyTemplates, runtimeTemplate, type = "javascript") { + if (this.codeGeneration === Module.prototype.codeGeneration) { + const AbstractMethodError = __webpack_require__(570); + throw new AbstractMethodError(); + } + const chunkGraph = ChunkGraph.getChunkGraphForModule( + this, + "Module.source() is deprecated. Use Compilation.codeGenerationResults.getSource(module, runtime, type) instead", + "DEP_WEBPACK_MODULE_SOURCE" + ); + /** @type {CodeGenerationContext} */ + const codeGenContext = { + dependencyTemplates, + runtimeTemplate, + moduleGraph: chunkGraph.moduleGraph, + chunkGraph, + runtime: undefined + }; + const sources = this.codeGeneration(codeGenContext).sources; + return type ? sources.get(type) : sources.get(first(this.getSourceTypes())); + } -/** @typedef {import("webpack-sources").Source} Source */ -/** @typedef {import("../declarations/WebpackOptions").WebpackOptionsNormalized} WebpackOptions */ -/** @typedef {import("./ChunkGraph")} ChunkGraph */ -/** @typedef {import("./Compilation")} Compilation */ -/** @typedef {import("./Dependency").UpdateHashContext} UpdateHashContext */ -/** @typedef {import("./DependencyTemplates")} DependencyTemplates */ -/** @typedef {import("./Module").CodeGenerationContext} CodeGenerationContext */ -/** @typedef {import("./Module").CodeGenerationResult} CodeGenerationResult */ -/** @typedef {import("./Module").NeedBuildContext} NeedBuildContext */ -/** @typedef {import("./RequestShortener")} RequestShortener */ -/** @typedef {import("./ResolverFactory").ResolverWithOptions} ResolverWithOptions */ -/** @typedef {import("./RuntimeTemplate")} RuntimeTemplate */ -/** @typedef {import("./WebpackError")} WebpackError */ -/** @typedef {import("./util/Hash")} Hash */ -/** @typedef {import("./util/fs").InputFileSystem} InputFileSystem */ + /* istanbul ignore next */ + /** + * @abstract + * @param {string=} type the source type for which the size should be estimated + * @returns {number} the estimated size of the module (must be non-zero) + */ + size(type) { + const AbstractMethodError = __webpack_require__(570); + throw new AbstractMethodError(); + } -const TYPES = new Set(["javascript"]); + /** + * @param {LibIdentOptions} options options + * @returns {string | null} an identifier for library inclusion + */ + libIdent(options) { + return null; + } -class RawModule extends Module { /** - * @param {string} source source code - * @param {string} identifier unique identifier - * @param {string=} readableIdentifier readable identifier - * @param {ReadonlySet=} runtimeRequirements runtime requirements needed for the source code + * @returns {string | null} absolute path which should be used for condition matching (usually the resource path) */ - constructor(source, identifier, readableIdentifier, runtimeRequirements) { - super("javascript/dynamic", null); - this.sourceStr = source; - this.identifierStr = identifier || this.sourceStr; - this.readableIdentifierStr = readableIdentifier || this.identifierStr; - this.runtimeRequirements = runtimeRequirements || null; + nameForCondition() { + return null; + } + + /** + * @param {ConcatenationBailoutReasonContext} context context + * @returns {string | undefined} reason why this module can't be concatenated, undefined when it can be concatenated + */ + getConcatenationBailoutReason(context) { + return `Module Concatenation is not implemented for ${this.constructor.name}`; + } + + /** + * @param {ModuleGraph} moduleGraph the module graph + * @returns {ConnectionState} how this module should be connected to referencing modules when consumed for side-effects only + */ + getSideEffectsConnectionState(moduleGraph) { + return true; + } + + /** + * @param {CodeGenerationContext} context context for code generation + * @returns {CodeGenerationResult} result + */ + codeGeneration(context) { + // Best override this method + const sources = new Map(); + for (const type of this.getSourceTypes()) { + if (type !== "unknown") { + sources.set( + type, + this.source( + context.dependencyTemplates, + context.runtimeTemplate, + type + ) + ); + } + } + return { + sources, + runtimeRequirements: new Set([ + RuntimeGlobals.module, + RuntimeGlobals.exports, + RuntimeGlobals.require + ]) + }; + } + + /** + * @param {Chunk} chunk the chunk which condition should be checked + * @param {Compilation} compilation the compilation + * @returns {boolean} true, if the chunk is ok for the module + */ + chunkCondition(chunk, compilation) { + return true; + } + + hasChunkCondition() { + return this.chunkCondition !== Module.prototype.chunkCondition; } /** - * @returns {Set} types available (do not mutate) + * Assuming this module is in the cache. Update the (cached) module with + * the fresh module from the factory. Usually updates internal references + * and properties. + * @param {Module} module fresh module + * @returns {void} */ - getSourceTypes() { - return TYPES; + updateCacheModule(module) { + this.type = module.type; + this.layer = module.layer; + this.context = module.context; + this.factoryMeta = module.factoryMeta; + this.resolveOptions = module.resolveOptions; } /** - * @returns {string} a unique identifier of the module + * Module should be unsafe cached. Get data that's needed for that. + * This data will be passed to restoreFromUnsafeCache later. + * @returns {object} cached data */ - identifier() { - return this.identifierStr; + getUnsafeCacheData() { + return { + factoryMeta: this.factoryMeta, + resolveOptions: this.resolveOptions + }; } /** - * @param {string=} type the source type for which the size should be estimated - * @returns {number} the estimated size of the module (must be non-zero) + * restore unsafe cache data + * @param {object} unsafeCacheData data from getUnsafeCacheData + * @param {NormalModuleFactory} normalModuleFactory the normal module factory handling the unsafe caching */ - size(type) { - return Math.max(1, this.sourceStr.length); + _restoreFromUnsafeCache(unsafeCacheData, normalModuleFactory) { + this.factoryMeta = unsafeCacheData.factoryMeta; + this.resolveOptions = unsafeCacheData.resolveOptions; } /** - * @param {RequestShortener} requestShortener the request shortener - * @returns {string} a user readable identifier of the module + * Assuming this module is in the cache. Remove internal references to allow freeing some memory. */ - readableIdentifier(requestShortener) { - return requestShortener.shorten(this.readableIdentifierStr); + cleanupForCache() { + this.factoryMeta = undefined; + this.resolveOptions = undefined; } /** - * @param {NeedBuildContext} context context info - * @param {function(WebpackError=, boolean=): void} callback callback function, returns true, if the module needs a rebuild - * @returns {void} + * @returns {Source | null} the original source for the module before webpack transformation */ - needBuild(context, callback) { - return callback(null, !this.buildMeta); + originalSource() { + return null; } /** - * @param {WebpackOptions} options webpack options - * @param {Compilation} compilation the compilation - * @param {ResolverWithOptions} resolver the resolver - * @param {InputFileSystem} fs the file system - * @param {function(WebpackError=): void} callback callback function - * @returns {void} + * @param {LazySet} fileDependencies set where file dependencies are added to + * @param {LazySet} contextDependencies set where context dependencies are added to + * @param {LazySet} missingDependencies set where missing dependencies are added to + * @param {LazySet} buildDependencies set where build dependencies are added to */ - build(options, compilation, resolver, fs, callback) { - this.buildMeta = {}; - this.buildInfo = { - cacheable: true - }; - callback(); + addCacheDependencies( + fileDependencies, + contextDependencies, + missingDependencies, + buildDependencies + ) {} + + serialize(context) { + const { write } = context; + write(this.type); + write(this.layer); + write(this.context); + write(this.resolveOptions); + write(this.factoryMeta); + write(this.useSourceMap); + write(this.useSimpleSourceMap); + write( + this._warnings !== undefined && this._warnings.length === 0 + ? undefined + : this._warnings + ); + write( + this._errors !== undefined && this._errors.length === 0 + ? undefined + : this._errors + ); + write(this.buildMeta); + write(this.buildInfo); + write(this.presentationalDependencies); + super.serialize(context); + } + + deserialize(context) { + const { read } = context; + this.type = read(); + this.layer = read(); + this.context = read(); + this.resolveOptions = read(); + this.factoryMeta = read(); + this.useSourceMap = read(); + this.useSimpleSourceMap = read(); + this._warnings = read(); + this._errors = read(); + this.buildMeta = read(); + this.buildInfo = read(); + this.presentationalDependencies = read(); + super.deserialize(context); + } +} + +makeSerializable(Module, "webpack/lib/Module"); + +// TODO remove in webpack 6 +Object.defineProperty(Module.prototype, "hasEqualsChunks", { + get() { + throw new Error( + "Module.hasEqualsChunks was renamed (use hasEqualChunks instead)" + ); + } +}); + +// TODO remove in webpack 6 +Object.defineProperty(Module.prototype, "isUsed", { + get() { + throw new Error( + "Module.isUsed was renamed (use getUsedName, isExportUsed or isModuleUsed instead)" + ); + } +}); + +// TODO remove in webpack 6 +Object.defineProperty(Module.prototype, "errors", { + get: util.deprecate( + /** + * @this {Module} + * @returns {WebpackError[]} array + */ + function () { + if (this._errors === undefined) { + this._errors = []; + } + return this._errors; + }, + "Module.errors was removed (use getErrors instead)", + "DEP_WEBPACK_MODULE_ERRORS" + ) +}); + +// TODO remove in webpack 6 +Object.defineProperty(Module.prototype, "warnings", { + get: util.deprecate( + /** + * @this {Module} + * @returns {WebpackError[]} array + */ + function () { + if (this._warnings === undefined) { + this._warnings = []; + } + return this._warnings; + }, + "Module.warnings was removed (use getWarnings instead)", + "DEP_WEBPACK_MODULE_WARNINGS" + ) +}); + +// TODO remove in webpack 6 +Object.defineProperty(Module.prototype, "used", { + get() { + throw new Error( + "Module.used was refactored (use ModuleGraph.getUsedExports instead)" + ); + }, + set(value) { + throw new Error( + "Module.used was refactored (use ModuleGraph.setUsedExports instead)" + ); } +}); + +module.exports = Module; + + +/***/ }), + +/***/ 37991: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ + + +const { cutOffLoaderExecution } = __webpack_require__(22569); +const WebpackError = __webpack_require__(68422); +const makeSerializable = __webpack_require__(26522); + +class ModuleBuildError extends WebpackError { /** - * @param {CodeGenerationContext} context context for code generation - * @returns {CodeGenerationResult} result + * @param {string | Error&any} err error thrown + * @param {{from?: string|null}} info additional info */ - codeGeneration(context) { - const sources = new Map(); - if (this.useSourceMap || this.useSimpleSourceMap) { - sources.set( - "javascript", - new OriginalSource(this.sourceStr, this.identifier()) - ); + constructor(err, { from = null } = {}) { + let message = "Module build failed"; + let details = undefined; + + if (from) { + message += ` (from ${from}):\n`; } else { - sources.set("javascript", new RawSource(this.sourceStr)); + message += ": "; } - return { sources, runtimeRequirements: this.runtimeRequirements }; - } - /** - * @param {Hash} hash the hash used to track dependencies - * @param {UpdateHashContext} context context - * @returns {void} - */ - updateHash(hash, context) { - hash.update(this.sourceStr); - super.updateHash(hash, context); + if (err !== null && typeof err === "object") { + if (typeof err.stack === "string" && err.stack) { + const stack = cutOffLoaderExecution(err.stack); + + if (!err.hideStack) { + message += stack; + } else { + details = stack; + + if (typeof err.message === "string" && err.message) { + message += err.message; + } else { + message += err; + } + } + } else if (typeof err.message === "string" && err.message) { + message += err.message; + } else { + message += String(err); + } + } else { + message += String(err); + } + + super(message); + + this.name = "ModuleBuildError"; + this.details = details; + this.error = err; } serialize(context) { const { write } = context; - write(this.sourceStr); - write(this.identifierStr); - write(this.readableIdentifierStr); - write(this.runtimeRequirements); + write(this.error); super.serialize(context); } @@ -57538,23 +52148,20 @@ class RawModule extends Module { deserialize(context) { const { read } = context; - this.sourceStr = read(); - this.identifierStr = read(); - this.readableIdentifierStr = read(); - this.runtimeRequirements = read(); + this.error = read(); super.deserialize(context); } } -makeSerializable(RawModule, "webpack/lib/RawModule"); +makeSerializable(ModuleBuildError, "webpack/lib/ModuleBuildError"); -module.exports = RawModule; +module.exports = ModuleBuildError; /***/ }), -/***/ 64122: +/***/ 30549: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; @@ -57565,242 +52172,44 @@ module.exports = RawModule; -const { compareNumbers } = __webpack_require__(26296); -const identifierUtils = __webpack_require__(96236); +const WebpackError = __webpack_require__(68422); -/** @typedef {import("./Chunk")} Chunk */ -/** @typedef {import("./Compiler")} Compiler */ +/** @typedef {import("./Dependency").DependencyLocation} DependencyLocation */ /** @typedef {import("./Module")} Module */ -/** - * @typedef {Object} RecordsChunks - * @property {Record=} byName - * @property {Record=} bySource - * @property {number[]=} usedIds - */ - -/** - * @typedef {Object} RecordsModules - * @property {Record=} byIdentifier - * @property {Record=} bySource - * @property {number[]=} usedIds - */ - -/** - * @typedef {Object} Records - * @property {RecordsChunks=} chunks - * @property {RecordsModules=} modules - */ - -class RecordIdsPlugin { - /** - * @param {Object} options Options object - * @param {boolean=} options.portableIds true, when ids need to be portable - */ - constructor(options) { - this.options = options || {}; - } - +class ModuleDependencyError extends WebpackError { /** - * @param {Compiler} compiler the Compiler - * @returns {void} + * Creates an instance of ModuleDependencyError. + * @param {Module} module module tied to dependency + * @param {Error} err error thrown + * @param {DependencyLocation} loc location of dependency */ - apply(compiler) { - const portableIds = this.options.portableIds; - - const makePathsRelative = - identifierUtils.makePathsRelative.bindContextCache( - compiler.context, - compiler.root - ); - - /** - * @param {Module} module the module - * @returns {string} the (portable) identifier - */ - const getModuleIdentifier = module => { - if (portableIds) { - return makePathsRelative(module.identifier()); - } - return module.identifier(); - }; - - compiler.hooks.compilation.tap("RecordIdsPlugin", compilation => { - compilation.hooks.recordModules.tap( - "RecordIdsPlugin", - /** - * @param {Module[]} modules the modules array - * @param {Records} records the records object - * @returns {void} - */ - (modules, records) => { - const chunkGraph = compilation.chunkGraph; - if (!records.modules) records.modules = {}; - if (!records.modules.byIdentifier) records.modules.byIdentifier = {}; - /** @type {Set} */ - const usedIds = new Set(); - for (const module of modules) { - const moduleId = chunkGraph.getModuleId(module); - if (typeof moduleId !== "number") continue; - const identifier = getModuleIdentifier(module); - records.modules.byIdentifier[identifier] = moduleId; - usedIds.add(moduleId); - } - records.modules.usedIds = Array.from(usedIds).sort(compareNumbers); - } - ); - compilation.hooks.reviveModules.tap( - "RecordIdsPlugin", - /** - * @param {Module[]} modules the modules array - * @param {Records} records the records object - * @returns {void} - */ - (modules, records) => { - if (!records.modules) return; - if (records.modules.byIdentifier) { - const chunkGraph = compilation.chunkGraph; - /** @type {Set} */ - const usedIds = new Set(); - for (const module of modules) { - const moduleId = chunkGraph.getModuleId(module); - if (moduleId !== null) continue; - const identifier = getModuleIdentifier(module); - const id = records.modules.byIdentifier[identifier]; - if (id === undefined) continue; - if (usedIds.has(id)) continue; - usedIds.add(id); - chunkGraph.setModuleId(module, id); - } - } - if (Array.isArray(records.modules.usedIds)) { - compilation.usedModuleIds = new Set(records.modules.usedIds); - } - } - ); - - /** - * @param {Chunk} chunk the chunk - * @returns {string[]} sources of the chunk - */ - const getChunkSources = chunk => { - /** @type {string[]} */ - const sources = []; - for (const chunkGroup of chunk.groupsIterable) { - const index = chunkGroup.chunks.indexOf(chunk); - if (chunkGroup.name) { - sources.push(`${index} ${chunkGroup.name}`); - } else { - for (const origin of chunkGroup.origins) { - if (origin.module) { - if (origin.request) { - sources.push( - `${index} ${getModuleIdentifier(origin.module)} ${ - origin.request - }` - ); - } else if (typeof origin.loc === "string") { - sources.push( - `${index} ${getModuleIdentifier(origin.module)} ${ - origin.loc - }` - ); - } else if ( - origin.loc && - typeof origin.loc === "object" && - "start" in origin.loc - ) { - sources.push( - `${index} ${getModuleIdentifier( - origin.module - )} ${JSON.stringify(origin.loc.start)}` - ); - } - } - } - } - } - return sources; - }; + constructor(module, err, loc) { + super(err.message); - compilation.hooks.recordChunks.tap( - "RecordIdsPlugin", - /** - * @param {Chunk[]} chunks the chunks array - * @param {Records} records the records object - * @returns {void} - */ - (chunks, records) => { - if (!records.chunks) records.chunks = {}; - if (!records.chunks.byName) records.chunks.byName = {}; - if (!records.chunks.bySource) records.chunks.bySource = {}; - /** @type {Set} */ - const usedIds = new Set(); - for (const chunk of chunks) { - if (typeof chunk.id !== "number") continue; - const name = chunk.name; - if (name) records.chunks.byName[name] = chunk.id; - const sources = getChunkSources(chunk); - for (const source of sources) { - records.chunks.bySource[source] = chunk.id; - } - usedIds.add(chunk.id); - } - records.chunks.usedIds = Array.from(usedIds).sort(compareNumbers); - } - ); - compilation.hooks.reviveChunks.tap( - "RecordIdsPlugin", - /** - * @param {Chunk[]} chunks the chunks array - * @param {Records} records the records object - * @returns {void} - */ - (chunks, records) => { - if (!records.chunks) return; - /** @type {Set} */ - const usedIds = new Set(); - if (records.chunks.byName) { - for (const chunk of chunks) { - if (chunk.id !== null) continue; - if (!chunk.name) continue; - const id = records.chunks.byName[chunk.name]; - if (id === undefined) continue; - if (usedIds.has(id)) continue; - usedIds.add(id); - chunk.id = id; - chunk.ids = [id]; - } - } - if (records.chunks.bySource) { - for (const chunk of chunks) { - if (chunk.id !== null) continue; - const sources = getChunkSources(chunk); - for (const source of sources) { - const id = records.chunks.bySource[source]; - if (id === undefined) continue; - if (usedIds.has(id)) continue; - usedIds.add(id); - chunk.id = id; - chunk.ids = [id]; - break; - } - } - } - if (Array.isArray(records.chunks.usedIds)) { - compilation.usedChunkIds = new Set(records.chunks.usedIds); - } - } - ); - }); + this.name = "ModuleDependencyError"; + this.details = + err && !(/** @type {any} */ (err).hideStack) + ? err.stack.split("\n").slice(1).join("\n") + : undefined; + this.module = module; + this.loc = loc; + /** error is not (de)serialized, so it might be undefined after deserialization */ + this.error = err; + + if (err && /** @type {any} */ (err).hideStack) { + this.stack = + err.stack.split("\n").slice(1).join("\n") + "\n\n" + this.stack; + } } } -module.exports = RecordIdsPlugin; + +module.exports = ModuleDependencyError; /***/ }), -/***/ 43157: +/***/ 61528: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; @@ -57811,38 +52220,49 @@ module.exports = RecordIdsPlugin; -const { contextify } = __webpack_require__(96236); +const WebpackError = __webpack_require__(68422); +const makeSerializable = __webpack_require__(26522); -class RequestShortener { - /** - * @param {string} dir the directory - * @param {object=} associatedObjectForCache an object to which the cache will be attached - */ - constructor(dir, associatedObjectForCache) { - this.contextify = contextify.bindContextCache( - dir, - associatedObjectForCache - ); - } +/** @typedef {import("./Dependency").DependencyLocation} DependencyLocation */ +/** @typedef {import("./Module")} Module */ +class ModuleDependencyWarning extends WebpackError { /** - * @param {string | undefined | null} request the request to shorten - * @returns {string | undefined | null} the shortened request + * @param {Module} module module tied to dependency + * @param {Error} err error thrown + * @param {DependencyLocation} loc location of dependency */ - shorten(request) { - if (!request) { - return request; + constructor(module, err, loc) { + super(err ? err.message : ""); + + this.name = "ModuleDependencyWarning"; + this.details = + err && !(/** @type {any} */ (err).hideStack) + ? err.stack.split("\n").slice(1).join("\n") + : undefined; + this.module = module; + this.loc = loc; + /** error is not (de)serialized, so it might be undefined after deserialization */ + this.error = err; + + if (err && /** @type {any} */ (err).hideStack) { + this.stack = + err.stack.split("\n").slice(1).join("\n") + "\n\n" + this.stack; } - return this.contextify(request); } } -module.exports = RequestShortener; +makeSerializable( + ModuleDependencyWarning, + "webpack/lib/ModuleDependencyWarning" +); + +module.exports = ModuleDependencyWarning; /***/ }), -/***/ 81898: +/***/ 11686: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; @@ -57853,81 +52273,65 @@ module.exports = RequestShortener; -const RuntimeGlobals = __webpack_require__(49404); -const ConstDependency = __webpack_require__(60864); -const { - toConstantDependency -} = __webpack_require__(28723); - -/** @typedef {import("./Compiler")} Compiler */ +const { cleanUp } = __webpack_require__(22569); +const WebpackError = __webpack_require__(68422); +const makeSerializable = __webpack_require__(26522); -module.exports = class RequireJsStuffPlugin { +class ModuleError extends WebpackError { /** - * Apply the plugin - * @param {Compiler} compiler the compiler instance - * @returns {void} + * @param {Error} err error thrown + * @param {{from?: string|null}} info additional info */ - apply(compiler) { - compiler.hooks.compilation.tap( - "RequireJsStuffPlugin", - (compilation, { normalModuleFactory }) => { - compilation.dependencyTemplates.set( - ConstDependency, - new ConstDependency.Template() - ); - const handler = (parser, parserOptions) => { - if ( - parserOptions.requireJs === undefined || - !parserOptions.requireJs - ) { - return; - } + constructor(err, { from = null } = {}) { + let message = "Module Error"; - parser.hooks.call - .for("require.config") - .tap( - "RequireJsStuffPlugin", - toConstantDependency(parser, "undefined") - ); - parser.hooks.call - .for("requirejs.config") - .tap( - "RequireJsStuffPlugin", - toConstantDependency(parser, "undefined") - ); + if (from) { + message += ` (from ${from}):\n`; + } else { + message += ": "; + } - parser.hooks.expression - .for("require.version") - .tap( - "RequireJsStuffPlugin", - toConstantDependency(parser, JSON.stringify("0.0.0")) - ); - parser.hooks.expression - .for("requirejs.onError") - .tap( - "RequireJsStuffPlugin", - toConstantDependency( - parser, - RuntimeGlobals.uncaughtErrorHandler, - [RuntimeGlobals.uncaughtErrorHandler] - ) - ); - }; - normalModuleFactory.hooks.parser - .for("javascript/auto") - .tap("RequireJsStuffPlugin", handler); - normalModuleFactory.hooks.parser - .for("javascript/dynamic") - .tap("RequireJsStuffPlugin", handler); - } - ); + if (err && typeof err === "object" && err.message) { + message += err.message; + } else if (err) { + message += err; + } + + super(message); + + this.name = "ModuleError"; + this.error = err; + this.details = + err && typeof err === "object" && err.stack + ? cleanUp(err.stack, this.message) + : undefined; } -}; + + serialize(context) { + const { write } = context; + + write(this.error); + + super.serialize(context); + } + + deserialize(context) { + const { read } = context; + + this.error = read(); + + super.deserialize(context); + } +} + +makeSerializable(ModuleError, "webpack/lib/ModuleError"); + +module.exports = ModuleError; /***/ }), -/***/ 88810: +/***/ 61574: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; @@ -57938,156 +52342,336 @@ module.exports = class RequireJsStuffPlugin { -const Factory = __webpack_require__(27480).ResolverFactory; -const { HookMap, SyncHook, SyncWaterfallHook } = __webpack_require__(34718); -const { - cachedCleverMerge, - removeOperations, - resolveByProperty -} = __webpack_require__(11217); - -/** @typedef {import("enhanced-resolve").ResolveOptions} ResolveOptions */ -/** @typedef {import("enhanced-resolve").Resolver} Resolver */ -/** @typedef {import("../declarations/WebpackOptions").ResolveOptions} WebpackResolveOptions */ -/** @typedef {import("../declarations/WebpackOptions").ResolvePluginInstance} ResolvePluginInstance */ +/** @typedef {import("../declarations/WebpackOptions").ResolveOptions} ResolveOptions */ +/** @typedef {import("./Dependency")} Dependency */ +/** @typedef {import("./Module")} Module */ -/** @typedef {WebpackResolveOptions & {dependencyType?: string, resolveToContext?: boolean }} ResolveOptionsWithDependencyType */ /** - * @typedef {Object} WithOptions - * @property {function(Partial): ResolverWithOptions} withOptions create a resolver with additional/different options + * @typedef {Object} ModuleFactoryResult + * @property {Module=} module the created module or unset if no module was created + * @property {Set=} fileDependencies + * @property {Set=} contextDependencies + * @property {Set=} missingDependencies + * @property {boolean=} cacheable allow to use the unsafe cache */ -/** @typedef {Resolver & WithOptions} ResolverWithOptions */ - -// need to be hoisted on module level for caching identity -const EMPTY_RESOLVE_OPTIONS = {}; +/** + * @typedef {Object} ModuleFactoryCreateDataContextInfo + * @property {string} issuer + * @property {string | null=} issuerLayer + * @property {string} compiler + */ /** - * @param {ResolveOptionsWithDependencyType} resolveOptionsWithDepType enhanced options - * @returns {ResolveOptions} merged options + * @typedef {Object} ModuleFactoryCreateData + * @property {ModuleFactoryCreateDataContextInfo} contextInfo + * @property {ResolveOptions=} resolveOptions + * @property {string} context + * @property {Dependency[]} dependencies */ -const convertToResolveOptions = resolveOptionsWithDepType => { - const { dependencyType, plugins, ...remaining } = resolveOptionsWithDepType; - // check type compat - /** @type {Partial} */ - const partialOptions = { - ...remaining, - plugins: - plugins && - /** @type {ResolvePluginInstance[]} */ ( - plugins.filter(item => item !== "...") - ) +class ModuleFactory { + /* istanbul ignore next */ + /** + * @abstract + * @param {ModuleFactoryCreateData} data data object + * @param {function(Error=, ModuleFactoryResult=): void} callback callback + * @returns {void} + */ + create(data, callback) { + const AbstractMethodError = __webpack_require__(570); + throw new AbstractMethodError(); + } +} + +module.exports = ModuleFactory; + + +/***/ }), + +/***/ 80295: +/***/ (function(__unused_webpack_module, exports, __webpack_require__) { + +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ + + + +const createHash = __webpack_require__(24123); +const memoize = __webpack_require__(84297); + +/** @typedef {import("./ChunkGraph")} ChunkGraph */ +/** @typedef {import("./Module")} Module */ +/** @typedef {import("./RequestShortener")} RequestShortener */ +/** @typedef {typeof import("./util/Hash")} Hash */ + +const ModuleFilenameHelpers = exports; + +// TODO webpack 6: consider removing these +ModuleFilenameHelpers.ALL_LOADERS_RESOURCE = "[all-loaders][resource]"; +ModuleFilenameHelpers.REGEXP_ALL_LOADERS_RESOURCE = + /\[all-?loaders\]\[resource\]/gi; +ModuleFilenameHelpers.LOADERS_RESOURCE = "[loaders][resource]"; +ModuleFilenameHelpers.REGEXP_LOADERS_RESOURCE = /\[loaders\]\[resource\]/gi; +ModuleFilenameHelpers.RESOURCE = "[resource]"; +ModuleFilenameHelpers.REGEXP_RESOURCE = /\[resource\]/gi; +ModuleFilenameHelpers.ABSOLUTE_RESOURCE_PATH = "[absolute-resource-path]"; +// cSpell:words olute +ModuleFilenameHelpers.REGEXP_ABSOLUTE_RESOURCE_PATH = + /\[abs(olute)?-?resource-?path\]/gi; +ModuleFilenameHelpers.RESOURCE_PATH = "[resource-path]"; +ModuleFilenameHelpers.REGEXP_RESOURCE_PATH = /\[resource-?path\]/gi; +ModuleFilenameHelpers.ALL_LOADERS = "[all-loaders]"; +ModuleFilenameHelpers.REGEXP_ALL_LOADERS = /\[all-?loaders\]/gi; +ModuleFilenameHelpers.LOADERS = "[loaders]"; +ModuleFilenameHelpers.REGEXP_LOADERS = /\[loaders\]/gi; +ModuleFilenameHelpers.QUERY = "[query]"; +ModuleFilenameHelpers.REGEXP_QUERY = /\[query\]/gi; +ModuleFilenameHelpers.ID = "[id]"; +ModuleFilenameHelpers.REGEXP_ID = /\[id\]/gi; +ModuleFilenameHelpers.HASH = "[hash]"; +ModuleFilenameHelpers.REGEXP_HASH = /\[hash\]/gi; +ModuleFilenameHelpers.NAMESPACE = "[namespace]"; +ModuleFilenameHelpers.REGEXP_NAMESPACE = /\[namespace\]/gi; + +const getAfter = (strFn, token) => { + return () => { + const str = strFn(); + const idx = str.indexOf(token); + return idx < 0 ? "" : str.substr(idx); }; +}; - if (!partialOptions.fileSystem) { - throw new Error( - "fileSystem is missing in resolveOptions, but it's required for enhanced-resolve" - ); +const getBefore = (strFn, token) => { + return () => { + const str = strFn(); + const idx = str.lastIndexOf(token); + return idx < 0 ? "" : str.substr(0, idx); + }; +}; + +const getHash = (strFn, hashFunction) => { + return () => { + const hash = createHash(hashFunction); + hash.update(strFn()); + const digest = /** @type {string} */ (hash.digest("hex")); + return digest.substr(0, 4); + }; +}; + +const asRegExp = test => { + if (typeof test === "string") { + test = new RegExp("^" + test.replace(/[-[\]{}()*+?.,\\^$|#\s]/g, "\\$&")); } - // These weird types validate that we checked all non-optional properties - const options = - /** @type {Partial & Pick} */ ( - partialOptions - ); + return test; +}; - return removeOperations( - resolveByProperty(options, "byDependency", dependencyType) - ); +const lazyObject = obj => { + const newObj = {}; + for (const key of Object.keys(obj)) { + const fn = obj[key]; + Object.defineProperty(newObj, key, { + get: () => fn(), + set: v => { + Object.defineProperty(newObj, key, { + value: v, + enumerable: true, + writable: true + }); + }, + enumerable: true, + configurable: true + }); + } + return newObj; }; +const REGEXP = /\[\\*([\w-]+)\\*\]/gi; + /** - * @typedef {Object} ResolverCache - * @property {WeakMap} direct - * @property {Map} stringified + * + * @param {Module | string} module the module + * @param {TODO} options options + * @param {Object} contextInfo context info + * @param {RequestShortener} contextInfo.requestShortener requestShortener + * @param {ChunkGraph} contextInfo.chunkGraph chunk graph + * @param {string | Hash} contextInfo.hashFunction the hash function to use + * @returns {string} the filename */ +ModuleFilenameHelpers.createFilename = ( + module = "", + options, + { requestShortener, chunkGraph, hashFunction = "md4" } +) => { + const opts = { + namespace: "", + moduleFilenameTemplate: "", + ...(typeof options === "object" + ? options + : { + moduleFilenameTemplate: options + }) + }; -module.exports = class ResolverFactory { - constructor() { - this.hooks = Object.freeze({ - /** @type {HookMap>} */ - resolveOptions: new HookMap( - () => new SyncWaterfallHook(["resolveOptions"]) - ), - /** @type {HookMap>} */ - resolver: new HookMap( - () => new SyncHook(["resolver", "resolveOptions", "userResolveOptions"]) - ) + let absoluteResourcePath; + let hash; + let identifier; + let moduleId; + let shortIdentifier; + if (typeof module === "string") { + shortIdentifier = memoize(() => requestShortener.shorten(module)); + identifier = shortIdentifier; + moduleId = () => ""; + absoluteResourcePath = () => module.split("!").pop(); + hash = getHash(identifier, hashFunction); + } else { + shortIdentifier = memoize(() => + module.readableIdentifier(requestShortener) + ); + identifier = memoize(() => requestShortener.shorten(module.identifier())); + moduleId = () => chunkGraph.getModuleId(module); + absoluteResourcePath = () => module.identifier().split("!").pop(); + hash = getHash(identifier, hashFunction); + } + const resource = memoize(() => shortIdentifier().split("!").pop()); + + const loaders = getBefore(shortIdentifier, "!"); + const allLoaders = getBefore(identifier, "!"); + const query = getAfter(resource, "?"); + const resourcePath = () => { + const q = query().length; + return q === 0 ? resource() : resource().slice(0, -q); + }; + if (typeof opts.moduleFilenameTemplate === "function") { + return opts.moduleFilenameTemplate( + lazyObject({ + identifier: identifier, + shortIdentifier: shortIdentifier, + resource: resource, + resourcePath: memoize(resourcePath), + absoluteResourcePath: memoize(absoluteResourcePath), + allLoaders: memoize(allLoaders), + query: memoize(query), + moduleId: memoize(moduleId), + hash: memoize(hash), + namespace: () => opts.namespace + }) + ); + } + + // TODO webpack 6: consider removing alternatives without dashes + /** @type {Map} */ + const replacements = new Map([ + ["identifier", identifier], + ["short-identifier", shortIdentifier], + ["resource", resource], + ["resource-path", resourcePath], + // cSpell:words resourcepath + ["resourcepath", resourcePath], + ["absolute-resource-path", absoluteResourcePath], + ["abs-resource-path", absoluteResourcePath], + // cSpell:words absoluteresource + ["absoluteresource-path", absoluteResourcePath], + // cSpell:words absresource + ["absresource-path", absoluteResourcePath], + // cSpell:words resourcepath + ["absolute-resourcepath", absoluteResourcePath], + // cSpell:words resourcepath + ["abs-resourcepath", absoluteResourcePath], + // cSpell:words absoluteresourcepath + ["absoluteresourcepath", absoluteResourcePath], + // cSpell:words absresourcepath + ["absresourcepath", absoluteResourcePath], + ["all-loaders", allLoaders], + // cSpell:words allloaders + ["allloaders", allLoaders], + ["loaders", loaders], + ["query", query], + ["id", moduleId], + ["hash", hash], + ["namespace", () => opts.namespace] + ]); + + // TODO webpack 6: consider removing weird double placeholders + return opts.moduleFilenameTemplate + .replace(ModuleFilenameHelpers.REGEXP_ALL_LOADERS_RESOURCE, "[identifier]") + .replace( + ModuleFilenameHelpers.REGEXP_LOADERS_RESOURCE, + "[short-identifier]" + ) + .replace(REGEXP, (match, content) => { + if (content.length + 2 === match.length) { + const replacement = replacements.get(content.toLowerCase()); + if (replacement !== undefined) { + return replacement(); + } + } else if (match.startsWith("[\\") && match.endsWith("\\]")) { + return `[${match.slice(2, -2)}]`; + } + return match; }); - /** @type {Map} */ - this.cache = new Map(); +}; + +ModuleFilenameHelpers.replaceDuplicates = (array, fn, comparator) => { + const countMap = Object.create(null); + const posMap = Object.create(null); + array.forEach((item, idx) => { + countMap[item] = countMap[item] || []; + countMap[item].push(idx); + posMap[item] = 0; + }); + if (comparator) { + Object.keys(countMap).forEach(item => { + countMap[item].sort(comparator); + }); + } + return array.map((item, i) => { + if (countMap[item].length > 1) { + if (comparator && countMap[item][0] === i) return item; + return fn(item, i, posMap[item]++); + } else { + return item; + } + }); +}; + +ModuleFilenameHelpers.matchPart = (str, test) => { + if (!test) return true; + test = asRegExp(test); + if (Array.isArray(test)) { + return test.map(asRegExp).some(regExp => regExp.test(str)); + } else { + return test.test(str); } +}; - /** - * @param {string} type type of resolver - * @param {ResolveOptionsWithDependencyType=} resolveOptions options - * @returns {ResolverWithOptions} the resolver - */ - get(type, resolveOptions = EMPTY_RESOLVE_OPTIONS) { - let typedCaches = this.cache.get(type); - if (!typedCaches) { - typedCaches = { - direct: new WeakMap(), - stringified: new Map() - }; - this.cache.set(type, typedCaches); - } - const cachedResolver = typedCaches.direct.get(resolveOptions); - if (cachedResolver) { - return cachedResolver; +ModuleFilenameHelpers.matchObject = (obj, str) => { + if (obj.test) { + if (!ModuleFilenameHelpers.matchPart(str, obj.test)) { + return false; } - const ident = JSON.stringify(resolveOptions); - const resolver = typedCaches.stringified.get(ident); - if (resolver) { - typedCaches.direct.set(resolveOptions, resolver); - return resolver; + } + if (obj.include) { + if (!ModuleFilenameHelpers.matchPart(str, obj.include)) { + return false; } - const newResolver = this._create(type, resolveOptions); - typedCaches.direct.set(resolveOptions, newResolver); - typedCaches.stringified.set(ident, newResolver); - return newResolver; } - - /** - * @param {string} type type of resolver - * @param {ResolveOptionsWithDependencyType} resolveOptionsWithDepType options - * @returns {ResolverWithOptions} the resolver - */ - _create(type, resolveOptionsWithDepType) { - /** @type {ResolveOptionsWithDependencyType} */ - const originalResolveOptions = { ...resolveOptionsWithDepType }; - - const resolveOptions = convertToResolveOptions( - this.hooks.resolveOptions.for(type).call(resolveOptionsWithDepType) - ); - const resolver = /** @type {ResolverWithOptions} */ ( - Factory.createResolver(resolveOptions) - ); - if (!resolver) { - throw new Error("No resolver created"); + if (obj.exclude) { + if (ModuleFilenameHelpers.matchPart(str, obj.exclude)) { + return false; } - /** @type {WeakMap, ResolverWithOptions>} */ - const childCache = new WeakMap(); - resolver.withOptions = options => { - const cacheEntry = childCache.get(options); - if (cacheEntry !== undefined) return cacheEntry; - const mergedOptions = cachedCleverMerge(originalResolveOptions, options); - const resolver = this.get(type, mergedOptions); - childCache.set(options, resolver); - return resolver; - }; - this.hooks.resolver - .for(type) - .call(resolver, resolveOptions, originalResolveOptions); - return resolver; } + return true; }; /***/ }), -/***/ 49404: -/***/ (function(__unused_webpack_module, exports) { +/***/ 20258: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; /* @@ -58097,981 +52681,861 @@ module.exports = class ResolverFactory { -/** - * the internal require function - */ -exports.require = "__webpack_require__"; - -/** - * access to properties of the internal require function/object - */ -exports.requireScope = "__webpack_require__.*"; - -/** - * the internal exports object - */ -exports.exports = "__webpack_exports__"; - -/** - * top-level this need to be the exports object - */ -exports.thisAsExports = "top-level-this-exports"; - -/** - * runtime need to return the exports of the last entry module - */ -exports.returnExportsFromRuntime = "return-exports-from-runtime"; - -/** - * the internal module object - */ -exports.module = "module"; - -/** - * the internal module object - */ -exports.moduleId = "module.id"; - -/** - * the internal module object - */ -exports.moduleLoaded = "module.loaded"; - -/** - * the bundle public path - */ -exports.publicPath = "__webpack_require__.p"; - -/** - * the module id of the entry point - */ -exports.entryModuleId = "__webpack_require__.s"; - -/** - * the module cache - */ -exports.moduleCache = "__webpack_require__.c"; - -/** - * the module functions - */ -exports.moduleFactories = "__webpack_require__.m"; - -/** - * the module functions, with only write access - */ -exports.moduleFactoriesAddOnly = "__webpack_require__.m (add only)"; - -/** - * the chunk ensure function - */ -exports.ensureChunk = "__webpack_require__.e"; - -/** - * an object with handlers to ensure a chunk - */ -exports.ensureChunkHandlers = "__webpack_require__.f"; - -/** - * a runtime requirement if ensureChunkHandlers should include loading of chunk needed for entries - */ -exports.ensureChunkIncludeEntries = "__webpack_require__.f (include entries)"; - -/** - * the chunk prefetch function - */ -exports.prefetchChunk = "__webpack_require__.E"; - -/** - * an object with handlers to prefetch a chunk - */ -exports.prefetchChunkHandlers = "__webpack_require__.F"; - -/** - * the chunk preload function - */ -exports.preloadChunk = "__webpack_require__.G"; - -/** - * an object with handlers to preload a chunk - */ -exports.preloadChunkHandlers = "__webpack_require__.H"; - -/** - * the exported property define getters function - */ -exports.definePropertyGetters = "__webpack_require__.d"; - -/** - * define compatibility on export - */ -exports.makeNamespaceObject = "__webpack_require__.r"; - -/** - * create a fake namespace object - */ -exports.createFakeNamespaceObject = "__webpack_require__.t"; - -/** - * compatibility get default export - */ -exports.compatGetDefaultExport = "__webpack_require__.n"; - -/** - * harmony module decorator - */ -exports.harmonyModuleDecorator = "__webpack_require__.hmd"; - -/** - * node.js module decorator - */ -exports.nodeModuleDecorator = "__webpack_require__.nmd"; - -/** - * the webpack hash - */ -exports.getFullHash = "__webpack_require__.h"; - -/** - * an object containing all installed WebAssembly.Instance export objects keyed by module id - */ -exports.wasmInstances = "__webpack_require__.w"; - -/** - * instantiate a wasm instance from module exports object, id, hash and importsObject - */ -exports.instantiateWasm = "__webpack_require__.v"; - -/** - * the uncaught error handler for the webpack runtime - */ -exports.uncaughtErrorHandler = "__webpack_require__.oe"; - -/** - * the script nonce - */ -exports.scriptNonce = "__webpack_require__.nc"; - -/** - * function to load a script tag. - * Arguments: (url: string, done: (event) => void), key?: string | number, chunkId?: string | number) => void - * done function is called when loading has finished or timeout occurred. - * It will attach to existing script tags with data-webpack == key or src == url. - */ -exports.loadScript = "__webpack_require__.l"; - -/** - * function to promote a string to a TrustedScriptURL using webpack's Trusted - * Types policy - * Arguments: (url: string) => TrustedScriptURL - */ -exports.createScriptUrl = "__webpack_require__.tu"; - -/** - * the chunk name of the chunk with the runtime - */ -exports.chunkName = "__webpack_require__.cn"; +const util = __webpack_require__(31669); +const ExportsInfo = __webpack_require__(4295); +const ModuleGraphConnection = __webpack_require__(94144); +const SortableSet = __webpack_require__(67563); +const WeakTupleMap = __webpack_require__(73963); -/** - * the runtime id of the current runtime - */ -exports.runtimeId = "__webpack_require__.j"; +/** @typedef {import("./DependenciesBlock")} DependenciesBlock */ +/** @typedef {import("./Dependency")} Dependency */ +/** @typedef {import("./ExportsInfo").ExportInfo} ExportInfo */ +/** @typedef {import("./Module")} Module */ +/** @typedef {import("./ModuleProfile")} ModuleProfile */ +/** @typedef {import("./RequestShortener")} RequestShortener */ +/** @typedef {import("./util/runtime").RuntimeSpec} RuntimeSpec */ /** - * the filename of the script part of the chunk + * @callback OptimizationBailoutFunction + * @param {RequestShortener} requestShortener + * @returns {string} */ -exports.getChunkScriptFilename = "__webpack_require__.u"; -/** - * the filename of the script part of the hot update chunk - */ -exports.getChunkUpdateScriptFilename = "__webpack_require__.hu"; +const EMPTY_SET = new Set(); /** - * startup signal from runtime - * This will be called when the runtime chunk has been loaded. + * @param {SortableSet} set input + * @returns {readonly Map} mapped by origin module */ -exports.startup = "__webpack_require__.x"; +const getConnectionsByOriginModule = set => { + const map = new Map(); + /** @type {Module | 0} */ + let lastModule = 0; + /** @type {ModuleGraphConnection[]} */ + let lastList = undefined; + for (const connection of set) { + const { originModule } = connection; + if (lastModule === originModule) { + lastList.push(connection); + } else { + lastModule = originModule; + const list = map.get(originModule); + if (list !== undefined) { + lastList = list; + list.push(connection); + } else { + const list = [connection]; + lastList = list; + map.set(originModule, list); + } + } + } + return map; +}; /** - * @deprecated - * creating a default startup function with the entry modules + * @param {SortableSet} set input + * @returns {readonly Map} mapped by module */ -exports.startupNoDefault = "__webpack_require__.x (no default handler)"; +const getConnectionsByModule = set => { + const map = new Map(); + /** @type {Module | 0} */ + let lastModule = 0; + /** @type {ModuleGraphConnection[]} */ + let lastList = undefined; + for (const connection of set) { + const { module } = connection; + if (lastModule === module) { + lastList.push(connection); + } else { + lastModule = module; + const list = map.get(module); + if (list !== undefined) { + lastList = list; + list.push(connection); + } else { + const list = [connection]; + lastList = list; + map.set(module, list); + } + } + } + return map; +}; -/** - * startup signal from runtime but only used to add logic after the startup - */ -exports.startupOnlyAfter = "__webpack_require__.x (only after)"; +class ModuleGraphModule { + constructor() { + /** @type {SortableSet} */ + this.incomingConnections = new SortableSet(); + /** @type {SortableSet | undefined} */ + this.outgoingConnections = undefined; + /** @type {Module | null} */ + this.issuer = undefined; + /** @type {(string | OptimizationBailoutFunction)[]} */ + this.optimizationBailout = []; + /** @type {ExportsInfo} */ + this.exports = new ExportsInfo(); + /** @type {number} */ + this.preOrderIndex = null; + /** @type {number} */ + this.postOrderIndex = null; + /** @type {number} */ + this.depth = null; + /** @type {ModuleProfile} */ + this.profile = undefined; + /** @type {boolean} */ + this.async = false; + /** @type {ModuleGraphConnection[]} */ + this._unassignedConnections = undefined; + } +} -/** - * startup signal from runtime but only used to add sync logic before the startup - */ -exports.startupOnlyBefore = "__webpack_require__.x (only before)"; +class ModuleGraph { + constructor() { + /** @type {WeakMap} */ + this._dependencyMap = new WeakMap(); + /** @type {Map} */ + this._moduleMap = new Map(); + /** @type {WeakMap} */ + this._metaMap = new WeakMap(); -/** - * global callback functions for installing chunks - */ -exports.chunkCallback = "webpackChunk"; + /** @type {WeakTupleMap} */ + this._cache = undefined; -/** - * method to startup an entrypoint with needed chunks. - * Signature: (moduleId: Id, chunkIds: Id[]) => any. - * Returns the exports of the module or a Promise - */ -exports.startupEntrypoint = "__webpack_require__.X"; + /** @type {Map>} */ + this._moduleMemCaches = undefined; + } -/** - * register deferred code, which will run when certain - * chunks are loaded. - * Signature: (chunkIds: Id[], fn: () => any, priority: int >= 0 = 0) => any - * Returned value will be returned directly when all chunks are already loaded - * When (priority & 1) it will wait for all other handlers with lower priority to - * be executed before itself is executed - */ -exports.onChunksLoaded = "__webpack_require__.O"; + /** + * @param {Module} module the module + * @returns {ModuleGraphModule} the internal module + */ + _getModuleGraphModule(module) { + let mgm = this._moduleMap.get(module); + if (mgm === undefined) { + mgm = new ModuleGraphModule(); + this._moduleMap.set(module, mgm); + } + return mgm; + } -/** - * method to install a chunk that was loaded somehow - * Signature: ({ id, ids, modules, runtime }) => void - */ -exports.externalInstallChunk = "__webpack_require__.C"; + /** + * @param {Dependency} dependency the dependency + * @param {DependenciesBlock} block parent block + * @param {Module} module parent module + * @param {number=} indexInBlock position in block + * @returns {void} + */ + setParents(dependency, block, module, indexInBlock = -1) { + dependency._parentDependenciesBlockIndex = indexInBlock; + dependency._parentDependenciesBlock = block; + dependency._parentModule = module; + } -/** - * interceptor for module executions - */ -exports.interceptModuleExecution = "__webpack_require__.i"; + /** + * @param {Dependency} dependency the dependency + * @returns {Module} parent module + */ + getParentModule(dependency) { + return dependency._parentModule; + } -/** - * the global object - */ -exports.global = "__webpack_require__.g"; + /** + * @param {Dependency} dependency the dependency + * @returns {DependenciesBlock} parent block + */ + getParentBlock(dependency) { + return dependency._parentDependenciesBlock; + } -/** - * an object with all share scopes - */ -exports.shareScopeMap = "__webpack_require__.S"; + /** + * @param {Dependency} dependency the dependency + * @returns {number} index + */ + getParentBlockIndex(dependency) { + return dependency._parentDependenciesBlockIndex; + } -/** - * The sharing init sequence function (only runs once per share scope). - * Has one argument, the name of the share scope. - * Creates a share scope if not existing - */ -exports.initializeSharing = "__webpack_require__.I"; + /** + * @param {Module} originModule the referencing module + * @param {Dependency} dependency the referencing dependency + * @param {Module} module the referenced module + * @returns {void} + */ + setResolvedModule(originModule, dependency, module) { + const connection = new ModuleGraphConnection( + originModule, + dependency, + module, + undefined, + dependency.weak, + dependency.getCondition(this) + ); + const connections = this._getModuleGraphModule(module).incomingConnections; + connections.add(connection); + if (originModule) { + const mgm = this._getModuleGraphModule(originModule); + if (mgm._unassignedConnections === undefined) { + mgm._unassignedConnections = []; + } + mgm._unassignedConnections.push(connection); + if (mgm.outgoingConnections === undefined) { + mgm.outgoingConnections = new SortableSet(); + } + mgm.outgoingConnections.add(connection); + } else { + this._dependencyMap.set(dependency, connection); + } + } -/** - * The current scope when getting a module from a remote - */ -exports.currentRemoteGetScope = "__webpack_require__.R"; + /** + * @param {Dependency} dependency the referencing dependency + * @param {Module} module the referenced module + * @returns {void} + */ + updateModule(dependency, module) { + const connection = this.getConnection(dependency); + if (connection.module === module) return; + const newConnection = connection.clone(); + newConnection.module = module; + this._dependencyMap.set(dependency, newConnection); + connection.setActive(false); + const originMgm = this._getModuleGraphModule(connection.originModule); + originMgm.outgoingConnections.add(newConnection); + const targetMgm = this._getModuleGraphModule(module); + targetMgm.incomingConnections.add(newConnection); + } -/** - * the filename of the HMR manifest - */ -exports.getUpdateManifestFilename = "__webpack_require__.hmrF"; + /** + * @param {Dependency} dependency the referencing dependency + * @returns {void} + */ + removeConnection(dependency) { + const connection = this.getConnection(dependency); + const targetMgm = this._getModuleGraphModule(connection.module); + targetMgm.incomingConnections.delete(connection); + const originMgm = this._getModuleGraphModule(connection.originModule); + originMgm.outgoingConnections.delete(connection); + this._dependencyMap.set(dependency, null); + } -/** - * function downloading the update manifest - */ -exports.hmrDownloadManifest = "__webpack_require__.hmrM"; + /** + * @param {Dependency} dependency the referencing dependency + * @param {string} explanation an explanation + * @returns {void} + */ + addExplanation(dependency, explanation) { + const connection = this.getConnection(dependency); + connection.addExplanation(explanation); + } -/** - * array with handler functions to download chunk updates - */ -exports.hmrDownloadUpdateHandlers = "__webpack_require__.hmrC"; + /** + * @param {Module} sourceModule the source module + * @param {Module} targetModule the target module + * @returns {void} + */ + cloneModuleAttributes(sourceModule, targetModule) { + const oldMgm = this._getModuleGraphModule(sourceModule); + const newMgm = this._getModuleGraphModule(targetModule); + newMgm.postOrderIndex = oldMgm.postOrderIndex; + newMgm.preOrderIndex = oldMgm.preOrderIndex; + newMgm.depth = oldMgm.depth; + newMgm.exports = oldMgm.exports; + newMgm.async = oldMgm.async; + } -/** - * object with all hmr module data for all modules - */ -exports.hmrModuleData = "__webpack_require__.hmrD"; + /** + * @param {Module} module the module + * @returns {void} + */ + removeModuleAttributes(module) { + const mgm = this._getModuleGraphModule(module); + mgm.postOrderIndex = null; + mgm.preOrderIndex = null; + mgm.depth = null; + mgm.async = false; + } -/** - * array with handler functions when a module should be invalidated - */ -exports.hmrInvalidateModuleHandlers = "__webpack_require__.hmrI"; + /** + * @returns {void} + */ + removeAllModuleAttributes() { + for (const mgm of this._moduleMap.values()) { + mgm.postOrderIndex = null; + mgm.preOrderIndex = null; + mgm.depth = null; + mgm.async = false; + } + } -/** - * the prefix for storing state of runtime modules when hmr is enabled - */ -exports.hmrRuntimeStatePrefix = "__webpack_require__.hmrS"; + /** + * @param {Module} oldModule the old referencing module + * @param {Module} newModule the new referencing module + * @param {function(ModuleGraphConnection): boolean} filterConnection filter predicate for replacement + * @returns {void} + */ + moveModuleConnections(oldModule, newModule, filterConnection) { + if (oldModule === newModule) return; + const oldMgm = this._getModuleGraphModule(oldModule); + const newMgm = this._getModuleGraphModule(newModule); + // Outgoing connections + const oldConnections = oldMgm.outgoingConnections; + if (oldConnections !== undefined) { + if (newMgm.outgoingConnections === undefined) { + newMgm.outgoingConnections = new SortableSet(); + } + const newConnections = newMgm.outgoingConnections; + for (const connection of oldConnections) { + if (filterConnection(connection)) { + connection.originModule = newModule; + newConnections.add(connection); + oldConnections.delete(connection); + } + } + } + // Incoming connections + const oldConnections2 = oldMgm.incomingConnections; + const newConnections2 = newMgm.incomingConnections; + for (const connection of oldConnections2) { + if (filterConnection(connection)) { + connection.module = newModule; + newConnections2.add(connection); + oldConnections2.delete(connection); + } + } + } -/** - * the AMD define function - */ -exports.amdDefine = "__webpack_require__.amdD"; + /** + * @param {Module} oldModule the old referencing module + * @param {Module} newModule the new referencing module + * @param {function(ModuleGraphConnection): boolean} filterConnection filter predicate for replacement + * @returns {void} + */ + copyOutgoingModuleConnections(oldModule, newModule, filterConnection) { + if (oldModule === newModule) return; + const oldMgm = this._getModuleGraphModule(oldModule); + const newMgm = this._getModuleGraphModule(newModule); + // Outgoing connections + const oldConnections = oldMgm.outgoingConnections; + if (oldConnections !== undefined) { + if (newMgm.outgoingConnections === undefined) { + newMgm.outgoingConnections = new SortableSet(); + } + const newConnections = newMgm.outgoingConnections; + for (const connection of oldConnections) { + if (filterConnection(connection)) { + const newConnection = connection.clone(); + newConnection.originModule = newModule; + newConnections.add(newConnection); + if (newConnection.module !== undefined) { + const otherMgm = this._getModuleGraphModule(newConnection.module); + otherMgm.incomingConnections.add(newConnection); + } + } + } + } + } -/** - * the AMD options - */ -exports.amdOptions = "__webpack_require__.amdO"; + /** + * @param {Module} module the referenced module + * @param {string} explanation an explanation why it's referenced + * @returns {void} + */ + addExtraReason(module, explanation) { + const connections = this._getModuleGraphModule(module).incomingConnections; + connections.add(new ModuleGraphConnection(null, null, module, explanation)); + } -/** - * the System polyfill object - */ -exports.system = "__webpack_require__.System"; + /** + * @param {Dependency} dependency the dependency to look for a referenced module + * @returns {Module} the referenced module + */ + getResolvedModule(dependency) { + const connection = this.getConnection(dependency); + return connection !== undefined ? connection.resolvedModule : null; + } -/** - * the shorthand for Object.prototype.hasOwnProperty - * using of it decreases the compiled bundle size - */ -exports.hasOwnProperty = "__webpack_require__.o"; + /** + * @param {Dependency} dependency the dependency to look for a referenced module + * @returns {ModuleGraphConnection | undefined} the connection + */ + getConnection(dependency) { + const connection = this._dependencyMap.get(dependency); + if (connection === undefined) { + const module = this.getParentModule(dependency); + if (module !== undefined) { + const mgm = this._getModuleGraphModule(module); + if ( + mgm._unassignedConnections && + mgm._unassignedConnections.length !== 0 + ) { + let foundConnection; + for (const connection of mgm._unassignedConnections) { + this._dependencyMap.set(connection.dependency, connection); + if (connection.dependency === dependency) + foundConnection = connection; + } + mgm._unassignedConnections.length = 0; + if (foundConnection !== undefined) { + return foundConnection; + } + } + } + this._dependencyMap.set(dependency, null); + return undefined; + } + return connection === null ? undefined : connection; + } -/** - * the System.register context object - */ -exports.systemContext = "__webpack_require__.y"; + /** + * @param {Dependency} dependency the dependency to look for a referenced module + * @returns {Module} the referenced module + */ + getModule(dependency) { + const connection = this.getConnection(dependency); + return connection !== undefined ? connection.module : null; + } -/** - * the baseURI of current document - */ -exports.baseURI = "__webpack_require__.b"; + /** + * @param {Dependency} dependency the dependency to look for a referencing module + * @returns {Module} the referencing module + */ + getOrigin(dependency) { + const connection = this.getConnection(dependency); + return connection !== undefined ? connection.originModule : null; + } -/** - * a RelativeURL class when relative URLs are used - */ -exports.relativeUrl = "__webpack_require__.U"; + /** + * @param {Dependency} dependency the dependency to look for a referencing module + * @returns {Module} the original referencing module + */ + getResolvedOrigin(dependency) { + const connection = this.getConnection(dependency); + return connection !== undefined ? connection.resolvedOriginModule : null; + } -/** - * Creates an async module. The body function must be a async function. - * "module.exports" will be decorated with an AsyncModulePromise. - * The body function will be called. - * To handle async dependencies correctly do this: "([a, b, c] = await handleDependencies([a, b, c]));". - * If "hasAwaitAfterDependencies" is truthy, "handleDependencies()" must be called at the end of the body function. - * Signature: function( - * module: Module, - * body: (handleDependencies: (deps: AsyncModulePromise[]) => Promise & () => void, - * hasAwaitAfterDependencies?: boolean - * ) => void - */ -exports.asyncModule = "__webpack_require__.a"; + /** + * @param {Module} module the module + * @returns {Iterable} reasons why a module is included + */ + getIncomingConnections(module) { + const connections = this._getModuleGraphModule(module).incomingConnections; + return connections; + } + /** + * @param {Module} module the module + * @returns {Iterable} list of outgoing connections + */ + getOutgoingConnections(module) { + const connections = this._getModuleGraphModule(module).outgoingConnections; + return connections === undefined ? EMPTY_SET : connections; + } -/***/ }), + /** + * @param {Module} module the module + * @returns {readonly Map} reasons why a module is included, in a map by source module + */ + getIncomingConnectionsByOriginModule(module) { + const connections = this._getModuleGraphModule(module).incomingConnections; + return connections.getFromUnorderedCache(getConnectionsByOriginModule); + } -/***/ 61439: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + /** + * @param {Module} module the module + * @returns {readonly Map | undefined} connections to modules, in a map by module + */ + getOutgoingConnectionsByModule(module) { + const connections = this._getModuleGraphModule(module).outgoingConnections; + return connections === undefined + ? undefined + : connections.getFromUnorderedCache(getConnectionsByModule); + } -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ + /** + * @param {Module} module the module + * @returns {ModuleProfile | null} the module profile + */ + getProfile(module) { + const mgm = this._getModuleGraphModule(module); + return mgm.profile; + } + /** + * @param {Module} module the module + * @param {ModuleProfile | null} profile the module profile + * @returns {void} + */ + setProfile(module, profile) { + const mgm = this._getModuleGraphModule(module); + mgm.profile = profile; + } + /** + * @param {Module} module the module + * @returns {Module | null} the issuer module + */ + getIssuer(module) { + const mgm = this._getModuleGraphModule(module); + return mgm.issuer; + } -const { RawSource } = __webpack_require__(96192); -const OriginalSource = __webpack_require__(96192).OriginalSource; -const Module = __webpack_require__(85887); + /** + * @param {Module} module the module + * @param {Module | null} issuer the issuer module + * @returns {void} + */ + setIssuer(module, issuer) { + const mgm = this._getModuleGraphModule(module); + mgm.issuer = issuer; + } -/** @typedef {import("webpack-sources").Source} Source */ -/** @typedef {import("../declarations/WebpackOptions").WebpackOptionsNormalized} WebpackOptions */ -/** @typedef {import("./Chunk")} Chunk */ -/** @typedef {import("./ChunkGraph")} ChunkGraph */ -/** @typedef {import("./Compilation")} Compilation */ -/** @typedef {import("./Dependency").UpdateHashContext} UpdateHashContext */ -/** @typedef {import("./Module").CodeGenerationContext} CodeGenerationContext */ -/** @typedef {import("./Module").CodeGenerationResult} CodeGenerationResult */ -/** @typedef {import("./Module").NeedBuildContext} NeedBuildContext */ -/** @typedef {import("./RequestShortener")} RequestShortener */ -/** @typedef {import("./ResolverFactory").ResolverWithOptions} ResolverWithOptions */ -/** @typedef {import("./WebpackError")} WebpackError */ -/** @typedef {import("./util/Hash")} Hash */ -/** @typedef {import("./util/fs").InputFileSystem} InputFileSystem */ + /** + * @param {Module} module the module + * @param {Module | null} issuer the issuer module + * @returns {void} + */ + setIssuerIfUnset(module, issuer) { + const mgm = this._getModuleGraphModule(module); + if (mgm.issuer === undefined) mgm.issuer = issuer; + } -const TYPES = new Set(["runtime"]); + /** + * @param {Module} module the module + * @returns {(string | OptimizationBailoutFunction)[]} optimization bailouts + */ + getOptimizationBailout(module) { + const mgm = this._getModuleGraphModule(module); + return mgm.optimizationBailout; + } -class RuntimeModule extends Module { /** - * @param {string} name a readable name - * @param {number=} stage an optional stage + * @param {Module} module the module + * @returns {true | string[] | null} the provided exports */ - constructor(name, stage = 0) { - super("runtime"); - this.name = name; - this.stage = stage; - this.buildMeta = {}; - this.buildInfo = {}; - /** @type {Compilation} */ - this.compilation = undefined; - /** @type {Chunk} */ - this.chunk = undefined; - /** @type {ChunkGraph} */ - this.chunkGraph = undefined; - this.fullHash = false; - this.dependentHash = false; - /** @type {string} */ - this._cachedGeneratedCode = undefined; + getProvidedExports(module) { + const mgm = this._getModuleGraphModule(module); + return mgm.exports.getProvidedExports(); } /** - * @param {Compilation} compilation the compilation - * @param {Chunk} chunk the chunk - * @param {ChunkGraph} chunkGraph the chunk graph - * @returns {void} + * @param {Module} module the module + * @param {string | string[]} exportName a name of an export + * @returns {boolean | null} true, if the export is provided by the module. + * null, if it's unknown. + * false, if it's not provided. */ - attach(compilation, chunk, chunkGraph = compilation.chunkGraph) { - this.compilation = compilation; - this.chunk = chunk; - this.chunkGraph = chunkGraph; + isExportProvided(module, exportName) { + const mgm = this._getModuleGraphModule(module); + const result = mgm.exports.isExportProvided(exportName); + return result === undefined ? null : result; } /** - * @returns {string} a unique identifier of the module + * @param {Module} module the module + * @returns {ExportsInfo} info about the exports */ - identifier() { - return `webpack/runtime/${this.name}`; + getExportsInfo(module) { + const mgm = this._getModuleGraphModule(module); + return mgm.exports; } /** - * @param {RequestShortener} requestShortener the request shortener - * @returns {string} a user readable identifier of the module + * @param {Module} module the module + * @param {string} exportName the export + * @returns {ExportInfo} info about the export */ - readableIdentifier(requestShortener) { - return `webpack/runtime/${this.name}`; + getExportInfo(module, exportName) { + const mgm = this._getModuleGraphModule(module); + return mgm.exports.getExportInfo(exportName); } /** - * @param {NeedBuildContext} context context info - * @param {function(WebpackError=, boolean=): void} callback callback function, returns true, if the module needs a rebuild - * @returns {void} + * @param {Module} module the module + * @param {string} exportName the export + * @returns {ExportInfo} info about the export (do not modify) */ - needBuild(context, callback) { - return callback(null, false); + getReadOnlyExportInfo(module, exportName) { + const mgm = this._getModuleGraphModule(module); + return mgm.exports.getReadOnlyExportInfo(exportName); } /** - * @param {WebpackOptions} options webpack options - * @param {Compilation} compilation the compilation - * @param {ResolverWithOptions} resolver the resolver - * @param {InputFileSystem} fs the file system - * @param {function(WebpackError=): void} callback callback function - * @returns {void} + * @param {Module} module the module + * @param {RuntimeSpec} runtime the runtime + * @returns {false | true | SortableSet | null} the used exports + * false: module is not used at all. + * true: the module namespace/object export is used. + * SortableSet: these export names are used. + * empty SortableSet: module is used but no export. + * null: unknown, worst case should be assumed. */ - build(options, compilation, resolver, fs, callback) { - // do nothing - // should not be called as runtime modules are added later to the compilation - callback(); + getUsedExports(module, runtime) { + const mgm = this._getModuleGraphModule(module); + return mgm.exports.getUsedExports(runtime); } /** - * @param {Hash} hash the hash used to track dependencies - * @param {UpdateHashContext} context context - * @returns {void} + * @param {Module} module the module + * @returns {number} the index of the module */ - updateHash(hash, context) { - hash.update(this.name); - hash.update(`${this.stage}`); - try { - if (this.fullHash || this.dependentHash) { - // Do not use getGeneratedCode here, because i. e. compilation hash might be not - // ready at this point. We will cache it later instead. - hash.update(this.generate()); - } else { - hash.update(this.getGeneratedCode()); - } - } catch (err) { - hash.update(err.message); - } - super.updateHash(hash, context); + getPreOrderIndex(module) { + const mgm = this._getModuleGraphModule(module); + return mgm.preOrderIndex; } /** - * @returns {Set} types available (do not mutate) + * @param {Module} module the module + * @returns {number} the index of the module */ - getSourceTypes() { - return TYPES; + getPostOrderIndex(module) { + const mgm = this._getModuleGraphModule(module); + return mgm.postOrderIndex; } /** - * @param {CodeGenerationContext} context context for code generation - * @returns {CodeGenerationResult} result + * @param {Module} module the module + * @param {number} index the index of the module + * @returns {void} */ - codeGeneration(context) { - const sources = new Map(); - const generatedCode = this.getGeneratedCode(); - if (generatedCode) { - sources.set( - "runtime", - this.useSourceMap || this.useSimpleSourceMap - ? new OriginalSource(generatedCode, this.identifier()) - : new RawSource(generatedCode) - ); - } - return { - sources, - runtimeRequirements: null - }; + setPreOrderIndex(module, index) { + const mgm = this._getModuleGraphModule(module); + mgm.preOrderIndex = index; } /** - * @param {string=} type the source type for which the size should be estimated - * @returns {number} the estimated size of the module (must be non-zero) + * @param {Module} module the module + * @param {number} index the index of the module + * @returns {boolean} true, if the index was set */ - size(type) { - try { - const source = this.getGeneratedCode(); - return source ? source.length : 0; - } catch (e) { - return 0; + setPreOrderIndexIfUnset(module, index) { + const mgm = this._getModuleGraphModule(module); + if (mgm.preOrderIndex === null) { + mgm.preOrderIndex = index; + return true; } + return false; } - /* istanbul ignore next */ /** - * @abstract - * @returns {string} runtime code + * @param {Module} module the module + * @param {number} index the index of the module + * @returns {void} */ - generate() { - const AbstractMethodError = __webpack_require__(570); - throw new AbstractMethodError(); + setPostOrderIndex(module, index) { + const mgm = this._getModuleGraphModule(module); + mgm.postOrderIndex = index; } /** - * @returns {string} runtime code + * @param {Module} module the module + * @param {number} index the index of the module + * @returns {boolean} true, if the index was set */ - getGeneratedCode() { - if (this._cachedGeneratedCode) { - return this._cachedGeneratedCode; + setPostOrderIndexIfUnset(module, index) { + const mgm = this._getModuleGraphModule(module); + if (mgm.postOrderIndex === null) { + mgm.postOrderIndex = index; + return true; } - return (this._cachedGeneratedCode = this.generate()); + return false; } /** - * @returns {boolean} true, if the runtime module should get it's own scope + * @param {Module} module the module + * @returns {number} the depth of the module */ - shouldIsolate() { - return true; + getDepth(module) { + const mgm = this._getModuleGraphModule(module); + return mgm.depth; } -} - -/** - * Runtime modules without any dependencies to other runtime modules - */ -RuntimeModule.STAGE_NORMAL = 0; - -/** - * Runtime modules with simple dependencies on other runtime modules - */ -RuntimeModule.STAGE_BASIC = 5; - -/** - * Runtime modules which attach to handlers of other runtime modules - */ -RuntimeModule.STAGE_ATTACH = 10; - -/** - * Runtime modules which trigger actions on bootstrap - */ -RuntimeModule.STAGE_TRIGGER = 20; - -module.exports = RuntimeModule; - - -/***/ }), - -/***/ 86809: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ - - - -const RuntimeGlobals = __webpack_require__(49404); -const RuntimeRequirementsDependency = __webpack_require__(75941); -const JavascriptModulesPlugin = __webpack_require__(76767); -const AsyncModuleRuntimeModule = __webpack_require__(31372); -const AutoPublicPathRuntimeModule = __webpack_require__(86150); -const CompatGetDefaultExportRuntimeModule = __webpack_require__(24013); -const CompatRuntimeModule = __webpack_require__(65788); -const CreateFakeNamespaceObjectRuntimeModule = __webpack_require__(58470); -const CreateScriptUrlRuntimeModule = __webpack_require__(41690); -const DefinePropertyGettersRuntimeModule = __webpack_require__(24905); -const EnsureChunkRuntimeModule = __webpack_require__(92857); -const GetChunkFilenameRuntimeModule = __webpack_require__(53288); -const GetMainFilenameRuntimeModule = __webpack_require__(10034); -const GlobalRuntimeModule = __webpack_require__(89651); -const HasOwnPropertyRuntimeModule = __webpack_require__(39399); -const LoadScriptRuntimeModule = __webpack_require__(80647); -const MakeNamespaceObjectRuntimeModule = __webpack_require__(62962); -const OnChunksLoadedRuntimeModule = __webpack_require__(92794); -const PublicPathRuntimeModule = __webpack_require__(10569); -const RelativeUrlRuntimeModule = __webpack_require__(68642); -const RuntimeIdRuntimeModule = __webpack_require__(90984); -const SystemContextRuntimeModule = __webpack_require__(33248); -const ShareRuntimeModule = __webpack_require__(97207); -const StringXor = __webpack_require__(23877); - -/** @typedef {import("./Chunk")} Chunk */ -/** @typedef {import("./Compiler")} Compiler */ -/** @typedef {import("./Module")} Module */ - -const GLOBALS_ON_REQUIRE = [ - RuntimeGlobals.chunkName, - RuntimeGlobals.runtimeId, - RuntimeGlobals.compatGetDefaultExport, - RuntimeGlobals.createFakeNamespaceObject, - RuntimeGlobals.createScriptUrl, - RuntimeGlobals.definePropertyGetters, - RuntimeGlobals.ensureChunk, - RuntimeGlobals.entryModuleId, - RuntimeGlobals.getFullHash, - RuntimeGlobals.global, - RuntimeGlobals.makeNamespaceObject, - RuntimeGlobals.moduleCache, - RuntimeGlobals.moduleFactories, - RuntimeGlobals.moduleFactoriesAddOnly, - RuntimeGlobals.interceptModuleExecution, - RuntimeGlobals.publicPath, - RuntimeGlobals.baseURI, - RuntimeGlobals.relativeUrl, - RuntimeGlobals.scriptNonce, - RuntimeGlobals.uncaughtErrorHandler, - RuntimeGlobals.asyncModule, - RuntimeGlobals.wasmInstances, - RuntimeGlobals.instantiateWasm, - RuntimeGlobals.shareScopeMap, - RuntimeGlobals.initializeSharing, - RuntimeGlobals.loadScript, - RuntimeGlobals.systemContext, - RuntimeGlobals.onChunksLoaded -]; - -const MODULE_DEPENDENCIES = { - [RuntimeGlobals.moduleLoaded]: [RuntimeGlobals.module], - [RuntimeGlobals.moduleId]: [RuntimeGlobals.module] -}; - -const TREE_DEPENDENCIES = { - [RuntimeGlobals.definePropertyGetters]: [RuntimeGlobals.hasOwnProperty], - [RuntimeGlobals.compatGetDefaultExport]: [ - RuntimeGlobals.definePropertyGetters - ], - [RuntimeGlobals.createFakeNamespaceObject]: [ - RuntimeGlobals.definePropertyGetters, - RuntimeGlobals.makeNamespaceObject, - RuntimeGlobals.require - ], - [RuntimeGlobals.initializeSharing]: [RuntimeGlobals.shareScopeMap], - [RuntimeGlobals.shareScopeMap]: [RuntimeGlobals.hasOwnProperty] -}; -class RuntimePlugin { /** - * @param {Compiler} compiler the Compiler + * @param {Module} module the module + * @param {number} depth the depth of the module * @returns {void} */ - apply(compiler) { - compiler.hooks.compilation.tap("RuntimePlugin", compilation => { - compilation.dependencyTemplates.set( - RuntimeRequirementsDependency, - new RuntimeRequirementsDependency.Template() - ); - for (const req of GLOBALS_ON_REQUIRE) { - compilation.hooks.runtimeRequirementInModule - .for(req) - .tap("RuntimePlugin", (module, set) => { - set.add(RuntimeGlobals.requireScope); - }); - compilation.hooks.runtimeRequirementInTree - .for(req) - .tap("RuntimePlugin", (module, set) => { - set.add(RuntimeGlobals.requireScope); - }); - } - for (const req of Object.keys(TREE_DEPENDENCIES)) { - const deps = TREE_DEPENDENCIES[req]; - compilation.hooks.runtimeRequirementInTree - .for(req) - .tap("RuntimePlugin", (chunk, set) => { - for (const dep of deps) set.add(dep); - }); - } - for (const req of Object.keys(MODULE_DEPENDENCIES)) { - const deps = MODULE_DEPENDENCIES[req]; - compilation.hooks.runtimeRequirementInModule - .for(req) - .tap("RuntimePlugin", (chunk, set) => { - for (const dep of deps) set.add(dep); - }); - } - compilation.hooks.runtimeRequirementInTree - .for(RuntimeGlobals.definePropertyGetters) - .tap("RuntimePlugin", chunk => { - compilation.addRuntimeModule( - chunk, - new DefinePropertyGettersRuntimeModule() - ); - return true; - }); - compilation.hooks.runtimeRequirementInTree - .for(RuntimeGlobals.makeNamespaceObject) - .tap("RuntimePlugin", chunk => { - compilation.addRuntimeModule( - chunk, - new MakeNamespaceObjectRuntimeModule() - ); - return true; - }); - compilation.hooks.runtimeRequirementInTree - .for(RuntimeGlobals.createFakeNamespaceObject) - .tap("RuntimePlugin", chunk => { - compilation.addRuntimeModule( - chunk, - new CreateFakeNamespaceObjectRuntimeModule() - ); - return true; - }); - compilation.hooks.runtimeRequirementInTree - .for(RuntimeGlobals.hasOwnProperty) - .tap("RuntimePlugin", chunk => { - compilation.addRuntimeModule( - chunk, - new HasOwnPropertyRuntimeModule() - ); - return true; - }); - compilation.hooks.runtimeRequirementInTree - .for(RuntimeGlobals.compatGetDefaultExport) - .tap("RuntimePlugin", chunk => { - compilation.addRuntimeModule( - chunk, - new CompatGetDefaultExportRuntimeModule() - ); - return true; - }); - compilation.hooks.runtimeRequirementInTree - .for(RuntimeGlobals.runtimeId) - .tap("RuntimePlugin", chunk => { - compilation.addRuntimeModule(chunk, new RuntimeIdRuntimeModule()); - return true; - }); - compilation.hooks.runtimeRequirementInTree - .for(RuntimeGlobals.publicPath) - .tap("RuntimePlugin", (chunk, set) => { - const { outputOptions } = compilation; - const { publicPath: globalPublicPath, scriptType } = outputOptions; - const entryOptions = chunk.getEntryOptions(); - const publicPath = - entryOptions && entryOptions.publicPath !== undefined - ? entryOptions.publicPath - : globalPublicPath; - - if (publicPath === "auto") { - const module = new AutoPublicPathRuntimeModule(); - if (scriptType !== "module") set.add(RuntimeGlobals.global); - compilation.addRuntimeModule(chunk, module); - } else { - const module = new PublicPathRuntimeModule(publicPath); - - if ( - typeof publicPath !== "string" || - /\[(full)?hash\]/.test(publicPath) - ) { - module.fullHash = true; - } - - compilation.addRuntimeModule(chunk, module); - } - return true; - }); - compilation.hooks.runtimeRequirementInTree - .for(RuntimeGlobals.global) - .tap("RuntimePlugin", chunk => { - compilation.addRuntimeModule(chunk, new GlobalRuntimeModule()); - return true; - }); - compilation.hooks.runtimeRequirementInTree - .for(RuntimeGlobals.asyncModule) - .tap("RuntimePlugin", chunk => { - compilation.addRuntimeModule(chunk, new AsyncModuleRuntimeModule()); - return true; - }); - compilation.hooks.runtimeRequirementInTree - .for(RuntimeGlobals.systemContext) - .tap("RuntimePlugin", chunk => { - const { outputOptions } = compilation; - const { library: globalLibrary } = outputOptions; - const entryOptions = chunk.getEntryOptions(); - const libraryType = - entryOptions && entryOptions.library !== undefined - ? entryOptions.library.type - : globalLibrary.type; + setDepth(module, depth) { + const mgm = this._getModuleGraphModule(module); + mgm.depth = depth; + } - if (libraryType === "system") { - compilation.addRuntimeModule( - chunk, - new SystemContextRuntimeModule() - ); - } - return true; - }); - compilation.hooks.runtimeRequirementInTree - .for(RuntimeGlobals.getChunkScriptFilename) - .tap("RuntimePlugin", (chunk, set) => { - if ( - typeof compilation.outputOptions.chunkFilename === "string" && - /\[(full)?hash(:\d+)?\]/.test( - compilation.outputOptions.chunkFilename - ) - ) { - set.add(RuntimeGlobals.getFullHash); - } - compilation.addRuntimeModule( - chunk, - new GetChunkFilenameRuntimeModule( - "javascript", - "javascript", - RuntimeGlobals.getChunkScriptFilename, - chunk => - chunk.filenameTemplate || - (chunk.canBeInitial() - ? compilation.outputOptions.filename - : compilation.outputOptions.chunkFilename), - false - ) - ); - return true; - }); - compilation.hooks.runtimeRequirementInTree - .for(RuntimeGlobals.getChunkUpdateScriptFilename) - .tap("RuntimePlugin", (chunk, set) => { - if ( - /\[(full)?hash(:\d+)?\]/.test( - compilation.outputOptions.hotUpdateChunkFilename - ) - ) - set.add(RuntimeGlobals.getFullHash); - compilation.addRuntimeModule( - chunk, - new GetChunkFilenameRuntimeModule( - "javascript", - "javascript update", - RuntimeGlobals.getChunkUpdateScriptFilename, - c => compilation.outputOptions.hotUpdateChunkFilename, - true - ) - ); - return true; - }); - compilation.hooks.runtimeRequirementInTree - .for(RuntimeGlobals.getUpdateManifestFilename) - .tap("RuntimePlugin", (chunk, set) => { - if ( - /\[(full)?hash(:\d+)?\]/.test( - compilation.outputOptions.hotUpdateMainFilename - ) - ) { - set.add(RuntimeGlobals.getFullHash); - } - compilation.addRuntimeModule( - chunk, - new GetMainFilenameRuntimeModule( - "update manifest", - RuntimeGlobals.getUpdateManifestFilename, - compilation.outputOptions.hotUpdateMainFilename - ) - ); - return true; - }); - compilation.hooks.runtimeRequirementInTree - .for(RuntimeGlobals.ensureChunk) - .tap("RuntimePlugin", (chunk, set) => { - const hasAsyncChunks = chunk.hasAsyncChunks(); - if (hasAsyncChunks) { - set.add(RuntimeGlobals.ensureChunkHandlers); - } - compilation.addRuntimeModule( - chunk, - new EnsureChunkRuntimeModule(set) - ); - return true; - }); - compilation.hooks.runtimeRequirementInTree - .for(RuntimeGlobals.ensureChunkIncludeEntries) - .tap("RuntimePlugin", (chunk, set) => { - set.add(RuntimeGlobals.ensureChunkHandlers); - }); - compilation.hooks.runtimeRequirementInTree - .for(RuntimeGlobals.shareScopeMap) - .tap("RuntimePlugin", (chunk, set) => { - compilation.addRuntimeModule(chunk, new ShareRuntimeModule()); - return true; - }); - compilation.hooks.runtimeRequirementInTree - .for(RuntimeGlobals.loadScript) - .tap("RuntimePlugin", (chunk, set) => { - const withCreateScriptUrl = !!compilation.outputOptions.trustedTypes; - if (withCreateScriptUrl) { - set.add(RuntimeGlobals.createScriptUrl); - } - compilation.addRuntimeModule( - chunk, - new LoadScriptRuntimeModule(withCreateScriptUrl) - ); - return true; - }); - compilation.hooks.runtimeRequirementInTree - .for(RuntimeGlobals.createScriptUrl) - .tap("RuntimePlugin", (chunk, set) => { - compilation.addRuntimeModule( - chunk, - new CreateScriptUrlRuntimeModule() - ); - return true; - }); - compilation.hooks.runtimeRequirementInTree - .for(RuntimeGlobals.relativeUrl) - .tap("RuntimePlugin", (chunk, set) => { - compilation.addRuntimeModule(chunk, new RelativeUrlRuntimeModule()); - return true; - }); - compilation.hooks.runtimeRequirementInTree - .for(RuntimeGlobals.onChunksLoaded) - .tap("RuntimePlugin", (chunk, set) => { - compilation.addRuntimeModule( - chunk, - new OnChunksLoadedRuntimeModule() - ); - return true; - }); - // TODO webpack 6: remove CompatRuntimeModule - compilation.hooks.additionalTreeRuntimeRequirements.tap( - "RuntimePlugin", - (chunk, set) => { - const { mainTemplate } = compilation; - if ( - mainTemplate.hooks.bootstrap.isUsed() || - mainTemplate.hooks.localVars.isUsed() || - mainTemplate.hooks.requireEnsure.isUsed() || - mainTemplate.hooks.requireExtensions.isUsed() - ) { - compilation.addRuntimeModule(chunk, new CompatRuntimeModule()); - } - } - ); - JavascriptModulesPlugin.getCompilationHooks(compilation).chunkHash.tap( - "RuntimePlugin", - (chunk, hash, { chunkGraph }) => { - const xor = new StringXor(); - for (const m of chunkGraph.getChunkRuntimeModulesIterable(chunk)) { - xor.add(chunkGraph.getModuleHash(m, chunk.runtime)); - } - xor.updateHash(hash); - } + /** + * @param {Module} module the module + * @param {number} depth the depth of the module + * @returns {boolean} true, if the depth was set + */ + setDepthIfLower(module, depth) { + const mgm = this._getModuleGraphModule(module); + if (mgm.depth === null || mgm.depth > depth) { + mgm.depth = depth; + return true; + } + return false; + } + + /** + * @param {Module} module the module + * @returns {boolean} true, if the module is async + */ + isAsync(module) { + const mgm = this._getModuleGraphModule(module); + return mgm.async; + } + + /** + * @param {Module} module the module + * @returns {void} + */ + setAsync(module) { + const mgm = this._getModuleGraphModule(module); + mgm.async = true; + } + + /** + * @param {any} thing any thing + * @returns {Object} metadata + */ + getMeta(thing) { + let meta = this._metaMap.get(thing); + if (meta === undefined) { + meta = Object.create(null); + this._metaMap.set(thing, meta); + } + return meta; + } + + /** + * @param {any} thing any thing + * @returns {Object} metadata + */ + getMetaIfExisting(thing) { + return this._metaMap.get(thing); + } + + /** + * @param {string=} cacheStage a persistent stage name for caching + */ + freeze(cacheStage) { + this._cache = new WeakTupleMap(); + this._cacheStage = cacheStage; + } + + unfreeze() { + this._cache = undefined; + this._cacheStage = undefined; + } + + /** + * @template {any[]} T + * @template V + * @param {(moduleGraph: ModuleGraph, ...args: T) => V} fn computer + * @param {T} args arguments + * @returns {V} computed value or cached + */ + cached(fn, ...args) { + if (this._cache === undefined) return fn(this, ...args); + return this._cache.provide(fn, ...args, () => fn(this, ...args)); + } + + /** + * @param {Map>} moduleMemCaches mem caches for modules for better caching + */ + setModuleMemCaches(moduleMemCaches) { + this._moduleMemCaches = moduleMemCaches; + } + + /** + * @param {Dependency} dependency dependency + * @param {...any} args arguments, last argument is a function called with moduleGraph, dependency, ...args + * @returns {any} computed value or cached + */ + dependencyCacheProvide(dependency, ...args) { + /** @type {(moduleGraph: ModuleGraph, dependency: Dependency, ...args: any[]) => any} */ + const fn = args.pop(); + if (this._moduleMemCaches && this._cacheStage) { + const memCache = this._moduleMemCaches.get( + this.getParentModule(dependency) ); - }); + if (memCache !== undefined) { + return memCache.provide(dependency, this._cacheStage, ...args, () => + fn(this, dependency, ...args) + ); + } + } + if (this._cache === undefined) return fn(this, dependency, ...args); + return this._cache.provide(dependency, ...args, () => + fn(this, dependency, ...args) + ); + } + + // TODO remove in webpack 6 + /** + * @param {Module} module the module + * @param {string} deprecateMessage message for the deprecation message + * @param {string} deprecationCode code for the deprecation + * @returns {ModuleGraph} the module graph + */ + static getModuleGraphForModule(module, deprecateMessage, deprecationCode) { + const fn = deprecateMap.get(deprecateMessage); + if (fn) return fn(module); + const newFn = util.deprecate( + /** + * @param {Module} module the module + * @returns {ModuleGraph} the module graph + */ + module => { + const moduleGraph = moduleGraphForModuleMap.get(module); + if (!moduleGraph) + throw new Error( + deprecateMessage + + "There was no ModuleGraph assigned to the Module for backward-compat (Use the new API)" + ); + return moduleGraph; + }, + deprecateMessage + ": Use new ModuleGraph API", + deprecationCode + ); + deprecateMap.set(deprecateMessage, newFn); + return newFn(module); + } + + // TODO remove in webpack 6 + /** + * @param {Module} module the module + * @param {ModuleGraph} moduleGraph the module graph + * @returns {void} + */ + static setModuleGraphForModule(module, moduleGraph) { + moduleGraphForModuleMap.set(module, moduleGraph); + } + + // TODO remove in webpack 6 + /** + * @param {Module} module the module + * @returns {void} + */ + static clearModuleGraphForModule(module) { + moduleGraphForModuleMap.delete(module); } } -module.exports = RuntimePlugin; + +// TODO remove in webpack 6 +/** @type {WeakMap} */ +const moduleGraphForModuleMap = new WeakMap(); + +// TODO remove in webpack 6 +/** @type {Map ModuleGraph>} */ +const deprecateMap = new Map(); + +module.exports = ModuleGraph; +module.exports.ModuleGraphConnection = ModuleGraphConnection; /***/ }), -/***/ 23974: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { +/***/ 94144: +/***/ (function(module) { "use strict"; /* @@ -59081,934 +53545,1104 @@ module.exports = RuntimePlugin; -const InitFragment = __webpack_require__(51739); -const RuntimeGlobals = __webpack_require__(49404); -const Template = __webpack_require__(92066); -const { equals } = __webpack_require__(21537); -const compileBooleanMatcher = __webpack_require__(356); -const propertyAccess = __webpack_require__(86709); -const { forEachRuntime, subtractRuntime } = __webpack_require__(19655); - -/** @typedef {import("../declarations/WebpackOptions").OutputNormalized} OutputOptions */ -/** @typedef {import("./AsyncDependenciesBlock")} AsyncDependenciesBlock */ -/** @typedef {import("./ChunkGraph")} ChunkGraph */ -/** @typedef {import("./Compilation")} Compilation */ /** @typedef {import("./Dependency")} Dependency */ /** @typedef {import("./Module")} Module */ -/** @typedef {import("./ModuleGraph")} ModuleGraph */ -/** @typedef {import("./RequestShortener")} RequestShortener */ /** @typedef {import("./util/runtime").RuntimeSpec} RuntimeSpec */ /** - * @param {Module} module the module - * @param {ChunkGraph} chunkGraph the chunk graph - * @returns {string} error message + * Module itself is not connected, but transitive modules are connected transitively. */ -const noModuleIdErrorMessage = (module, chunkGraph) => { - return `Module ${module.identifier()} has no id assigned. -This should not happen. -It's in these chunks: ${ - Array.from( - chunkGraph.getModuleChunksIterable(module), - c => c.name || c.id || c.debugId - ).join(", ") || "none" - } (If module is in no chunk this indicates a bug in some chunk/module optimization logic) -Module has these incoming connections: ${Array.from( - chunkGraph.moduleGraph.getIncomingConnections(module), - connection => - `\n - ${ - connection.originModule && connection.originModule.identifier() - } ${connection.dependency && connection.dependency.type} ${ - (connection.explanations && - Array.from(connection.explanations).join(", ")) || - "" - }` - ).join("")}`; +const TRANSITIVE_ONLY = Symbol("transitive only"); + +/** + * While determining the active state, this flag is used to signal a circular connection. + */ +const CIRCULAR_CONNECTION = Symbol("circular connection"); + +/** @typedef {boolean | typeof TRANSITIVE_ONLY | typeof CIRCULAR_CONNECTION} ConnectionState */ + +/** + * @param {ConnectionState} a first + * @param {ConnectionState} b second + * @returns {ConnectionState} merged + */ +const addConnectionStates = (a, b) => { + if (a === true || b === true) return true; + if (a === false) return b; + if (b === false) return a; + if (a === TRANSITIVE_ONLY) return b; + if (b === TRANSITIVE_ONLY) return a; + return a; }; -class RuntimeTemplate { +/** + * @param {ConnectionState} a first + * @param {ConnectionState} b second + * @returns {ConnectionState} intersected + */ +const intersectConnectionStates = (a, b) => { + if (a === false || b === false) return false; + if (a === true) return b; + if (b === true) return a; + if (a === CIRCULAR_CONNECTION) return b; + if (b === CIRCULAR_CONNECTION) return a; + return a; +}; + +class ModuleGraphConnection { /** - * @param {Compilation} compilation the compilation - * @param {OutputOptions} outputOptions the compilation output options - * @param {RequestShortener} requestShortener the request shortener + * @param {Module|null} originModule the referencing module + * @param {Dependency|null} dependency the referencing dependency + * @param {Module} module the referenced module + * @param {string=} explanation some extra detail + * @param {boolean=} weak the reference is weak + * @param {false | function(ModuleGraphConnection, RuntimeSpec): ConnectionState=} condition condition for the connection */ - constructor(compilation, outputOptions, requestShortener) { - this.compilation = compilation; - this.outputOptions = outputOptions || {}; - this.requestShortener = requestShortener; - } - - isIIFE() { - return this.outputOptions.iife; + constructor( + originModule, + dependency, + module, + explanation, + weak = false, + condition = undefined + ) { + this.originModule = originModule; + this.resolvedOriginModule = originModule; + this.dependency = dependency; + this.resolvedModule = module; + this.module = module; + this.weak = weak; + this.conditional = !!condition; + this._active = condition !== false; + /** @type {function(ModuleGraphConnection, RuntimeSpec): ConnectionState} */ + this.condition = condition || undefined; + /** @type {Set} */ + this.explanations = undefined; + if (explanation) { + this.explanations = new Set(); + this.explanations.add(explanation); + } } - isModule() { - return this.outputOptions.module; + clone() { + const clone = new ModuleGraphConnection( + this.resolvedOriginModule, + this.dependency, + this.resolvedModule, + undefined, + this.weak, + this.condition + ); + clone.originModule = this.originModule; + clone.module = this.module; + clone.conditional = this.conditional; + clone._active = this._active; + if (this.explanations) clone.explanations = new Set(this.explanations); + return clone; } - supportsConst() { - return this.outputOptions.environment.const; + /** + * @param {function(ModuleGraphConnection, RuntimeSpec): ConnectionState} condition condition for the connection + * @returns {void} + */ + addCondition(condition) { + if (this.conditional) { + const old = this.condition; + this.condition = (c, r) => + intersectConnectionStates(old(c, r), condition(c, r)); + } else if (this._active) { + this.conditional = true; + this.condition = condition; + } } - supportsArrowFunction() { - return this.outputOptions.environment.arrowFunction; + /** + * @param {string} explanation the explanation to add + * @returns {void} + */ + addExplanation(explanation) { + if (this.explanations === undefined) { + this.explanations = new Set(); + } + this.explanations.add(explanation); } - supportsForOf() { - return this.outputOptions.environment.forOf; + get explanation() { + if (this.explanations === undefined) return ""; + return Array.from(this.explanations).join(" "); } - supportsDestructuring() { - return this.outputOptions.environment.destructuring; + // TODO webpack 5 remove + get active() { + throw new Error("Use getActiveState instead"); } - supportsBigIntLiteral() { - return this.outputOptions.environment.bigIntLiteral; + /** + * @param {RuntimeSpec} runtime the runtime + * @returns {boolean} true, if the connection is active + */ + isActive(runtime) { + if (!this.conditional) return this._active; + return this.condition(this, runtime) !== false; } - supportsDynamicImport() { - return this.outputOptions.environment.dynamicImport; + /** + * @param {RuntimeSpec} runtime the runtime + * @returns {boolean} true, if the connection is active + */ + isTargetActive(runtime) { + if (!this.conditional) return this._active; + return this.condition(this, runtime) === true; } - supportsEcmaScriptModuleSyntax() { - return this.outputOptions.environment.module; + /** + * @param {RuntimeSpec} runtime the runtime + * @returns {ConnectionState} true: fully active, false: inactive, TRANSITIVE: direct module inactive, but transitive connection maybe active + */ + getActiveState(runtime) { + if (!this.conditional) return this._active; + return this.condition(this, runtime); } - supportTemplateLiteral() { - // TODO - return false; + /** + * @param {boolean} value active or not + * @returns {void} + */ + setActive(value) { + this.conditional = false; + this._active = value; } - returningFunction(returnValue, args = "") { - return this.supportsArrowFunction() - ? `(${args}) => (${returnValue})` - : `function(${args}) { return ${returnValue}; }`; + set active(value) { + throw new Error("Use setActive instead"); } +} - basicFunction(args, body) { - return this.supportsArrowFunction() - ? `(${args}) => {\n${Template.indent(body)}\n}` - : `function(${args}) {\n${Template.indent(body)}\n}`; - } +/** @typedef {typeof TRANSITIVE_ONLY} TRANSITIVE_ONLY */ +/** @typedef {typeof CIRCULAR_CONNECTION} CIRCULAR_CONNECTION */ - expressionFunction(expression, args = "") { - return this.supportsArrowFunction() - ? `(${args}) => (${expression})` - : `function(${args}) { ${expression}; }`; - } +module.exports = ModuleGraphConnection; +module.exports.addConnectionStates = addConnectionStates; +module.exports.TRANSITIVE_ONLY = /** @type {typeof TRANSITIVE_ONLY} */ ( + TRANSITIVE_ONLY +); +module.exports.CIRCULAR_CONNECTION = /** @type {typeof CIRCULAR_CONNECTION} */ ( + CIRCULAR_CONNECTION +); - emptyFunction() { - return this.supportsArrowFunction() ? "x => {}" : "function() {}"; - } - destructureArray(items, value) { - return this.supportsDestructuring() - ? `var [${items.join(", ")}] = ${value};` - : Template.asString( - items.map((item, i) => `var ${item} = ${value}[${i}];`) - ); - } +/***/ }), - destructureObject(items, value) { - return this.supportsDestructuring() - ? `var {${items.join(", ")}} = ${value};` - : Template.asString( - items.map(item => `var ${item} = ${value}${propertyAccess([item])};`) - ); - } +/***/ 45095: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - iife(args, body) { - return `(${this.basicFunction(args, body)})()`; - } +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ - forEach(variable, array, body) { - return this.supportsForOf() - ? `for(const ${variable} of ${array}) {\n${Template.indent(body)}\n}` - : `${array}.forEach(function(${variable}) {\n${Template.indent( - body - )}\n});`; - } - /** - * Add a comment - * @param {object} options Information content of the comment - * @param {string=} options.request request string used originally - * @param {string=} options.chunkName name of the chunk referenced - * @param {string=} options.chunkReason reason information of the chunk - * @param {string=} options.message additional message - * @param {string=} options.exportName name of the export - * @returns {string} comment - */ - comment({ request, chunkName, chunkReason, message, exportName }) { - let content; - if (this.outputOptions.pathinfo) { - content = [message, request, chunkName, chunkReason] - .filter(Boolean) - .map(item => this.requestShortener.shorten(item)) - .join(" | "); - } else { - content = [message, chunkName, chunkReason] - .filter(Boolean) - .map(item => this.requestShortener.shorten(item)) - .join(" | "); - } - if (!content) return ""; - if (this.outputOptions.pathinfo) { - return Template.toComment(content) + " "; - } else { - return Template.toNormalComment(content) + " "; - } - } - /** - * @param {object} options generation options - * @param {string=} options.request request string used originally - * @returns {string} generated error block - */ - throwMissingModuleErrorBlock({ request }) { - const err = `Cannot find module '${request}'`; - return `var e = new Error(${JSON.stringify( - err - )}); e.code = 'MODULE_NOT_FOUND'; throw e;`; - } +const { ConcatSource, RawSource, CachedSource } = __webpack_require__(96192); +const { UsageState } = __webpack_require__(4295); +const Template = __webpack_require__(92066); +const JavascriptModulesPlugin = __webpack_require__(76767); - /** - * @param {object} options generation options - * @param {string=} options.request request string used originally - * @returns {string} generated error function - */ - throwMissingModuleErrorFunction({ request }) { - return `function webpackMissingModule() { ${this.throwMissingModuleErrorBlock( - { request } - )} }`; - } +/** @typedef {import("webpack-sources").Source} Source */ +/** @typedef {import("./Compiler")} Compiler */ +/** @typedef {import("./ExportsInfo")} ExportsInfo */ +/** @typedef {import("./ExportsInfo").ExportInfo} ExportInfo */ +/** @typedef {import("./Module")} Module */ +/** @typedef {import("./ModuleGraph")} ModuleGraph */ +/** @typedef {import("./ModuleTemplate")} ModuleTemplate */ +/** @typedef {import("./RequestShortener")} RequestShortener */ - /** - * @param {object} options generation options - * @param {string=} options.request request string used originally - * @returns {string} generated error IIFE - */ - missingModule({ request }) { - return `Object(${this.throwMissingModuleErrorFunction({ request })}())`; +const joinIterableWithComma = iterable => { + // This is more performant than Array.from().join(", ") + // as it doesn't create an array + let str = ""; + let first = true; + for (const item of iterable) { + if (first) { + first = false; + } else { + str += ", "; + } + str += item; } + return str; +}; - /** - * @param {object} options generation options - * @param {string=} options.request request string used originally - * @returns {string} generated error statement - */ - missingModuleStatement({ request }) { - return `${this.missingModule({ request })};\n`; - } +/** + * @param {ConcatSource} source output + * @param {string} indent spacing + * @param {ExportsInfo} exportsInfo data + * @param {ModuleGraph} moduleGraph moduleGraph + * @param {RequestShortener} requestShortener requestShortener + * @param {Set} alreadyPrinted deduplication set + * @returns {void} + */ +const printExportsInfoToSource = ( + source, + indent, + exportsInfo, + moduleGraph, + requestShortener, + alreadyPrinted = new Set() +) => { + const otherExportsInfo = exportsInfo.otherExportsInfo; - /** - * @param {object} options generation options - * @param {string=} options.request request string used originally - * @returns {string} generated error code - */ - missingModulePromise({ request }) { - return `Promise.resolve().then(${this.throwMissingModuleErrorFunction({ - request - })})`; - } + let alreadyPrintedExports = 0; - /** - * @param {Object} options options object - * @param {ChunkGraph} options.chunkGraph the chunk graph - * @param {Module} options.module the module - * @param {string} options.request the request that should be printed as comment - * @param {string=} options.idExpr expression to use as id expression - * @param {"expression" | "promise" | "statements"} options.type which kind of code should be returned - * @returns {string} the code - */ - weakError({ module, chunkGraph, request, idExpr, type }) { - const moduleId = chunkGraph.getModuleId(module); - const errorMessage = - moduleId === null - ? JSON.stringify("Module is not available (weak dependency)") - : idExpr - ? `"Module '" + ${idExpr} + "' is not available (weak dependency)"` - : JSON.stringify( - `Module '${moduleId}' is not available (weak dependency)` - ); - const comment = request ? Template.toNormalComment(request) + " " : ""; - const errorStatements = - `var e = new Error(${errorMessage}); ` + - comment + - "e.code = 'MODULE_NOT_FOUND'; throw e;"; - switch (type) { - case "statements": - return errorStatements; - case "promise": - return `Promise.resolve().then(${this.basicFunction( - "", - errorStatements - )})`; - case "expression": - return this.iife("", errorStatements); + // determine exports to print + const printedExports = []; + for (const exportInfo of exportsInfo.orderedExports) { + if (!alreadyPrinted.has(exportInfo)) { + alreadyPrinted.add(exportInfo); + printedExports.push(exportInfo); + } else { + alreadyPrintedExports++; } } + let showOtherExports = false; + if (!alreadyPrinted.has(otherExportsInfo)) { + alreadyPrinted.add(otherExportsInfo); + showOtherExports = true; + } else { + alreadyPrintedExports++; + } - /** - * @param {Object} options options object - * @param {Module} options.module the module - * @param {ChunkGraph} options.chunkGraph the chunk graph - * @param {string} options.request the request that should be printed as comment - * @param {boolean=} options.weak if the dependency is weak (will create a nice error message) - * @returns {string} the expression - */ - moduleId({ module, chunkGraph, request, weak }) { - if (!module) { - return this.missingModule({ - request - }); - } - const moduleId = chunkGraph.getModuleId(module); - if (moduleId === null) { - if (weak) { - return "null /* weak dependency, without id */"; - } - throw new Error( - `RuntimeTemplate.moduleId(): ${noModuleIdErrorMessage( - module, - chunkGraph - )}` + // print the exports + for (const exportInfo of printedExports) { + const target = exportInfo.getTarget(moduleGraph); + source.add( + Template.toComment( + `${indent}export ${JSON.stringify(exportInfo.name).slice( + 1, + -1 + )} [${exportInfo.getProvidedInfo()}] [${exportInfo.getUsedInfo()}] [${exportInfo.getRenameInfo()}]${ + target + ? ` -> ${target.module.readableIdentifier(requestShortener)}${ + target.export + ? ` .${target.export + .map(e => JSON.stringify(e).slice(1, -1)) + .join(".")}` + : "" + }` + : "" + }` + ) + "\n" + ); + if (exportInfo.exportsInfo) { + printExportsInfoToSource( + source, + indent + " ", + exportInfo.exportsInfo, + moduleGraph, + requestShortener, + alreadyPrinted ); } - return `${this.comment({ request })}${JSON.stringify(moduleId)}`; } - /** - * @param {Object} options options object - * @param {Module} options.module the module - * @param {ChunkGraph} options.chunkGraph the chunk graph - * @param {string} options.request the request that should be printed as comment - * @param {boolean=} options.weak if the dependency is weak (will create a nice error message) - * @param {Set} options.runtimeRequirements if set, will be filled with runtime requirements - * @returns {string} the expression - */ - moduleRaw({ module, chunkGraph, request, weak, runtimeRequirements }) { - if (!module) { - return this.missingModule({ - request - }); - } - const moduleId = chunkGraph.getModuleId(module); - if (moduleId === null) { - if (weak) { - // only weak referenced modules don't get an id - // we can always emit an error emitting code here - return this.weakError({ - module, - chunkGraph, - request, - type: "expression" - }); - } - throw new Error( - `RuntimeTemplate.moduleId(): ${noModuleIdErrorMessage( - module, - chunkGraph - )}` + if (alreadyPrintedExports) { + source.add( + Template.toComment( + `${indent}... (${alreadyPrintedExports} already listed exports)` + ) + "\n" + ); + } + + if (showOtherExports) { + const target = otherExportsInfo.getTarget(moduleGraph); + if ( + target || + otherExportsInfo.provided !== false || + otherExportsInfo.getUsed(undefined) !== UsageState.Unused + ) { + const title = + printedExports.length > 0 || alreadyPrintedExports > 0 + ? "other exports" + : "exports"; + source.add( + Template.toComment( + `${indent}${title} [${otherExportsInfo.getProvidedInfo()}] [${otherExportsInfo.getUsedInfo()}]${ + target + ? ` -> ${target.module.readableIdentifier(requestShortener)}` + : "" + }` + ) + "\n" ); } - runtimeRequirements.add(RuntimeGlobals.require); - return `__webpack_require__(${this.moduleId({ - module, - chunkGraph, - request, - weak - })})`; } +}; - /** - * @param {Object} options options object - * @param {Module} options.module the module - * @param {ChunkGraph} options.chunkGraph the chunk graph - * @param {string} options.request the request that should be printed as comment - * @param {boolean=} options.weak if the dependency is weak (will create a nice error message) - * @param {Set} options.runtimeRequirements if set, will be filled with runtime requirements - * @returns {string} the expression - */ - moduleExports({ module, chunkGraph, request, weak, runtimeRequirements }) { - return this.moduleRaw({ - module, - chunkGraph, - request, - weak, - runtimeRequirements - }); - } +/** @type {WeakMap }>>} */ +const caches = new WeakMap(); +class ModuleInfoHeaderPlugin { /** - * @param {Object} options options object - * @param {Module} options.module the module - * @param {ChunkGraph} options.chunkGraph the chunk graph - * @param {string} options.request the request that should be printed as comment - * @param {boolean=} options.strict if the current module is in strict esm mode - * @param {boolean=} options.weak if the dependency is weak (will create a nice error message) - * @param {Set} options.runtimeRequirements if set, will be filled with runtime requirements - * @returns {string} the expression + * @param {boolean=} verbose add more information like exports, runtime requirements and bailouts */ - moduleNamespace({ - module, - chunkGraph, - request, - strict, - weak, - runtimeRequirements - }) { - if (!module) { - return this.missingModule({ - request - }); - } - if (chunkGraph.getModuleId(module) === null) { - if (weak) { - // only weak referenced modules don't get an id - // we can always emit an error emitting code here - return this.weakError({ - module, - chunkGraph, - request, - type: "expression" - }); - } - throw new Error( - `RuntimeTemplate.moduleNamespace(): ${noModuleIdErrorMessage( - module, - chunkGraph - )}` - ); - } - const moduleId = this.moduleId({ - module, - chunkGraph, - request, - weak - }); - const exportsType = module.getExportsType(chunkGraph.moduleGraph, strict); - switch (exportsType) { - case "namespace": - return this.moduleRaw({ - module, - chunkGraph, - request, - weak, - runtimeRequirements - }); - case "default-with-named": - runtimeRequirements.add(RuntimeGlobals.createFakeNamespaceObject); - return `${RuntimeGlobals.createFakeNamespaceObject}(${moduleId}, 3)`; - case "default-only": - runtimeRequirements.add(RuntimeGlobals.createFakeNamespaceObject); - return `${RuntimeGlobals.createFakeNamespaceObject}(${moduleId}, 1)`; - case "dynamic": - runtimeRequirements.add(RuntimeGlobals.createFakeNamespaceObject); - return `${RuntimeGlobals.createFakeNamespaceObject}(${moduleId}, 7)`; - } + constructor(verbose = true) { + this._verbose = verbose; } - /** - * @param {Object} options options object - * @param {ChunkGraph} options.chunkGraph the chunk graph - * @param {AsyncDependenciesBlock=} options.block the current dependencies block - * @param {Module} options.module the module - * @param {string} options.request the request that should be printed as comment - * @param {string} options.message a message for the comment - * @param {boolean=} options.strict if the current module is in strict esm mode - * @param {boolean=} options.weak if the dependency is weak (will create a nice error message) - * @param {Set} options.runtimeRequirements if set, will be filled with runtime requirements - * @returns {string} the promise expression + * @param {Compiler} compiler the compiler + * @returns {void} */ - moduleNamespacePromise({ - chunkGraph, - block, - module, - request, - message, - strict, - weak, - runtimeRequirements - }) { - if (!module) { - return this.missingModulePromise({ - request - }); - } - const moduleId = chunkGraph.getModuleId(module); - if (moduleId === null) { - if (weak) { - // only weak referenced modules don't get an id - // we can always emit an error emitting code here - return this.weakError({ - module, - chunkGraph, - request, - type: "promise" - }); - } - throw new Error( - `RuntimeTemplate.moduleNamespacePromise(): ${noModuleIdErrorMessage( + apply(compiler) { + const { _verbose: verbose } = this; + compiler.hooks.compilation.tap("ModuleInfoHeaderPlugin", compilation => { + const hooks = JavascriptModulesPlugin.getCompilationHooks(compilation); + hooks.renderModulePackage.tap( + "ModuleInfoHeaderPlugin", + ( + moduleSource, module, - chunkGraph - )}` - ); - } - const promise = this.blockPromise({ - chunkGraph, - block, - message, - runtimeRequirements - }); - - let appending; - let idExpr = JSON.stringify(chunkGraph.getModuleId(module)); - const comment = this.comment({ - request - }); - let header = ""; - if (weak) { - if (idExpr.length > 8) { - // 'var x="nnnnnn";x,"+x+",x' vs '"nnnnnn",nnnnnn,"nnnnnn"' - header += `var id = ${idExpr}; `; - idExpr = "id"; - } - runtimeRequirements.add(RuntimeGlobals.moduleFactories); - header += `if(!${ - RuntimeGlobals.moduleFactories - }[${idExpr}]) { ${this.weakError({ - module, - chunkGraph, - request, - idExpr, - type: "statements" - })} } `; - } - const moduleIdExpr = this.moduleId({ - module, - chunkGraph, - request, - weak - }); - const exportsType = module.getExportsType(chunkGraph.moduleGraph, strict); - let fakeType = 16; - switch (exportsType) { - case "namespace": - if (header) { - const rawModule = this.moduleRaw({ - module, - chunkGraph, - request, - weak, - runtimeRequirements - }); - appending = `.then(${this.basicFunction( - "", - `${header}return ${rawModule};` - )})`; - } else { - runtimeRequirements.add(RuntimeGlobals.require); - appending = `.then(__webpack_require__.bind(__webpack_require__, ${comment}${idExpr}))`; - } - break; - case "dynamic": - fakeType |= 4; - /* fall through */ - case "default-with-named": - fakeType |= 2; - /* fall through */ - case "default-only": - runtimeRequirements.add(RuntimeGlobals.createFakeNamespaceObject); - if (chunkGraph.moduleGraph.isAsync(module)) { - if (header) { - const rawModule = this.moduleRaw({ + { chunk, chunkGraph, moduleGraph, runtimeTemplate } + ) => { + const { requestShortener } = runtimeTemplate; + let cacheEntry; + let cache = caches.get(requestShortener); + if (cache === undefined) { + caches.set(requestShortener, (cache = new WeakMap())); + cache.set( module, - chunkGraph, - request, - weak, - runtimeRequirements - }); - appending = `.then(${this.basicFunction( - "", - `${header}return ${rawModule};` - )})`; + (cacheEntry = { header: undefined, full: new WeakMap() }) + ); } else { - runtimeRequirements.add(RuntimeGlobals.require); - appending = `.then(__webpack_require__.bind(__webpack_require__, ${comment}${idExpr}))`; + cacheEntry = cache.get(module); + if (cacheEntry === undefined) { + cache.set( + module, + (cacheEntry = { header: undefined, full: new WeakMap() }) + ); + } else if (!verbose) { + const cachedSource = cacheEntry.full.get(moduleSource); + if (cachedSource !== undefined) return cachedSource; + } } - appending += `.then(${this.returningFunction( - `${RuntimeGlobals.createFakeNamespaceObject}(m, ${fakeType})`, - "m" - )})`; - } else { - fakeType |= 1; - if (header) { - const returnExpression = `${RuntimeGlobals.createFakeNamespaceObject}(${moduleIdExpr}, ${fakeType})`; - appending = `.then(${this.basicFunction( - "", - `${header}return ${returnExpression};` - )})`; + const source = new ConcatSource(); + let header = cacheEntry.header; + if (header === undefined) { + const req = module.readableIdentifier(requestShortener); + const reqStr = req.replace(/\*\//g, "*_/"); + const reqStrStar = "*".repeat(reqStr.length); + const headerStr = `/*!****${reqStrStar}****!*\\\n !*** ${reqStr} ***!\n \\****${reqStrStar}****/\n`; + header = new RawSource(headerStr); + cacheEntry.header = header; + } + source.add(header); + if (verbose) { + const exportsType = module.buildMeta.exportsType; + source.add( + Template.toComment( + exportsType + ? `${exportsType} exports` + : "unknown exports (runtime-defined)" + ) + "\n" + ); + if (exportsType) { + const exportsInfo = moduleGraph.getExportsInfo(module); + printExportsInfoToSource( + source, + "", + exportsInfo, + moduleGraph, + requestShortener + ); + } + source.add( + Template.toComment( + `runtime requirements: ${joinIterableWithComma( + chunkGraph.getModuleRuntimeRequirements(module, chunk.runtime) + )}` + ) + "\n" + ); + const optimizationBailout = + moduleGraph.getOptimizationBailout(module); + if (optimizationBailout) { + for (const text of optimizationBailout) { + let code; + if (typeof text === "function") { + code = text(requestShortener); + } else { + code = text; + } + source.add(Template.toComment(`${code}`) + "\n"); + } + } + source.add(moduleSource); + return source; } else { - appending = `.then(${RuntimeGlobals.createFakeNamespaceObject}.bind(__webpack_require__, ${comment}${idExpr}, ${fakeType}))`; + source.add(moduleSource); + const cachedSource = new CachedSource(source); + cacheEntry.full.set(moduleSource, cachedSource); + return cachedSource; } } - break; - } - - return `${promise || "Promise.resolve()"}${appending}`; + ); + hooks.chunkHash.tap("ModuleInfoHeaderPlugin", (chunk, hash) => { + hash.update("ModuleInfoHeaderPlugin"); + hash.update("1"); + }); + }); } +} +module.exports = ModuleInfoHeaderPlugin; - /** - * @param {Object} options options object - * @param {ChunkGraph} options.chunkGraph the chunk graph - * @param {RuntimeSpec=} options.runtime runtime for which this code will be generated - * @param {RuntimeSpec | boolean=} options.runtimeCondition only execute the statement in some runtimes - * @param {Set} options.runtimeRequirements if set, will be filled with runtime requirements - * @returns {string} expression - */ - runtimeConditionExpression({ - chunkGraph, - runtimeCondition, - runtime, - runtimeRequirements - }) { - if (runtimeCondition === undefined) return "true"; - if (typeof runtimeCondition === "boolean") return `${runtimeCondition}`; - /** @type {Set} */ - const positiveRuntimeIds = new Set(); - forEachRuntime(runtimeCondition, runtime => - positiveRuntimeIds.add(`${chunkGraph.getRuntimeId(runtime)}`) - ); - /** @type {Set} */ - const negativeRuntimeIds = new Set(); - forEachRuntime(subtractRuntime(runtime, runtimeCondition), runtime => - negativeRuntimeIds.add(`${chunkGraph.getRuntimeId(runtime)}`) - ); - runtimeRequirements.add(RuntimeGlobals.runtimeId); - return compileBooleanMatcher.fromLists( - Array.from(positiveRuntimeIds), - Array.from(negativeRuntimeIds) - )(RuntimeGlobals.runtimeId); - } +/***/ }), + +/***/ 82908: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ + + + +const WebpackError = __webpack_require__(68422); + +/** @typedef {import("./Dependency").DependencyLocation} DependencyLocation */ +/** @typedef {import("./Module")} Module */ + +const previouslyPolyfilledBuiltinModules = { + assert: "assert/", + buffer: "buffer/", + console: "console-browserify", + constants: "constants-browserify", + crypto: "crypto-browserify", + domain: "domain-browser", + events: "events/", + http: "stream-http", + https: "https-browserify", + os: "os-browserify/browser", + path: "path-browserify", + punycode: "punycode/", + process: "process/browser", + querystring: "querystring-es3", + stream: "stream-browserify", + _stream_duplex: "readable-stream/duplex", + _stream_passthrough: "readable-stream/passthrough", + _stream_readable: "readable-stream/readable", + _stream_transform: "readable-stream/transform", + _stream_writable: "readable-stream/writable", + string_decoder: "string_decoder/", + sys: "util/", + timers: "timers-browserify", + tty: "tty-browserify", + url: "url/", + util: "util/", + vm: "vm-browserify", + zlib: "browserify-zlib" +}; + +class ModuleNotFoundError extends WebpackError { /** - * - * @param {Object} options options object - * @param {boolean=} options.update whether a new variable should be created or the existing one updated - * @param {Module} options.module the module - * @param {ChunkGraph} options.chunkGraph the chunk graph - * @param {string} options.request the request that should be printed as comment - * @param {string} options.importVar name of the import variable - * @param {Module} options.originModule module in which the statement is emitted - * @param {boolean=} options.weak true, if this is a weak dependency - * @param {Set} options.runtimeRequirements if set, will be filled with runtime requirements - * @returns {[string, string]} the import statement and the compat statement + * @param {Module} module module tied to dependency + * @param {Error&any} err error thrown + * @param {DependencyLocation} loc location of dependency */ - importStatement({ - update, - module, - chunkGraph, - request, - importVar, - originModule, - weak, - runtimeRequirements - }) { - if (!module) { - return [ - this.missingModuleStatement({ - request - }), - "" - ]; - } - if (chunkGraph.getModuleId(module) === null) { - if (weak) { - // only weak referenced modules don't get an id - // we can always emit an error emitting code here - return [ - this.weakError({ - module, - chunkGraph, - request, - type: "statements" - }), - "" - ]; + constructor(module, err, loc) { + let message = `Module not found: ${err.toString()}`; + + // TODO remove in webpack 6 + const match = err.message.match(/Can't resolve '([^']+)'/); + if (match) { + const request = match[1]; + const alias = previouslyPolyfilledBuiltinModules[request]; + if (alias) { + const pathIndex = alias.indexOf("/"); + const dependency = pathIndex > 0 ? alias.slice(0, pathIndex) : alias; + message += + "\n\n" + + "BREAKING CHANGE: " + + "webpack < 5 used to include polyfills for node.js core modules by default.\n" + + "This is no longer the case. Verify if you need this module and configure a polyfill for it.\n\n"; + message += + "If you want to include a polyfill, you need to:\n" + + `\t- add a fallback 'resolve.fallback: { "${request}": require.resolve("${alias}") }'\n` + + `\t- install '${dependency}'\n`; + message += + "If you don't want to include a polyfill, you can use an empty module like this:\n" + + `\tresolve.fallback: { "${request}": false }`; } - throw new Error( - `RuntimeTemplate.importStatement(): ${noModuleIdErrorMessage( - module, - chunkGraph - )}` - ); } - const moduleId = this.moduleId({ - module, - chunkGraph, - request, - weak - }); - const optDeclaration = update ? "" : "var "; - const exportsType = module.getExportsType( - chunkGraph.moduleGraph, - originModule.buildMeta.strictHarmonyModule - ); - runtimeRequirements.add(RuntimeGlobals.require); - const importContent = `/* harmony import */ ${optDeclaration}${importVar} = __webpack_require__(${moduleId});\n`; + super(message); - if (exportsType === "dynamic") { - runtimeRequirements.add(RuntimeGlobals.compatGetDefaultExport); - return [ - importContent, - `/* harmony import */ ${optDeclaration}${importVar}_default = /*#__PURE__*/${RuntimeGlobals.compatGetDefaultExport}(${importVar});\n` - ]; - } - return [importContent, ""]; + this.name = "ModuleNotFoundError"; + this.details = err.details; + this.module = module; + this.error = err; + this.loc = loc; } +} + +module.exports = ModuleNotFoundError; + + +/***/ }), + +/***/ 13110: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ + + + +const WebpackError = __webpack_require__(68422); +const makeSerializable = __webpack_require__(26522); + +const WASM_HEADER = Buffer.from([0x00, 0x61, 0x73, 0x6d]); +class ModuleParseError extends WebpackError { /** - * @param {Object} options options - * @param {ModuleGraph} options.moduleGraph the module graph - * @param {Module} options.module the module - * @param {string} options.request the request - * @param {string | string[]} options.exportName the export name - * @param {Module} options.originModule the origin module - * @param {boolean|undefined} options.asiSafe true, if location is safe for ASI, a bracket can be emitted - * @param {boolean} options.isCall true, if expression will be called - * @param {boolean} options.callContext when false, call context will not be preserved - * @param {boolean} options.defaultInterop when true and accessing the default exports, interop code will be generated - * @param {string} options.importVar the identifier name of the import variable - * @param {InitFragment[]} options.initFragments init fragments will be added here - * @param {RuntimeSpec} options.runtime runtime for which this code will be generated - * @param {Set} options.runtimeRequirements if set, will be filled with runtime requirements - * @returns {string} expression + * @param {string | Buffer} source source code + * @param {Error&any} err the parse error + * @param {string[]} loaders the loaders used + * @param {string} type module type */ - exportFromImport({ - moduleGraph, - module, - request, - exportName, - originModule, - asiSafe, - isCall, - callContext, - defaultInterop, - importVar, - initFragments, - runtime, - runtimeRequirements - }) { - if (!module) { - return this.missingModule({ - request - }); - } - if (!Array.isArray(exportName)) { - exportName = exportName ? [exportName] : []; + constructor(source, err, loaders, type) { + let message = "Module parse failed: " + (err && err.message); + let loc = undefined; + + if ( + ((Buffer.isBuffer(source) && source.slice(0, 4).equals(WASM_HEADER)) || + (typeof source === "string" && /^\0asm/.test(source))) && + !type.startsWith("webassembly") + ) { + message += + "\nThe module seem to be a WebAssembly module, but module is not flagged as WebAssembly module for webpack."; + message += + "\nBREAKING CHANGE: Since webpack 5 WebAssembly is not enabled by default and flagged as experimental feature."; + message += + "\nYou need to enable one of the WebAssembly experiments via 'experiments.asyncWebAssembly: true' (based on async modules) or 'experiments.syncWebAssembly: true' (like webpack 4, deprecated)."; + message += + "\nFor files that transpile to WebAssembly, make sure to set the module type in the 'module.rules' section of the config (e. g. 'type: \"webassembly/async\"')."; + } else if (!loaders) { + message += + "\nYou may need an appropriate loader to handle this file type."; + } else if (loaders.length >= 1) { + message += `\nFile was processed with these loaders:${loaders + .map(loader => `\n * ${loader}`) + .join("")}`; + message += + "\nYou may need an additional loader to handle the result of these loaders."; + } else { + message += + "\nYou may need an appropriate loader to handle this file type, currently no loaders are configured to process this file. See https://webpack.js.org/concepts#loaders"; } - const exportsType = module.getExportsType( - moduleGraph, - originModule.buildMeta.strictHarmonyModule - ); - if (defaultInterop) { - if (exportName.length > 0 && exportName[0] === "default") { - switch (exportsType) { - case "dynamic": - if (isCall) { - return `${importVar}_default()${propertyAccess(exportName, 1)}`; - } else { - return asiSafe - ? `(${importVar}_default()${propertyAccess(exportName, 1)})` - : asiSafe === false - ? `;(${importVar}_default()${propertyAccess(exportName, 1)})` - : `${importVar}_default.a${propertyAccess(exportName, 1)}`; - } - case "default-only": - case "default-with-named": - exportName = exportName.slice(1); - break; - } - } else if (exportName.length > 0) { - if (exportsType === "default-only") { - return ( - "/* non-default import from non-esm module */undefined" + - propertyAccess(exportName, 1) - ); - } else if ( - exportsType !== "namespace" && - exportName[0] === "__esModule" - ) { - return "/* __esModule */true"; - } - } else if ( - exportsType === "default-only" || - exportsType === "default-with-named" + if ( + err && + err.loc && + typeof err.loc === "object" && + typeof err.loc.line === "number" + ) { + var lineNumber = err.loc.line; + + if ( + Buffer.isBuffer(source) || + /[\0\u0001\u0002\u0003\u0004\u0005\u0006\u0007]/.test(source) ) { - runtimeRequirements.add(RuntimeGlobals.createFakeNamespaceObject); - initFragments.push( - new InitFragment( - `var ${importVar}_namespace_cache;\n`, - InitFragment.STAGE_CONSTANTS, - -1, - `${importVar}_namespace_cache` - ) - ); - return `/*#__PURE__*/ ${ - asiSafe ? "" : asiSafe === false ? ";" : "Object" - }(${importVar}_namespace_cache || (${importVar}_namespace_cache = ${ - RuntimeGlobals.createFakeNamespaceObject - }(${importVar}${exportsType === "default-only" ? "" : ", 2"})))`; + // binary file + message += "\n(Source code omitted for this binary file)"; + } else { + const sourceLines = source.split(/\r?\n/); + const start = Math.max(0, lineNumber - 3); + const linesBefore = sourceLines.slice(start, lineNumber - 1); + const theLine = sourceLines[lineNumber - 1]; + const linesAfter = sourceLines.slice(lineNumber, lineNumber + 2); + + message += + linesBefore.map(l => `\n| ${l}`).join("") + + `\n> ${theLine}` + + linesAfter.map(l => `\n| ${l}`).join(""); } + + loc = { start: err.loc }; + } else if (err && err.stack) { + message += "\n" + err.stack; } - if (exportName.length > 0) { - const exportsInfo = moduleGraph.getExportsInfo(module); - const used = exportsInfo.getUsedName(exportName, runtime); - if (!used) { - const comment = Template.toNormalComment( - `unused export ${propertyAccess(exportName)}` - ); - return `${comment} undefined`; - } - const comment = equals(used, exportName) - ? "" - : Template.toNormalComment(propertyAccess(exportName)) + " "; - const access = `${importVar}${comment}${propertyAccess(used)}`; - if (isCall && callContext === false) { - return asiSafe - ? `(0,${access})` - : asiSafe === false - ? `;(0,${access})` - : `/*#__PURE__*/Object(${access})`; + super(message); + + this.name = "ModuleParseError"; + this.loc = loc; + this.error = err; + } + + serialize(context) { + const { write } = context; + + write(this.error); + + super.serialize(context); + } + + deserialize(context) { + const { read } = context; + + this.error = read(); + + super.deserialize(context); + } +} + +makeSerializable(ModuleParseError, "webpack/lib/ModuleParseError"); + +module.exports = ModuleParseError; + + +/***/ }), + +/***/ 69631: +/***/ (function(module) { + +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ + + + +class ModuleProfile { + constructor() { + this.startTime = Date.now(); + + this.factoryStartTime = 0; + this.factoryEndTime = 0; + this.factory = 0; + this.factoryParallelismFactor = 0; + + this.restoringStartTime = 0; + this.restoringEndTime = 0; + this.restoring = 0; + this.restoringParallelismFactor = 0; + + this.integrationStartTime = 0; + this.integrationEndTime = 0; + this.integration = 0; + this.integrationParallelismFactor = 0; + + this.buildingStartTime = 0; + this.buildingEndTime = 0; + this.building = 0; + this.buildingParallelismFactor = 0; + + this.storingStartTime = 0; + this.storingEndTime = 0; + this.storing = 0; + this.storingParallelismFactor = 0; + + this.additionalFactoryTimes = undefined; + this.additionalFactories = 0; + this.additionalFactoriesParallelismFactor = 0; + + /** @deprecated */ + this.additionalIntegration = 0; + } + + markFactoryStart() { + this.factoryStartTime = Date.now(); + } + + markFactoryEnd() { + this.factoryEndTime = Date.now(); + this.factory = this.factoryEndTime - this.factoryStartTime; + } + + markRestoringStart() { + this.restoringStartTime = Date.now(); + } + + markRestoringEnd() { + this.restoringEndTime = Date.now(); + this.restoring = this.restoringEndTime - this.restoringStartTime; + } + + markIntegrationStart() { + this.integrationStartTime = Date.now(); + } + + markIntegrationEnd() { + this.integrationEndTime = Date.now(); + this.integration = this.integrationEndTime - this.integrationStartTime; + } + + markBuildingStart() { + this.buildingStartTime = Date.now(); + } + + markBuildingEnd() { + this.buildingEndTime = Date.now(); + this.building = this.buildingEndTime - this.buildingStartTime; + } + + markStoringStart() { + this.storingStartTime = Date.now(); + } + + markStoringEnd() { + this.storingEndTime = Date.now(); + this.storing = this.storingEndTime - this.storingStartTime; + } + + // This depends on timing so we ignore it for coverage + /* istanbul ignore next */ + /** + * Merge this profile into another one + * @param {ModuleProfile} realProfile the profile to merge into + * @returns {void} + */ + mergeInto(realProfile) { + realProfile.additionalFactories = this.factory; + (realProfile.additionalFactoryTimes = + realProfile.additionalFactoryTimes || []).push({ + start: this.factoryStartTime, + end: this.factoryEndTime + }); + } +} + +module.exports = ModuleProfile; + + +/***/ }), + +/***/ 93106: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ + + + +const WebpackError = __webpack_require__(68422); + +/** @typedef {import("./Module")} Module */ + +class ModuleRestoreError extends WebpackError { + /** + * @param {Module} module module tied to dependency + * @param {string | Error} err error thrown + */ + constructor(module, err) { + let message = "Module restore failed: "; + let details = undefined; + if (err !== null && typeof err === "object") { + if (typeof err.stack === "string" && err.stack) { + const stack = err.stack; + message += stack; + } else if (typeof err.message === "string" && err.message) { + message += err.message; + } else { + message += err; } - return access; } else { - return importVar; + message += String(err); } + + super(message); + + this.name = "ModuleRestoreError"; + this.details = details; + this.module = module; + this.error = err; } +} + +module.exports = ModuleRestoreError; + + +/***/ }), + +/***/ 84521: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ + + + +const WebpackError = __webpack_require__(68422); + +/** @typedef {import("./Module")} Module */ + +class ModuleStoreError extends WebpackError { /** - * @param {Object} options options - * @param {AsyncDependenciesBlock} options.block the async block - * @param {string} options.message the message - * @param {ChunkGraph} options.chunkGraph the chunk graph - * @param {Set} options.runtimeRequirements if set, will be filled with runtime requirements - * @returns {string} expression + * @param {Module} module module tied to dependency + * @param {string | Error} err error thrown */ - blockPromise({ block, message, chunkGraph, runtimeRequirements }) { - if (!block) { - const comment = this.comment({ - message - }); - return `Promise.resolve(${comment.trim()})`; - } - const chunkGroup = chunkGraph.getBlockChunkGroup(block); - if (!chunkGroup || chunkGroup.chunks.length === 0) { - const comment = this.comment({ - message - }); - return `Promise.resolve(${comment.trim()})`; - } - const chunks = chunkGroup.chunks.filter( - chunk => !chunk.hasRuntime() && chunk.id !== null - ); - const comment = this.comment({ - message, - chunkName: block.chunkName - }); - if (chunks.length === 1) { - const chunkId = JSON.stringify(chunks[0].id); - runtimeRequirements.add(RuntimeGlobals.ensureChunk); - return `${RuntimeGlobals.ensureChunk}(${comment}${chunkId})`; - } else if (chunks.length > 0) { - runtimeRequirements.add(RuntimeGlobals.ensureChunk); - const requireChunkId = chunk => - `${RuntimeGlobals.ensureChunk}(${JSON.stringify(chunk.id)})`; - return `Promise.all(${comment.trim()}[${chunks - .map(requireChunkId) - .join(", ")}])`; + constructor(module, err) { + let message = "Module storing failed: "; + let details = undefined; + if (err !== null && typeof err === "object") { + if (typeof err.stack === "string" && err.stack) { + const stack = err.stack; + message += stack; + } else if (typeof err.message === "string" && err.message) { + message += err.message; + } else { + message += err; + } } else { - return `Promise.resolve(${comment.trim()})`; + message += String(err); } + + super(message); + + this.name = "ModuleStoreError"; + this.details = details; + this.module = module; + this.error = err; } +} + +module.exports = ModuleStoreError; + + +/***/ }), +/***/ 38256: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ + + + +const util = __webpack_require__(31669); +const memoize = __webpack_require__(84297); + +/** @typedef {import("webpack-sources").Source} Source */ +/** @typedef {import("./Chunk")} Chunk */ +/** @typedef {import("./ChunkGraph")} ChunkGraph */ +/** @typedef {import("./Compilation")} Compilation */ +/** @typedef {import("./DependencyTemplates")} DependencyTemplates */ +/** @typedef {import("./Module")} Module */ +/** @typedef {import("./ModuleGraph")} ModuleGraph */ +/** @typedef {import("./RuntimeTemplate")} RuntimeTemplate */ +/** @typedef {import("./util/Hash")} Hash */ + +const getJavascriptModulesPlugin = memoize(() => + __webpack_require__(76767) +); + +// TODO webpack 6: remove this class +class ModuleTemplate { /** - * @param {Object} options options - * @param {AsyncDependenciesBlock} options.block the async block - * @param {ChunkGraph} options.chunkGraph the chunk graph - * @param {Set} options.runtimeRequirements if set, will be filled with runtime requirements - * @param {string=} options.request request string used originally - * @returns {string} expression + * @param {RuntimeTemplate} runtimeTemplate the runtime template + * @param {Compilation} compilation the compilation */ - asyncModuleFactory({ block, chunkGraph, runtimeRequirements, request }) { - const dep = block.dependencies[0]; - const module = chunkGraph.moduleGraph.getModule(dep); - const ensureChunk = this.blockPromise({ - block, - message: "", - chunkGraph, - runtimeRequirements + constructor(runtimeTemplate, compilation) { + this._runtimeTemplate = runtimeTemplate; + this.type = "javascript"; + this.hooks = Object.freeze({ + content: { + tap: util.deprecate( + (options, fn) => { + getJavascriptModulesPlugin() + .getCompilationHooks(compilation) + .renderModuleContent.tap( + options, + (source, module, renderContext) => + fn( + source, + module, + renderContext, + renderContext.dependencyTemplates + ) + ); + }, + "ModuleTemplate.hooks.content is deprecated (use JavascriptModulesPlugin.getCompilationHooks().renderModuleContent instead)", + "DEP_MODULE_TEMPLATE_CONTENT" + ) + }, + module: { + tap: util.deprecate( + (options, fn) => { + getJavascriptModulesPlugin() + .getCompilationHooks(compilation) + .renderModuleContent.tap( + options, + (source, module, renderContext) => + fn( + source, + module, + renderContext, + renderContext.dependencyTemplates + ) + ); + }, + "ModuleTemplate.hooks.module is deprecated (use JavascriptModulesPlugin.getCompilationHooks().renderModuleContent instead)", + "DEP_MODULE_TEMPLATE_MODULE" + ) + }, + render: { + tap: util.deprecate( + (options, fn) => { + getJavascriptModulesPlugin() + .getCompilationHooks(compilation) + .renderModuleContainer.tap( + options, + (source, module, renderContext) => + fn( + source, + module, + renderContext, + renderContext.dependencyTemplates + ) + ); + }, + "ModuleTemplate.hooks.render is deprecated (use JavascriptModulesPlugin.getCompilationHooks().renderModuleContainer instead)", + "DEP_MODULE_TEMPLATE_RENDER" + ) + }, + package: { + tap: util.deprecate( + (options, fn) => { + getJavascriptModulesPlugin() + .getCompilationHooks(compilation) + .renderModulePackage.tap( + options, + (source, module, renderContext) => + fn( + source, + module, + renderContext, + renderContext.dependencyTemplates + ) + ); + }, + "ModuleTemplate.hooks.package is deprecated (use JavascriptModulesPlugin.getCompilationHooks().renderModulePackage instead)", + "DEP_MODULE_TEMPLATE_PACKAGE" + ) + }, + hash: { + tap: util.deprecate( + (options, fn) => { + compilation.hooks.fullHash.tap(options, fn); + }, + "ModuleTemplate.hooks.hash is deprecated (use Compilation.hooks.fullHash instead)", + "DEP_MODULE_TEMPLATE_HASH" + ) + } }); - const factory = this.returningFunction( - this.moduleRaw({ - module, - chunkGraph, - request, - runtimeRequirements - }) - ); - return this.returningFunction( - ensureChunk.startsWith("Promise.resolve(") - ? `${factory}` - : `${ensureChunk}.then(${this.returningFunction(factory)})` - ); } +} + +Object.defineProperty(ModuleTemplate.prototype, "runtimeTemplate", { + get: util.deprecate( + /** + * @this {ModuleTemplate} + * @returns {TODO} output options + */ + function () { + return this._runtimeTemplate; + }, + "ModuleTemplate.runtimeTemplate is deprecated (use Compilation.runtimeTemplate instead)", + "DEP_WEBPACK_CHUNK_TEMPLATE_OUTPUT_OPTIONS" + ) +}); + +module.exports = ModuleTemplate; + + +/***/ }), + +/***/ 92085: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ + + + +const { cleanUp } = __webpack_require__(22569); +const WebpackError = __webpack_require__(68422); +const makeSerializable = __webpack_require__(26522); +class ModuleWarning extends WebpackError { /** - * @param {Object} options options - * @param {Dependency} options.dependency the dependency - * @param {ChunkGraph} options.chunkGraph the chunk graph - * @param {Set} options.runtimeRequirements if set, will be filled with runtime requirements - * @param {string=} options.request request string used originally - * @returns {string} expression + * @param {Error} warning error thrown + * @param {{from?: string|null}} info additional info */ - syncModuleFactory({ dependency, chunkGraph, runtimeRequirements, request }) { - const module = chunkGraph.moduleGraph.getModule(dependency); - const factory = this.returningFunction( - this.moduleRaw({ - module, - chunkGraph, - request, - runtimeRequirements - }) - ); - return this.returningFunction(factory); + constructor(warning, { from = null } = {}) { + let message = "Module Warning"; + + if (from) { + message += ` (from ${from}):\n`; + } else { + message += ": "; + } + + if (warning && typeof warning === "object" && warning.message) { + message += warning.message; + } else if (warning) { + message += String(warning); + } + + super(message); + + this.name = "ModuleWarning"; + this.warning = warning; + this.details = + warning && typeof warning === "object" && warning.stack + ? cleanUp(warning.stack, this.message) + : undefined; } - /** - * @param {Object} options options - * @param {string} options.exportsArgument the name of the exports object - * @param {Set} options.runtimeRequirements if set, will be filled with runtime requirements - * @returns {string} statement - */ - defineEsModuleFlagStatement({ exportsArgument, runtimeRequirements }) { - runtimeRequirements.add(RuntimeGlobals.makeNamespaceObject); - runtimeRequirements.add(RuntimeGlobals.exports); - return `${RuntimeGlobals.makeNamespaceObject}(${exportsArgument});\n`; + serialize(context) { + const { write } = context; + + write(this.warning); + + super.serialize(context); + } + + deserialize(context) { + const { read } = context; + + this.warning = read(); + + super.deserialize(context); } } -module.exports = RuntimeTemplate; +makeSerializable(ModuleWarning, "webpack/lib/ModuleWarning"); + +module.exports = ModuleWarning; /***/ }), -/***/ 31374: -/***/ (function(module) { +/***/ 73663: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; /* @@ -60018,141 +54652,586 @@ module.exports = RuntimeTemplate; -class SelfModuleFactory { - constructor(moduleGraph) { - this.moduleGraph = moduleGraph; +const asyncLib = __webpack_require__(36386); +const { SyncHook, MultiHook } = __webpack_require__(34718); + +const ConcurrentCompilationError = __webpack_require__(51684); +const MultiStats = __webpack_require__(76396); +const MultiWatching = __webpack_require__(22831); +const ArrayQueue = __webpack_require__(29704); + +/** @template T @typedef {import("tapable").AsyncSeriesHook} AsyncSeriesHook */ +/** @template T @template R @typedef {import("tapable").SyncBailHook} SyncBailHook */ +/** @typedef {import("../declarations/WebpackOptions").WatchOptions} WatchOptions */ +/** @typedef {import("./Compiler")} Compiler */ +/** @typedef {import("./Stats")} Stats */ +/** @typedef {import("./Watching")} Watching */ +/** @typedef {import("./util/fs").InputFileSystem} InputFileSystem */ +/** @typedef {import("./util/fs").IntermediateFileSystem} IntermediateFileSystem */ +/** @typedef {import("./util/fs").OutputFileSystem} OutputFileSystem */ +/** @typedef {import("./util/fs").WatchFileSystem} WatchFileSystem */ + +/** + * @template T + * @callback Callback + * @param {Error=} err + * @param {T=} result + */ + +/** + * @callback RunWithDependenciesHandler + * @param {Compiler} compiler + * @param {Callback} callback + */ + +/** + * @typedef {Object} MultiCompilerOptions + * @property {number=} parallelism how many Compilers are allows to run at the same time in parallel + */ + +module.exports = class MultiCompiler { + /** + * @param {Compiler[] | Record} compilers child compilers + * @param {MultiCompilerOptions} options options + */ + constructor(compilers, options) { + if (!Array.isArray(compilers)) { + compilers = Object.keys(compilers).map(name => { + compilers[name].name = name; + return compilers[name]; + }); + } + + this.hooks = Object.freeze({ + /** @type {SyncHook<[MultiStats]>} */ + done: new SyncHook(["stats"]), + /** @type {MultiHook>} */ + invalid: new MultiHook(compilers.map(c => c.hooks.invalid)), + /** @type {MultiHook>} */ + run: new MultiHook(compilers.map(c => c.hooks.run)), + /** @type {SyncHook<[]>} */ + watchClose: new SyncHook([]), + /** @type {MultiHook>} */ + watchRun: new MultiHook(compilers.map(c => c.hooks.watchRun)), + /** @type {MultiHook>} */ + infrastructureLog: new MultiHook( + compilers.map(c => c.hooks.infrastructureLog) + ) + }); + this.compilers = compilers; + /** @type {MultiCompilerOptions} */ + this._options = { + parallelism: options.parallelism || Infinity + }; + /** @type {WeakMap} */ + this.dependencies = new WeakMap(); + this.running = false; + + /** @type {Stats[]} */ + const compilerStats = this.compilers.map(() => null); + let doneCompilers = 0; + for (let index = 0; index < this.compilers.length; index++) { + const compiler = this.compilers[index]; + const compilerIndex = index; + let compilerDone = false; + compiler.hooks.done.tap("MultiCompiler", stats => { + if (!compilerDone) { + compilerDone = true; + doneCompilers++; + } + compilerStats[compilerIndex] = stats; + if (doneCompilers === this.compilers.length) { + this.hooks.done.call(new MultiStats(compilerStats)); + } + }); + compiler.hooks.invalid.tap("MultiCompiler", () => { + if (compilerDone) { + compilerDone = false; + doneCompilers--; + } + }); + } } - create(data, callback) { - const module = this.moduleGraph.getParentModule(data.dependencies[0]); - callback(null, { - module - }); + get options() { + return Object.assign( + this.compilers.map(c => c.options), + this._options + ); } -} - -module.exports = SelfModuleFactory; - - -/***/ }), - -/***/ 16551: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Sean Larkin @thelarkinn -*/ - + get outputPath() { + let commonPath = this.compilers[0].outputPath; + for (const compiler of this.compilers) { + while ( + compiler.outputPath.indexOf(commonPath) !== 0 && + /[/\\]/.test(commonPath) + ) { + commonPath = commonPath.replace(/[/\\][^/\\]*$/, ""); + } + } -module.exports = __webpack_require__(82430); + if (!commonPath && this.compilers[0].outputPath[0] === "/") return "/"; + return commonPath; + } + get inputFileSystem() { + throw new Error("Cannot read inputFileSystem of a MultiCompiler"); + } -/***/ }), + get outputFileSystem() { + throw new Error("Cannot read outputFileSystem of a MultiCompiler"); + } -/***/ 15979: -/***/ (function(__unused_webpack_module, exports) { + get watchFileSystem() { + throw new Error("Cannot read watchFileSystem of a MultiCompiler"); + } -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Sean Larkin @thelarkinn -*/ + get intermediateFileSystem() { + throw new Error("Cannot read outputFileSystem of a MultiCompiler"); + } + /** + * @param {InputFileSystem} value the new input file system + */ + set inputFileSystem(value) { + for (const compiler of this.compilers) { + compiler.inputFileSystem = value; + } + } + /** + * @param {OutputFileSystem} value the new output file system + */ + set outputFileSystem(value) { + for (const compiler of this.compilers) { + compiler.outputFileSystem = value; + } + } -/** - * @param {number} size the size in bytes - * @returns {string} the formatted size - */ -exports.formatSize = size => { - if (typeof size !== "number" || Number.isNaN(size) === true) { - return "unknown size"; + /** + * @param {WatchFileSystem} value the new watch file system + */ + set watchFileSystem(value) { + for (const compiler of this.compilers) { + compiler.watchFileSystem = value; + } } - if (size <= 0) { - return "0 bytes"; + /** + * @param {IntermediateFileSystem} value the new intermediate file system + */ + set intermediateFileSystem(value) { + for (const compiler of this.compilers) { + compiler.intermediateFileSystem = value; + } } - const abbreviations = ["bytes", "KiB", "MiB", "GiB"]; - const index = Math.floor(Math.log(size) / Math.log(1024)); + getInfrastructureLogger(name) { + return this.compilers[0].getInfrastructureLogger(name); + } - return `${+(size / Math.pow(1024, index)).toPrecision(3)} ${ - abbreviations[index] - }`; -}; + /** + * @param {Compiler} compiler the child compiler + * @param {string[]} dependencies its dependencies + * @returns {void} + */ + setDependencies(compiler, dependencies) { + this.dependencies.set(compiler, dependencies); + } + /** + * @param {Callback} callback signals when the validation is complete + * @returns {boolean} true if the dependencies are valid + */ + validateDependencies(callback) { + /** @type {Set<{source: Compiler, target: Compiler}>} */ + const edges = new Set(); + /** @type {string[]} */ + const missing = []; + const targetFound = compiler => { + for (const edge of edges) { + if (edge.target === compiler) { + return true; + } + } + return false; + }; + const sortEdges = (e1, e2) => { + return ( + e1.source.name.localeCompare(e2.source.name) || + e1.target.name.localeCompare(e2.target.name) + ); + }; + for (const source of this.compilers) { + const dependencies = this.dependencies.get(source); + if (dependencies) { + for (const dep of dependencies) { + const target = this.compilers.find(c => c.name === dep); + if (!target) { + missing.push(dep); + } else { + edges.add({ + source, + target + }); + } + } + } + } + /** @type {string[]} */ + const errors = missing.map(m => `Compiler dependency \`${m}\` not found.`); + const stack = this.compilers.filter(c => !targetFound(c)); + while (stack.length > 0) { + const current = stack.pop(); + for (const edge of edges) { + if (edge.source === current) { + edges.delete(edge); + const target = edge.target; + if (!targetFound(target)) { + stack.push(target); + } + } + } + } + if (edges.size > 0) { + /** @type {string[]} */ + const lines = Array.from(edges) + .sort(sortEdges) + .map(edge => `${edge.source.name} -> ${edge.target.name}`); + lines.unshift("Circular dependency found in compiler dependencies."); + errors.unshift(lines.join("\n")); + } + if (errors.length > 0) { + const message = errors.join("\n"); + callback(new Error(message)); + return false; + } + return true; + } -/***/ }), + // TODO webpack 6 remove + /** + * @deprecated This method should have been private + * @param {Compiler[]} compilers the child compilers + * @param {RunWithDependenciesHandler} fn a handler to run for each compiler + * @param {Callback} callback the compiler's handler + * @returns {void} + */ + runWithDependencies(compilers, fn, callback) { + const fulfilledNames = new Set(); + let remainingCompilers = compilers; + const isDependencyFulfilled = d => fulfilledNames.has(d); + const getReadyCompilers = () => { + let readyCompilers = []; + let list = remainingCompilers; + remainingCompilers = []; + for (const c of list) { + const dependencies = this.dependencies.get(c); + const ready = + !dependencies || dependencies.every(isDependencyFulfilled); + if (ready) { + readyCompilers.push(c); + } else { + remainingCompilers.push(c); + } + } + return readyCompilers; + }; + const runCompilers = callback => { + if (remainingCompilers.length === 0) return callback(); + asyncLib.map( + getReadyCompilers(), + (compiler, callback) => { + fn(compiler, err => { + if (err) return callback(err); + fulfilledNames.add(compiler.name); + runCompilers(callback); + }); + }, + callback + ); + }; + runCompilers(callback); + } -/***/ 37661: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + /** + * @template SetupResult + * @param {function(Compiler, number, Callback, function(): boolean, function(): void, function(): void): SetupResult} setup setup a single compiler + * @param {function(Compiler, SetupResult, Callback): void} run run/continue a single compiler + * @param {Callback} callback callback when all compilers are done, result includes Stats of all changed compilers + * @returns {SetupResult[]} result of setup + */ + _runGraph(setup, run, callback) { + /** @typedef {{ compiler: Compiler, setupResult: SetupResult, result: Stats, state: "pending" | "blocked" | "queued" | "starting" | "running" | "running-outdated" | "done", children: Node[], parents: Node[] }} Node */ -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ + // State transitions for nodes: + // -> blocked (initial) + // blocked -> starting [running++] (when all parents done) + // queued -> starting [running++] (when processing the queue) + // starting -> running (when run has been called) + // running -> done [running--] (when compilation is done) + // done -> pending (when invalidated from file change) + // pending -> blocked [add to queue] (when invalidated from aggregated changes) + // done -> blocked [add to queue] (when invalidated, from parent invalidation) + // running -> running-outdated (when invalidated, either from change or parent invalidation) + // running-outdated -> blocked [running--] (when compilation is done) + /** @type {Node[]} */ + const nodes = this.compilers.map(compiler => ({ + compiler, + setupResult: undefined, + result: undefined, + state: "blocked", + children: [], + parents: [] + })); + /** @type {Map} */ + const compilerToNode = new Map(); + for (const node of nodes) compilerToNode.set(node.compiler.name, node); + for (const node of nodes) { + const dependencies = this.dependencies.get(node.compiler); + if (!dependencies) continue; + for (const dep of dependencies) { + const parent = compilerToNode.get(dep); + node.parents.push(parent); + parent.children.push(node); + } + } + /** @type {ArrayQueue} */ + const queue = new ArrayQueue(); + for (const node of nodes) { + if (node.parents.length === 0) { + node.state = "queued"; + queue.enqueue(node); + } + } + let errored = false; + let running = 0; + const parallelism = this._options.parallelism; + /** + * @param {Node} node node + * @param {Error=} err error + * @param {Stats=} stats result + * @returns {void} + */ + const nodeDone = (node, err, stats) => { + if (errored) return; + if (err) { + errored = true; + return asyncLib.each( + nodes, + (node, callback) => { + if (node.compiler.watching) { + node.compiler.watching.close(callback); + } else { + callback(); + } + }, + () => callback(err) + ); + } + node.result = stats; + running--; + if (node.state === "running") { + node.state = "done"; + for (const child of node.children) { + if (child.state === "blocked") queue.enqueue(child); + } + } else if (node.state === "running-outdated") { + node.state = "blocked"; + queue.enqueue(node); + } + processQueue(); + }; + /** + * @param {Node} node node + * @returns {void} + */ + const nodeInvalidFromParent = node => { + if (node.state === "done") { + node.state = "blocked"; + } else if (node.state === "running") { + node.state = "running-outdated"; + } + for (const child of node.children) { + nodeInvalidFromParent(child); + } + }; + /** + * @param {Node} node node + * @returns {void} + */ + const nodeInvalid = node => { + if (node.state === "done") { + node.state = "pending"; + } else if (node.state === "running") { + node.state = "running-outdated"; + } + for (const child of node.children) { + nodeInvalidFromParent(child); + } + }; + /** + * @param {Node} node node + * @returns {void} + */ + const nodeChange = node => { + nodeInvalid(node); + if (node.state === "pending") { + node.state = "blocked"; + } + if (node.state === "blocked") { + queue.enqueue(node); + processQueue(); + } + }; + const setupResults = []; + nodes.forEach((node, i) => { + setupResults.push( + (node.setupResult = setup( + node.compiler, + i, + nodeDone.bind(null, node), + () => node.state !== "starting" && node.state !== "running", + () => nodeChange(node), + () => nodeInvalid(node) + )) + ); + }); + let processing = true; + const processQueue = () => { + if (processing) return; + processing = true; + process.nextTick(processQueueWorker); + }; + const processQueueWorker = () => { + while (running < parallelism && queue.length > 0 && !errored) { + const node = queue.dequeue(); + if ( + node.state === "queued" || + (node.state === "blocked" && + node.parents.every(p => p.state === "done")) + ) { + running++; + node.state = "starting"; + run(node.compiler, node.setupResult, nodeDone.bind(null, node)); + node.state = "running"; + } + } + processing = false; + if ( + !errored && + running === 0 && + nodes.every(node => node.state === "done") + ) { + const stats = []; + for (const node of nodes) { + const result = node.result; + if (result) { + node.result = undefined; + stats.push(result); + } + } + if (stats.length > 0) { + callback(null, new MultiStats(stats)); + } + } + }; + processQueueWorker(); + return setupResults; + } -const JavascriptModulesPlugin = __webpack_require__(76767); + /** + * @param {WatchOptions|WatchOptions[]} watchOptions the watcher's options + * @param {Callback} handler signals when the call finishes + * @returns {MultiWatching} a compiler watcher + */ + watch(watchOptions, handler) { + if (this.running) { + return handler(new ConcurrentCompilationError()); + } + this.running = true; -/** @typedef {import("./Compilation")} Compilation */ + if (this.validateDependencies(handler)) { + const watchings = this._runGraph( + (compiler, idx, callback, isBlocked, setChanged, setInvalid) => { + const watching = compiler.watch( + Array.isArray(watchOptions) ? watchOptions[idx] : watchOptions, + callback + ); + if (watching) { + watching._onInvalid = setInvalid; + watching._onChange = setChanged; + watching._isBlocked = isBlocked; + } + return watching; + }, + (compiler, watching, callback) => { + if (compiler.watching !== watching) return; + if (!watching.running) watching.invalidate(); + }, + handler + ); + return new MultiWatching(watchings, this); + } -class SourceMapDevToolModuleOptionsPlugin { - constructor(options) { - this.options = options; + return new MultiWatching([], this); } /** - * @param {Compilation} compilation the compiler instance + * @param {Callback} callback signals when the call finishes * @returns {void} */ - apply(compilation) { - const options = this.options; - if (options.module !== false) { - compilation.hooks.buildModule.tap( - "SourceMapDevToolModuleOptionsPlugin", - module => { - module.useSourceMap = true; - } - ); - compilation.hooks.runtimeModule.tap( - "SourceMapDevToolModuleOptionsPlugin", - module => { - module.useSourceMap = true; - } - ); - } else { - compilation.hooks.buildModule.tap( - "SourceMapDevToolModuleOptionsPlugin", - module => { - module.useSimpleSourceMap = true; - } - ); - compilation.hooks.runtimeModule.tap( - "SourceMapDevToolModuleOptionsPlugin", - module => { - module.useSimpleSourceMap = true; + run(callback) { + if (this.running) { + return callback(new ConcurrentCompilationError()); + } + this.running = true; + + if (this.validateDependencies(callback)) { + this._runGraph( + () => {}, + (compiler, setupResult, callback) => compiler.run(callback), + (err, stats) => { + this.running = false; + + if (callback !== undefined) { + return callback(err, stats); + } } ); } - JavascriptModulesPlugin.getCompilationHooks(compilation).useSourceMap.tap( - "SourceMapDevToolModuleOptionsPlugin", - () => true - ); } -} -module.exports = SourceMapDevToolModuleOptionsPlugin; + purgeInputFileSystem() { + for (const compiler of this.compilers) { + if (compiler.inputFileSystem && compiler.inputFileSystem.purge) { + compiler.inputFileSystem.purge(); + } + } + } + + /** + * @param {Callback} callback signals when the compiler closes + * @returns {void} + */ + close(callback) { + asyncLib.each( + this.compilers, + (compiler, callback) => { + compiler.close(callback); + }, + callback + ); + } +}; /***/ }), -/***/ 79917: +/***/ 76396: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; @@ -60163,564 +55242,255 @@ module.exports = SourceMapDevToolModuleOptionsPlugin; -const asyncLib = __webpack_require__(36386); -const { ConcatSource, RawSource } = __webpack_require__(96192); -const Compilation = __webpack_require__(59622); -const ModuleFilenameHelpers = __webpack_require__(80295); -const ProgressPlugin = __webpack_require__(41306); -const SourceMapDevToolModuleOptionsPlugin = __webpack_require__(37661); -const createSchemaValidation = __webpack_require__(77695); -const createHash = __webpack_require__(24123); -const { relative, dirname } = __webpack_require__(93204); -const { makePathsAbsolute } = __webpack_require__(96236); - -/** @typedef {import("webpack-sources").MapOptions} MapOptions */ -/** @typedef {import("webpack-sources").Source} Source */ -/** @typedef {import("../declarations/plugins/SourceMapDevToolPlugin").SourceMapDevToolPluginOptions} SourceMapDevToolPluginOptions */ -/** @typedef {import("./Cache").Etag} Etag */ -/** @typedef {import("./CacheFacade").ItemCacheFacade} ItemCacheFacade */ -/** @typedef {import("./Chunk")} Chunk */ -/** @typedef {import("./Compilation").AssetInfo} AssetInfo */ -/** @typedef {import("./Compiler")} Compiler */ -/** @typedef {import("./Module")} Module */ -/** @typedef {import("./NormalModule").SourceMap} SourceMap */ -/** @typedef {import("./util/Hash")} Hash */ +const identifierUtils = __webpack_require__(96236); -const validate = createSchemaValidation( - __webpack_require__(27084), - () => __webpack_require__(95228), - { - name: "SourceMap DevTool Plugin", - baseDataPath: "options" - } -); -/** - * @typedef {object} SourceMapTask - * @property {Source} asset - * @property {AssetInfo} assetInfo - * @property {(string | Module)[]} modules - * @property {string} source - * @property {string} file - * @property {SourceMap} sourceMap - * @property {ItemCacheFacade} cacheItem cache item - */ +/** @typedef {import("../declarations/WebpackOptions").StatsOptions} StatsOptions */ +/** @typedef {import("./Stats")} Stats */ +/** @typedef {import("./stats/DefaultStatsFactoryPlugin").KnownStatsCompilation} KnownStatsCompilation */ +/** @typedef {import("./stats/DefaultStatsFactoryPlugin").StatsCompilation} StatsCompilation */ -/** - * Escapes regular expression metacharacters - * @param {string} str String to quote - * @returns {string} Escaped string - */ -const quoteMeta = str => { - return str.replace(/[-[\]\\/{}()*+?.^$|]/g, "\\$&"); +const indent = (str, prefix) => { + const rem = str.replace(/\n([^\n])/g, "\n" + prefix + "$1"); + return prefix + rem; }; -/** - * Creating {@link SourceMapTask} for given file - * @param {string} file current compiled file - * @param {Source} asset the asset - * @param {AssetInfo} assetInfo the asset info - * @param {MapOptions} options source map options - * @param {Compilation} compilation compilation instance - * @param {ItemCacheFacade} cacheItem cache item - * @returns {SourceMapTask | undefined} created task instance or `undefined` - */ -const getTaskForFile = ( - file, - asset, - assetInfo, - options, - compilation, - cacheItem -) => { - let source; - /** @type {SourceMap} */ - let sourceMap; +class MultiStats { /** - * Check if asset can build source map + * @param {Stats[]} stats the child stats */ - if (asset.sourceAndMap) { - const sourceAndMap = asset.sourceAndMap(options); - sourceMap = /** @type {SourceMap} */ (sourceAndMap.map); - source = sourceAndMap.source; - } else { - sourceMap = /** @type {SourceMap} */ (asset.map(options)); - source = asset.source(); + constructor(stats) { + this.stats = stats; } - if (!sourceMap || typeof source !== "string") return; - const context = compilation.options.context; - const root = compilation.compiler.root; - const cachedAbsolutify = makePathsAbsolute.bindContextCache(context, root); - const modules = sourceMap.sources.map(source => { - if (!source.startsWith("webpack://")) return source; - source = cachedAbsolutify(source.slice(10)); - const module = compilation.findModule(source); - return module || source; - }); - return { - file, - asset, - source, - assetInfo, - sourceMap, - modules, - cacheItem - }; -}; + get hash() { + return this.stats.map(stat => stat.hash).join(""); + } -class SourceMapDevToolPlugin { /** - * @param {SourceMapDevToolPluginOptions} [options] options object - * @throws {Error} throws error, if got more than 1 arguments + * @returns {boolean} true if a child compilation encountered an error */ - constructor(options = {}) { - validate(options); - - /** @type {string | false} */ - this.sourceMapFilename = options.filename; - /** @type {string | false} */ - this.sourceMappingURLComment = - options.append === false - ? false - : options.append || "\n//# source" + "MappingURL=[url]"; - /** @type {string | Function} */ - this.moduleFilenameTemplate = - options.moduleFilenameTemplate || "webpack://[namespace]/[resourcePath]"; - /** @type {string | Function} */ - this.fallbackModuleFilenameTemplate = - options.fallbackModuleFilenameTemplate || - "webpack://[namespace]/[resourcePath]?[hash]"; - /** @type {string} */ - this.namespace = options.namespace || ""; - /** @type {SourceMapDevToolPluginOptions} */ - this.options = options; + hasErrors() { + return this.stats.some(stat => stat.hasErrors()); } /** - * Apply the plugin - * @param {Compiler} compiler compiler instance - * @returns {void} + * @returns {boolean} true if a child compilation had a warning */ - apply(compiler) { - const outputFs = compiler.outputFileSystem; - const sourceMapFilename = this.sourceMapFilename; - const sourceMappingURLComment = this.sourceMappingURLComment; - const moduleFilenameTemplate = this.moduleFilenameTemplate; - const namespace = this.namespace; - const fallbackModuleFilenameTemplate = this.fallbackModuleFilenameTemplate; - const requestShortener = compiler.requestShortener; - const options = this.options; - options.test = options.test || /\.((c|m)?js|css)($|\?)/i; - - const matchObject = ModuleFilenameHelpers.matchObject.bind( - undefined, - options - ); - - compiler.hooks.compilation.tap("SourceMapDevToolPlugin", compilation => { - new SourceMapDevToolModuleOptionsPlugin(options).apply(compilation); + hasWarnings() { + return this.stats.some(stat => stat.hasWarnings()); + } - compilation.hooks.processAssets.tapAsync( + _createChildOptions(options, context) { + if (!options) { + options = {}; + } + const { children: childrenOptions = undefined, ...baseOptions } = + typeof options === "string" ? { preset: options } : options; + const children = this.stats.map((stat, idx) => { + const childOptions = Array.isArray(childrenOptions) + ? childrenOptions[idx] + : childrenOptions; + return stat.compilation.createStatsOptions( { - name: "SourceMapDevToolPlugin", - stage: Compilation.PROCESS_ASSETS_STAGE_DEV_TOOLING, - additionalAssets: true + ...baseOptions, + ...(typeof childOptions === "string" + ? { preset: childOptions } + : childOptions && typeof childOptions === "object" + ? childOptions + : undefined) }, - (assets, callback) => { - const chunkGraph = compilation.chunkGraph; - const cache = compilation.getCache("SourceMapDevToolPlugin"); - /** @type {Map} */ - const moduleToSourceNameMapping = new Map(); - /** - * @type {Function} - * @returns {void} - */ - const reportProgress = - ProgressPlugin.getReporter(compilation.compiler) || (() => {}); - - /** @type {Map} */ - const fileToChunk = new Map(); - for (const chunk of compilation.chunks) { - for (const file of chunk.files) { - fileToChunk.set(file, chunk); - } - for (const file of chunk.auxiliaryFiles) { - fileToChunk.set(file, chunk); - } - } - - /** @type {string[]} */ - const files = []; - for (const file of Object.keys(assets)) { - if (matchObject(file)) { - files.push(file); - } - } - - reportProgress(0.0); - /** @type {SourceMapTask[]} */ - const tasks = []; - let fileIndex = 0; - - asyncLib.each( - files, - (file, callback) => { - const asset = compilation.getAsset(file); - if (asset.info.related && asset.info.related.sourceMap) { - fileIndex++; - return callback(); - } - const cacheItem = cache.getItemCache( - file, - cache.mergeEtags( - cache.getLazyHashedEtag(asset.source), - namespace - ) - ); - - cacheItem.get((err, cacheEntry) => { - if (err) { - return callback(err); - } - /** - * If presented in cache, reassigns assets. Cache assets already have source maps. - */ - if (cacheEntry) { - const { assets, assetsInfo } = cacheEntry; - for (const cachedFile of Object.keys(assets)) { - if (cachedFile === file) { - compilation.updateAsset( - cachedFile, - assets[cachedFile], - assetsInfo[cachedFile] - ); - } else { - compilation.emitAsset( - cachedFile, - assets[cachedFile], - assetsInfo[cachedFile] - ); - } - /** - * Add file to chunk, if not presented there - */ - if (cachedFile !== file) { - const chunk = fileToChunk.get(file); - if (chunk !== undefined) - chunk.auxiliaryFiles.add(cachedFile); - } - } - - reportProgress( - (0.5 * ++fileIndex) / files.length, - file, - "restored cached SourceMap" - ); - - return callback(); - } - - reportProgress( - (0.5 * fileIndex) / files.length, - file, - "generate SourceMap" - ); - - /** @type {SourceMapTask | undefined} */ - const task = getTaskForFile( - file, - asset.source, - asset.info, - { - module: options.module, - columns: options.columns - }, - compilation, - cacheItem - ); - - if (task) { - const modules = task.modules; - - for (let idx = 0; idx < modules.length; idx++) { - const module = modules[idx]; - if (!moduleToSourceNameMapping.get(module)) { - moduleToSourceNameMapping.set( - module, - ModuleFilenameHelpers.createFilename( - module, - { - moduleFilenameTemplate: moduleFilenameTemplate, - namespace: namespace - }, - { - requestShortener, - chunkGraph, - hashFunction: compilation.outputOptions.hashFunction - } - ) - ); - } - } - - tasks.push(task); - } + context + ); + }); + return { + version: children.every(o => o.version), + hash: children.every(o => o.hash), + errorsCount: children.every(o => o.errorsCount), + warningsCount: children.every(o => o.warningsCount), + errors: children.every(o => o.errors), + warnings: children.every(o => o.warnings), + children + }; + } - reportProgress( - (0.5 * ++fileIndex) / files.length, - file, - "generated SourceMap" - ); + /** + * @param {any} options stats options + * @returns {StatsCompilation} json output + */ + toJson(options) { + options = this._createChildOptions(options, { forToString: false }); + /** @type {KnownStatsCompilation} */ + const obj = {}; + obj.children = this.stats.map((stat, idx) => { + const obj = stat.toJson(options.children[idx]); + const compilationName = stat.compilation.name; + const name = + compilationName && + identifierUtils.makePathsRelative( + options.context, + compilationName, + stat.compilation.compiler.root + ); + obj.name = name; + return obj; + }); + if (options.version) { + obj.version = obj.children[0].version; + } + if (options.hash) { + obj.hash = obj.children.map(j => j.hash).join(""); + } + const mapError = (j, obj) => { + return { + ...obj, + compilerPath: obj.compilerPath + ? `${j.name}.${obj.compilerPath}` + : j.name + }; + }; + if (options.errors) { + obj.errors = []; + for (const j of obj.children) { + for (const i of j.errors) { + obj.errors.push(mapError(j, i)); + } + } + } + if (options.warnings) { + obj.warnings = []; + for (const j of obj.children) { + for (const i of j.warnings) { + obj.warnings.push(mapError(j, i)); + } + } + } + if (options.errorsCount) { + obj.errorsCount = 0; + for (const j of obj.children) { + obj.errorsCount += j.errorsCount; + } + } + if (options.warningsCount) { + obj.warningsCount = 0; + for (const j of obj.children) { + obj.warningsCount += j.warningsCount; + } + } + return obj; + } - callback(); - }); - }, - err => { - if (err) { - return callback(err); - } + toString(options) { + options = this._createChildOptions(options, { forToString: true }); + const results = this.stats.map((stat, idx) => { + const str = stat.toString(options.children[idx]); + const compilationName = stat.compilation.name; + const name = + compilationName && + identifierUtils + .makePathsRelative( + options.context, + compilationName, + stat.compilation.compiler.root + ) + .replace(/\|/g, " "); + if (!str) return str; + return name ? `${name}:\n${indent(str, " ")}` : str; + }); + return results.filter(Boolean).join("\n\n"); + } +} - reportProgress(0.5, "resolve sources"); - /** @type {Set} */ - const usedNamesSet = new Set(moduleToSourceNameMapping.values()); - /** @type {Set} */ - const conflictDetectionSet = new Set(); +module.exports = MultiStats; - /** - * all modules in defined order (longest identifier first) - * @type {Array} - */ - const allModules = Array.from( - moduleToSourceNameMapping.keys() - ).sort((a, b) => { - const ai = typeof a === "string" ? a : a.identifier(); - const bi = typeof b === "string" ? b : b.identifier(); - return ai.length - bi.length; - }); - // find modules with conflicting source names - for (let idx = 0; idx < allModules.length; idx++) { - const module = allModules[idx]; - let sourceName = moduleToSourceNameMapping.get(module); - let hasName = conflictDetectionSet.has(sourceName); - if (!hasName) { - conflictDetectionSet.add(sourceName); - continue; - } +/***/ }), - // try the fallback name first - sourceName = ModuleFilenameHelpers.createFilename( - module, - { - moduleFilenameTemplate: fallbackModuleFilenameTemplate, - namespace: namespace - }, - { - requestShortener, - chunkGraph, - hashFunction: compilation.outputOptions.hashFunction - } - ); - hasName = usedNamesSet.has(sourceName); - if (!hasName) { - moduleToSourceNameMapping.set(module, sourceName); - usedNamesSet.add(sourceName); - continue; - } +/***/ 22831: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - // otherwise just append stars until we have a valid name - while (hasName) { - sourceName += "*"; - hasName = usedNamesSet.has(sourceName); - } - moduleToSourceNameMapping.set(module, sourceName); - usedNamesSet.add(sourceName); - } +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ - let taskIndex = 0; - asyncLib.each( - tasks, - (task, callback) => { - const assets = Object.create(null); - const assetsInfo = Object.create(null); - const file = task.file; - const chunk = fileToChunk.get(file); - const sourceMap = task.sourceMap; - const source = task.source; - const modules = task.modules; - reportProgress( - 0.5 + (0.5 * taskIndex) / tasks.length, - file, - "attach SourceMap" - ); +const asyncLib = __webpack_require__(36386); - const moduleFilenames = modules.map(m => - moduleToSourceNameMapping.get(m) - ); - sourceMap.sources = moduleFilenames; - if (options.noSources) { - sourceMap.sourcesContent = undefined; - } - sourceMap.sourceRoot = options.sourceRoot || ""; - sourceMap.file = file; - const usesContentHash = - sourceMapFilename && - /\[contenthash(:\w+)?\]/.test(sourceMapFilename); +/** @typedef {import("./MultiCompiler")} MultiCompiler */ +/** @typedef {import("./Watching")} Watching */ - // If SourceMap and asset uses contenthash, avoid a circular dependency by hiding hash in `file` - if (usesContentHash && task.assetInfo.contenthash) { - const contenthash = task.assetInfo.contenthash; - let pattern; - if (Array.isArray(contenthash)) { - pattern = contenthash.map(quoteMeta).join("|"); - } else { - pattern = quoteMeta(contenthash); - } - sourceMap.file = sourceMap.file.replace( - new RegExp(pattern, "g"), - m => "x".repeat(m.length) - ); - } +/** + * @template T + * @callback Callback + * @param {Error=} err + * @param {T=} result + */ - /** @type {string | false} */ - let currentSourceMappingURLComment = sourceMappingURLComment; - if ( - currentSourceMappingURLComment !== false && - /\.css($|\?)/i.test(file) - ) { - currentSourceMappingURLComment = - currentSourceMappingURLComment.replace( - /^\n\/\/(.*)$/, - "\n/*$1*/" - ); - } - const sourceMapString = JSON.stringify(sourceMap); - if (sourceMapFilename) { - let filename = file; - const sourceMapContentHash = - usesContentHash && - /** @type {string} */ ( - createHash(compilation.outputOptions.hashFunction) - .update(sourceMapString) - .digest("hex") - ); - const pathParams = { - chunk, - filename: options.fileContext - ? relative( - outputFs, - `/${options.fileContext}`, - `/${filename}` - ) - : filename, - contentHash: sourceMapContentHash - }; - const { path: sourceMapFile, info: sourceMapInfo } = - compilation.getPathWithInfo( - sourceMapFilename, - pathParams - ); - const sourceMapUrl = options.publicPath - ? options.publicPath + sourceMapFile - : relative( - outputFs, - dirname(outputFs, `/${file}`), - `/${sourceMapFile}` - ); - /** @type {Source} */ - let asset = new RawSource(source); - if (currentSourceMappingURLComment !== false) { - // Add source map url to compilation asset, if currentSourceMappingURLComment is set - asset = new ConcatSource( - asset, - compilation.getPath( - currentSourceMappingURLComment, - Object.assign({ url: sourceMapUrl }, pathParams) - ) - ); - } - const assetInfo = { - related: { sourceMap: sourceMapFile } - }; - assets[file] = asset; - assetsInfo[file] = assetInfo; - compilation.updateAsset(file, asset, assetInfo); - // Add source map file to compilation assets and chunk files - const sourceMapAsset = new RawSource(sourceMapString); - const sourceMapAssetInfo = { - ...sourceMapInfo, - development: true - }; - assets[sourceMapFile] = sourceMapAsset; - assetsInfo[sourceMapFile] = sourceMapAssetInfo; - compilation.emitAsset( - sourceMapFile, - sourceMapAsset, - sourceMapAssetInfo - ); - if (chunk !== undefined) - chunk.auxiliaryFiles.add(sourceMapFile); - } else { - if (currentSourceMappingURLComment === false) { - throw new Error( - "SourceMapDevToolPlugin: append can't be false when no filename is provided" - ); - } - /** - * Add source map as data url to asset - */ - const asset = new ConcatSource( - new RawSource(source), - currentSourceMappingURLComment - .replace(/\[map\]/g, () => sourceMapString) - .replace( - /\[url\]/g, - () => - `data:application/json;charset=utf-8;base64,${Buffer.from( - sourceMapString, - "utf-8" - ).toString("base64")}` - ) - ); - assets[file] = asset; - assetsInfo[file] = undefined; - compilation.updateAsset(file, asset); - } +class MultiWatching { + /** + * @param {Watching[]} watchings child compilers' watchers + * @param {MultiCompiler} compiler the compiler + */ + constructor(watchings, compiler) { + this.watchings = watchings; + this.compiler = compiler; + } - task.cacheItem.store({ assets, assetsInfo }, err => { - reportProgress( - 0.5 + (0.5 * ++taskIndex) / tasks.length, - task.file, - "attached SourceMap" - ); + invalidate(callback) { + if (callback) { + asyncLib.each( + this.watchings, + (watching, callback) => watching.invalidate(callback), + callback + ); + } else { + for (const watching of this.watchings) { + watching.invalidate(); + } + } + } - if (err) { - return callback(err); - } - callback(); - }); - }, - err => { - reportProgress(1.0); - callback(err); - } - ); - } - ); + suspend() { + for (const watching of this.watchings) { + watching.suspend(); + } + } + + resume() { + for (const watching of this.watchings) { + watching.resume(); + } + } + + /** + * @param {Callback} callback signals when the watcher is closed + * @returns {void} + */ + close(callback) { + asyncLib.forEach( + this.watchings, + (watching, finishedCallback) => { + watching.close(finishedCallback); + }, + err => { + this.compiler.hooks.watchClose.call(); + if (typeof callback === "function") { + this.compiler.running = false; + callback(err); } - ); - }); + } + ); } } -module.exports = SourceMapDevToolPlugin; +module.exports = MultiWatching; /***/ }), -/***/ 87797: +/***/ 70760: /***/ (function(module) { "use strict"; @@ -60731,88 +55501,288 @@ module.exports = SourceMapDevToolPlugin; -/** @typedef {import("../declarations/WebpackOptions").StatsOptions} StatsOptions */ -/** @typedef {import("./Compilation")} Compilation */ -/** @typedef {import("./stats/DefaultStatsFactoryPlugin").StatsCompilation} StatsCompilation */ +/** @typedef {import("./Compiler")} Compiler */ -class Stats { +class NoEmitOnErrorsPlugin { /** - * @param {Compilation} compilation webpack compilation + * Apply the plugin + * @param {Compiler} compiler the compiler instance + * @returns {void} */ - constructor(compilation) { - this.compilation = compilation; + apply(compiler) { + compiler.hooks.shouldEmit.tap("NoEmitOnErrorsPlugin", compilation => { + if (compilation.getStats().hasErrors()) return false; + }); + compiler.hooks.compilation.tap("NoEmitOnErrorsPlugin", compilation => { + compilation.hooks.shouldRecord.tap("NoEmitOnErrorsPlugin", () => { + if (compilation.getStats().hasErrors()) return false; + }); + }); } +} - get hash() { - return this.compilation.hash; - } +module.exports = NoEmitOnErrorsPlugin; - get startTime() { - return this.compilation.startTime; - } - get endTime() { - return this.compilation.endTime; +/***/ }), + +/***/ 84991: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ + + + +const WebpackError = __webpack_require__(68422); + +module.exports = class NoModeWarning extends WebpackError { + constructor() { + super(); + + this.name = "NoModeWarning"; + this.message = + "configuration\n" + + "The 'mode' option has not been set, webpack will fallback to 'production' for this value.\n" + + "Set 'mode' option to 'development' or 'production' to enable defaults for each environment.\n" + + "You can also set it to 'none' to disable any default behavior. " + + "Learn more: https://webpack.js.org/configuration/mode/"; } +}; + + +/***/ }), + +/***/ 5771: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Ivan Kopeykin @vankop +*/ + + + +const WebpackError = __webpack_require__(68422); +const makeSerializable = __webpack_require__(26522); + +/** @typedef {import("./Dependency").DependencyLocation} DependencyLocation */ +class NodeStuffInWebError extends WebpackError { /** - * @returns {boolean} true if the compilation had a warning + * @param {DependencyLocation} loc loc + * @param {string} expression expression + * @param {string} description description */ - hasWarnings() { - return ( - this.compilation.warnings.length > 0 || - this.compilation.children.some(child => child.getStats().hasWarnings()) + constructor(loc, expression, description) { + super( + `${JSON.stringify( + expression + )} has been used, it will be undefined in next major version. +${description}` ); + + this.name = "NodeStuffInWebError"; + this.loc = loc; } +} - /** - * @returns {boolean} true if the compilation encountered an error - */ - hasErrors() { - return ( - this.compilation.errors.length > 0 || - this.compilation.children.some(child => child.getStats().hasErrors()) - ); +makeSerializable(NodeStuffInWebError, "webpack/lib/NodeStuffInWebError"); + +module.exports = NodeStuffInWebError; + + +/***/ }), + +/***/ 14290: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ + + + +const NodeStuffInWebError = __webpack_require__(5771); +const RuntimeGlobals = __webpack_require__(49404); +const CachedConstDependency = __webpack_require__(64177); +const ConstDependency = __webpack_require__(60864); +const { + evaluateToString, + expressionIsUnsupported +} = __webpack_require__(28723); +const { relative } = __webpack_require__(93204); +const { parseResource } = __webpack_require__(96236); + +/** @typedef {import("webpack-sources").ReplaceSource} ReplaceSource */ +/** @typedef {import("./Compiler")} Compiler */ +/** @typedef {import("./Dependency")} Dependency */ +/** @typedef {import("./DependencyTemplates")} DependencyTemplates */ +/** @typedef {import("./RuntimeTemplate")} RuntimeTemplate */ + +class NodeStuffPlugin { + constructor(options) { + this.options = options; } /** - * @param {(string|StatsOptions)=} options stats options - * @returns {StatsCompilation} json output + * Apply the plugin + * @param {Compiler} compiler the compiler instance + * @returns {void} */ - toJson(options) { - options = this.compilation.createStatsOptions(options, { - forToString: false - }); + apply(compiler) { + const options = this.options; + compiler.hooks.compilation.tap( + "NodeStuffPlugin", + (compilation, { normalModuleFactory }) => { + const handler = (parser, parserOptions) => { + if (parserOptions.node === false) return; - const statsFactory = this.compilation.createStatsFactory(options); + let localOptions = options; + if (parserOptions.node) { + localOptions = { ...localOptions, ...parserOptions.node }; + } - return statsFactory.create("compilation", this.compilation, { - compilation: this.compilation - }); - } + if (localOptions.global !== false) { + const withWarning = localOptions.global === "warn"; + parser.hooks.expression + .for("global") + .tap("NodeStuffPlugin", expr => { + const dep = new ConstDependency( + RuntimeGlobals.global, + expr.range, + [RuntimeGlobals.global] + ); + dep.loc = expr.loc; + parser.state.module.addPresentationalDependency(dep); - toString(options) { - options = this.compilation.createStatsOptions(options, { - forToString: true - }); + // TODO webpack 6 remove + if (withWarning) { + parser.state.module.addWarning( + new NodeStuffInWebError( + dep.loc, + "global", + "The global namespace object is Node.js feature and doesn't present in browser." + ) + ); + } + }); + } + + const setModuleConstant = (expressionName, fn, warning) => { + parser.hooks.expression + .for(expressionName) + .tap("NodeStuffPlugin", expr => { + const dep = new CachedConstDependency( + JSON.stringify(fn(parser.state.module)), + expr.range, + expressionName + ); + dep.loc = expr.loc; + parser.state.module.addPresentationalDependency(dep); + + // TODO webpack 6 remove + if (warning) { + parser.state.module.addWarning( + new NodeStuffInWebError(dep.loc, expressionName, warning) + ); + } + + return true; + }); + }; + + const setConstant = (expressionName, value, warning) => + setModuleConstant(expressionName, () => value, warning); + + const context = compiler.context; + if (localOptions.__filename) { + switch (localOptions.__filename) { + case "mock": + setConstant("__filename", "/index.js"); + break; + case "warn-mock": + setConstant( + "__filename", + "/index.js", + "The __filename is Node.js feature and doesn't present in browser." + ); + break; + case true: + setModuleConstant("__filename", module => + relative(compiler.inputFileSystem, context, module.resource) + ); + break; + } + + parser.hooks.evaluateIdentifier + .for("__filename") + .tap("NodeStuffPlugin", expr => { + if (!parser.state.module) return; + const resource = parseResource(parser.state.module.resource); + return evaluateToString(resource.path)(expr); + }); + } + if (localOptions.__dirname) { + switch (localOptions.__dirname) { + case "mock": + setConstant("__dirname", "/"); + break; + case "warn-mock": + setConstant( + "__dirname", + "/", + "The __dirname is Node.js feature and doesn't present in browser." + ); + break; + case true: + setModuleConstant("__dirname", module => + relative(compiler.inputFileSystem, context, module.context) + ); + break; + } - const statsFactory = this.compilation.createStatsFactory(options); - const statsPrinter = this.compilation.createStatsPrinter(options); + parser.hooks.evaluateIdentifier + .for("__dirname") + .tap("NodeStuffPlugin", expr => { + if (!parser.state.module) return; + return evaluateToString(parser.state.module.context)(expr); + }); + } + parser.hooks.expression + .for("require.extensions") + .tap( + "NodeStuffPlugin", + expressionIsUnsupported( + parser, + "require.extensions is not supported by webpack. Use a loader instead." + ) + ); + }; - const data = statsFactory.create("compilation", this.compilation, { - compilation: this.compilation - }); - const result = statsPrinter.print("compilation", data); - return result === undefined ? "" : result; + normalModuleFactory.hooks.parser + .for("javascript/auto") + .tap("NodeStuffPlugin", handler); + normalModuleFactory.hooks.parser + .for("javascript/dynamic") + .tap("NodeStuffPlugin", handler); + } + ); } } -module.exports = Stats; +module.exports = NodeStuffPlugin; /***/ }), -/***/ 92066: +/***/ 11026: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; @@ -60823,1814 +55793,2747 @@ module.exports = Stats; -const { ConcatSource, PrefixSource } = __webpack_require__(96192); +const parseJson = __webpack_require__(48335); +const { getContext, runLoaders } = __webpack_require__(67578); +const querystring = __webpack_require__(71191); +const { HookMap, SyncHook, AsyncSeriesBailHook } = __webpack_require__(34718); +const { + CachedSource, + OriginalSource, + RawSource, + SourceMapSource +} = __webpack_require__(96192); +const Compilation = __webpack_require__(59622); +const HookWebpackError = __webpack_require__(89935); +const Module = __webpack_require__(85887); +const ModuleBuildError = __webpack_require__(37991); +const ModuleError = __webpack_require__(11686); +const ModuleGraphConnection = __webpack_require__(94144); +const ModuleParseError = __webpack_require__(13110); +const ModuleWarning = __webpack_require__(92085); +const RuntimeGlobals = __webpack_require__(49404); +const UnhandledSchemeError = __webpack_require__(63859); +const WebpackError = __webpack_require__(68422); +const formatLocation = __webpack_require__(57261); +const LazySet = __webpack_require__(59534); +const { isSubset } = __webpack_require__(34715); +const { getScheme } = __webpack_require__(49606); +const { + compareLocations, + concatComparators, + compareSelect, + keepOriginalOrder +} = __webpack_require__(26296); +const createHash = __webpack_require__(24123); +const { createFakeHook } = __webpack_require__(2594); +const { join } = __webpack_require__(93204); +const { + contextify, + absolutify, + makePathsRelative +} = __webpack_require__(96236); +const makeSerializable = __webpack_require__(26522); +const memoize = __webpack_require__(84297); /** @typedef {import("webpack-sources").Source} Source */ -/** @typedef {import("../declarations/WebpackOptions").Output} OutputOptions */ -/** @typedef {import("./Chunk")} Chunk */ +/** @typedef {import("../declarations/LoaderContext").NormalModuleLoaderContext} NormalModuleLoaderContext */ +/** @typedef {import("../declarations/WebpackOptions").Mode} Mode */ +/** @typedef {import("../declarations/WebpackOptions").WebpackOptionsNormalized} WebpackOptions */ /** @typedef {import("./ChunkGraph")} ChunkGraph */ -/** @typedef {import("./CodeGenerationResults")} CodeGenerationResults */ -/** @typedef {import("./Compilation").AssetInfo} AssetInfo */ -/** @typedef {import("./Compilation").PathData} PathData */ +/** @typedef {import("./Compiler")} Compiler */ +/** @typedef {import("./Dependency").UpdateHashContext} UpdateHashContext */ /** @typedef {import("./DependencyTemplates")} DependencyTemplates */ -/** @typedef {import("./Module")} Module */ +/** @typedef {import("./Generator")} Generator */ +/** @typedef {import("./Module").CodeGenerationContext} CodeGenerationContext */ +/** @typedef {import("./Module").CodeGenerationResult} CodeGenerationResult */ +/** @typedef {import("./Module").ConcatenationBailoutReasonContext} ConcatenationBailoutReasonContext */ +/** @typedef {import("./Module").LibIdentOptions} LibIdentOptions */ +/** @typedef {import("./Module").NeedBuildContext} NeedBuildContext */ /** @typedef {import("./ModuleGraph")} ModuleGraph */ -/** @typedef {import("./ModuleTemplate")} ModuleTemplate */ -/** @typedef {import("./RuntimeModule")} RuntimeModule */ +/** @typedef {import("./ModuleGraphConnection").ConnectionState} ConnectionState */ +/** @typedef {import("./NormalModuleFactory")} NormalModuleFactory */ +/** @typedef {import("./Parser")} Parser */ +/** @typedef {import("./RequestShortener")} RequestShortener */ +/** @typedef {import("./ResolverFactory").ResolverWithOptions} ResolverWithOptions */ /** @typedef {import("./RuntimeTemplate")} RuntimeTemplate */ -/** @typedef {import("./javascript/JavascriptModulesPlugin").ChunkRenderContext} ChunkRenderContext */ -/** @typedef {import("./javascript/JavascriptModulesPlugin").RenderContext} RenderContext */ - -const START_LOWERCASE_ALPHABET_CODE = "a".charCodeAt(0); -const START_UPPERCASE_ALPHABET_CODE = "A".charCodeAt(0); -const DELTA_A_TO_Z = "z".charCodeAt(0) - START_LOWERCASE_ALPHABET_CODE + 1; -const NUMBER_OF_IDENTIFIER_START_CHARS = DELTA_A_TO_Z * 2 + 2; // a-z A-Z _ $ -const NUMBER_OF_IDENTIFIER_CONTINUATION_CHARS = - NUMBER_OF_IDENTIFIER_START_CHARS + 10; // a-z A-Z _ $ 0-9 -const FUNCTION_CONTENT_REGEX = /^function\s?\(\)\s?\{\r?\n?|\r?\n?\}$/g; -const INDENT_MULTILINE_REGEX = /^\t/gm; -const LINE_SEPARATOR_REGEX = /\r?\n/g; -const IDENTIFIER_NAME_REPLACE_REGEX = /^([^a-zA-Z$_])/; -const IDENTIFIER_ALPHA_NUMERIC_NAME_REPLACE_REGEX = /[^a-zA-Z0-9$]+/g; -const COMMENT_END_REGEX = /\*\//g; -const PATH_NAME_NORMALIZE_REPLACE_REGEX = /[^a-zA-Z0-9_!§$()=\-^°]+/g; -const MATCH_PADDED_HYPHENS_REPLACE_REGEX = /^-|-$/g; +/** @typedef {import("./logging/Logger").Logger} WebpackLogger */ +/** @typedef {import("./util/Hash")} Hash */ +/** @typedef {import("./util/fs").InputFileSystem} InputFileSystem */ +/** @typedef {import("./util/runtime").RuntimeSpec} RuntimeSpec */ /** - * @typedef {Object} RenderManifestOptions - * @property {Chunk} chunk the chunk used to render - * @property {string} hash - * @property {string} fullHash - * @property {OutputOptions} outputOptions - * @property {CodeGenerationResults} codeGenerationResults - * @property {{javascript: ModuleTemplate}} moduleTemplates - * @property {DependencyTemplates} dependencyTemplates - * @property {RuntimeTemplate} runtimeTemplate - * @property {ModuleGraph} moduleGraph - * @property {ChunkGraph} chunkGraph + * @typedef {Object} SourceMap + * @property {number} version + * @property {string[]} sources + * @property {string} mappings + * @property {string=} file + * @property {string=} sourceRoot + * @property {string[]=} sourcesContent + * @property {string[]=} names */ -/** @typedef {RenderManifestEntryTemplated | RenderManifestEntryStatic} RenderManifestEntry */ +const getInvalidDependenciesModuleWarning = memoize(() => + __webpack_require__(2822) +); +const getValidate = memoize(() => __webpack_require__(79286).validate); + +const ABSOLUTE_PATH_REGEX = /^([a-zA-Z]:\\|\\\\|\/)/; /** - * @typedef {Object} RenderManifestEntryTemplated - * @property {function(): Source} render - * @property {string | function(PathData, AssetInfo=): string} filenameTemplate - * @property {PathData=} pathOptions - * @property {AssetInfo=} info - * @property {string} identifier - * @property {string=} hash - * @property {boolean=} auxiliary + * @typedef {Object} LoaderItem + * @property {string} loader + * @property {any} options + * @property {string?} ident + * @property {string?} type */ /** - * @typedef {Object} RenderManifestEntryStatic - * @property {function(): Source} render - * @property {string} filename - * @property {AssetInfo} info - * @property {string} identifier - * @property {string=} hash - * @property {boolean=} auxiliary + * @param {string} context absolute context path + * @param {string} source a source path + * @param {Object=} associatedObjectForCache an object to which the cache will be attached + * @returns {string} new source path */ +const contextifySourceUrl = (context, source, associatedObjectForCache) => { + if (source.startsWith("webpack://")) return source; + return `webpack://${makePathsRelative( + context, + source, + associatedObjectForCache + )}`; +}; /** - * @typedef {Object} HasId - * @property {number | string} id + * @param {string} context absolute context path + * @param {SourceMap} sourceMap a source map + * @param {Object=} associatedObjectForCache an object to which the cache will be attached + * @returns {SourceMap} new source map */ +const contextifySourceMap = (context, sourceMap, associatedObjectForCache) => { + if (!Array.isArray(sourceMap.sources)) return sourceMap; + const { sourceRoot } = sourceMap; + /** @type {function(string): string} */ + const mapper = !sourceRoot + ? source => source + : sourceRoot.endsWith("/") + ? source => + source.startsWith("/") + ? `${sourceRoot.slice(0, -1)}${source}` + : `${sourceRoot}${source}` + : source => + source.startsWith("/") + ? `${sourceRoot}${source}` + : `${sourceRoot}/${source}`; + const newSources = sourceMap.sources.map(source => + contextifySourceUrl(context, mapper(source), associatedObjectForCache) + ); + return { + ...sourceMap, + file: "x", + sourceRoot: undefined, + sources: newSources + }; +}; /** - * @typedef {function(Module, number): boolean} ModuleFilterPredicate + * @param {string | Buffer} input the input + * @returns {string} the converted string */ - -class Template { - /** - * - * @param {Function} fn a runtime function (.runtime.js) "template" - * @returns {string} the updated and normalized function string - */ - static getFunctionContent(fn) { - return fn - .toString() - .replace(FUNCTION_CONTENT_REGEX, "") - .replace(INDENT_MULTILINE_REGEX, "") - .replace(LINE_SEPARATOR_REGEX, "\n"); +const asString = input => { + if (Buffer.isBuffer(input)) { + return input.toString("utf-8"); } + return input; +}; - /** - * @param {string} str the string converted to identifier - * @returns {string} created identifier - */ - static toIdentifier(str) { - if (typeof str !== "string") return ""; - return str - .replace(IDENTIFIER_NAME_REPLACE_REGEX, "_$1") - .replace(IDENTIFIER_ALPHA_NUMERIC_NAME_REPLACE_REGEX, "_"); - } - /** - * - * @param {string} str string to be converted to commented in bundle code - * @returns {string} returns a commented version of string - */ - static toComment(str) { - if (!str) return ""; - return `/*! ${str.replace(COMMENT_END_REGEX, "* /")} */`; +/** + * @param {string | Buffer} input the input + * @returns {Buffer} the converted buffer + */ +const asBuffer = input => { + if (!Buffer.isBuffer(input)) { + return Buffer.from(input, "utf-8"); } + return input; +}; - /** - * - * @param {string} str string to be converted to "normal comment" - * @returns {string} returns a commented version of string - */ - static toNormalComment(str) { - if (!str) return ""; - return `/* ${str.replace(COMMENT_END_REGEX, "* /")} */`; +class NonErrorEmittedError extends WebpackError { + constructor(error) { + super(); + + this.name = "NonErrorEmittedError"; + this.message = "(Emitted value instead of an instance of Error) " + error; } +} + +makeSerializable( + NonErrorEmittedError, + "webpack/lib/NormalModule", + "NonErrorEmittedError" +); + +/** + * @typedef {Object} NormalModuleCompilationHooks + * @property {SyncHook<[object, NormalModule]>} loader + * @property {SyncHook<[LoaderItem[], NormalModule, object]>} beforeLoaders + * @property {SyncHook<[NormalModule]>} beforeParse + * @property {SyncHook<[NormalModule]>} beforeSnapshot + * @property {HookMap>} readResourceForScheme + * @property {HookMap>} readResource + * @property {AsyncSeriesBailHook<[NormalModule, NeedBuildContext], boolean>} needBuild + */ + +/** @type {WeakMap} */ +const compilationHooksMap = new WeakMap(); +class NormalModule extends Module { /** - * @param {string} str string path to be normalized - * @returns {string} normalized bundle-safe path + * @param {Compilation} compilation the compilation + * @returns {NormalModuleCompilationHooks} the attached hooks */ - static toPath(str) { - if (typeof str !== "string") return ""; - return str - .replace(PATH_NAME_NORMALIZE_REPLACE_REGEX, "-") - .replace(MATCH_PADDED_HYPHENS_REPLACE_REGEX, ""); + static getCompilationHooks(compilation) { + if (!(compilation instanceof Compilation)) { + throw new TypeError( + "The 'compilation' argument must be an instance of Compilation" + ); + } + let hooks = compilationHooksMap.get(compilation); + if (hooks === undefined) { + hooks = { + loader: new SyncHook(["loaderContext", "module"]), + beforeLoaders: new SyncHook(["loaders", "module", "loaderContext"]), + beforeParse: new SyncHook(["module"]), + beforeSnapshot: new SyncHook(["module"]), + // TODO webpack 6 deprecate + readResourceForScheme: new HookMap(scheme => { + const hook = hooks.readResource.for(scheme); + return createFakeHook( + /** @type {AsyncSeriesBailHook<[string, NormalModule], string | Buffer>} */ ({ + tap: (options, fn) => + hook.tap(options, loaderContext => + fn(loaderContext.resource, loaderContext._module) + ), + tapAsync: (options, fn) => + hook.tapAsync(options, (loaderContext, callback) => + fn(loaderContext.resource, loaderContext._module, callback) + ), + tapPromise: (options, fn) => + hook.tapPromise(options, loaderContext => + fn(loaderContext.resource, loaderContext._module) + ) + }) + ); + }), + readResource: new HookMap( + () => new AsyncSeriesBailHook(["loaderContext"]) + ), + needBuild: new AsyncSeriesBailHook(["module", "context"]) + }; + compilationHooksMap.set(compilation, hooks); + } + return hooks; } - // map number to a single character a-z, A-Z or multiple characters if number is too big /** - * @param {number} n number to convert to ident - * @returns {string} returns single character ident + * @param {Object} options options object + * @param {string=} options.layer an optional layer in which the module is + * @param {string} options.type module type + * @param {string} options.request request string + * @param {string} options.userRequest request intended by user (without loaders from config) + * @param {string} options.rawRequest request without resolving + * @param {LoaderItem[]} options.loaders list of loaders + * @param {string} options.resource path + query of the real resource + * @param {Record=} options.resourceResolveData resource resolve data + * @param {string} options.context context directory for resolving + * @param {string | undefined} options.matchResource path + query of the matched resource (virtual) + * @param {Parser} options.parser the parser used + * @param {object} options.parserOptions the options of the parser used + * @param {Generator} options.generator the generator used + * @param {object} options.generatorOptions the options of the generator used + * @param {Object} options.resolveOptions options used for resolving requests from this module */ - static numberToIdentifier(n) { - if (n >= NUMBER_OF_IDENTIFIER_START_CHARS) { - // use multiple letters - return ( - Template.numberToIdentifier(n % NUMBER_OF_IDENTIFIER_START_CHARS) + - Template.numberToIdentifierContinuation( - Math.floor(n / NUMBER_OF_IDENTIFIER_START_CHARS) - ) - ); - } + constructor({ + layer, + type, + request, + userRequest, + rawRequest, + loaders, + resource, + resourceResolveData, + context, + matchResource, + parser, + parserOptions, + generator, + generatorOptions, + resolveOptions + }) { + super(type, context || getContext(resource), layer); - // lower case - if (n < DELTA_A_TO_Z) { - return String.fromCharCode(START_LOWERCASE_ALPHABET_CODE + n); + // Info from Factory + /** @type {string} */ + this.request = request; + /** @type {string} */ + this.userRequest = userRequest; + /** @type {string} */ + this.rawRequest = rawRequest; + /** @type {boolean} */ + this.binary = /^(asset|webassembly)\b/.test(type); + /** @type {Parser} */ + this.parser = parser; + this.parserOptions = parserOptions; + /** @type {Generator} */ + this.generator = generator; + this.generatorOptions = generatorOptions; + /** @type {string} */ + this.resource = resource; + this.resourceResolveData = resourceResolveData; + /** @type {string | undefined} */ + this.matchResource = matchResource; + /** @type {LoaderItem[]} */ + this.loaders = loaders; + if (resolveOptions !== undefined) { + // already declared in super class + this.resolveOptions = resolveOptions; } - n -= DELTA_A_TO_Z; - // upper case - if (n < DELTA_A_TO_Z) { - return String.fromCharCode(START_UPPERCASE_ALPHABET_CODE + n); - } + // Info from Build + /** @type {WebpackError=} */ + this.error = null; + /** @private @type {Source=} */ + this._source = null; + /** @private @type {Map | undefined} **/ + this._sourceSizes = undefined; + /** @private @type {Set} */ + this._sourceTypes = undefined; - if (n === DELTA_A_TO_Z) return "_"; - return "$"; + // Cache + this._lastSuccessfulBuildMeta = {}; + this._forceBuild = true; + this._isEvaluatingSideEffects = false; + /** @type {WeakSet | undefined} */ + this._addedSideEffectsBailout = undefined; } /** - * @param {number} n number to convert to ident - * @returns {string} returns single character ident + * @returns {string} a unique identifier of the module */ - static numberToIdentifierContinuation(n) { - if (n >= NUMBER_OF_IDENTIFIER_CONTINUATION_CHARS) { - // use multiple letters - return ( - Template.numberToIdentifierContinuation( - n % NUMBER_OF_IDENTIFIER_CONTINUATION_CHARS - ) + - Template.numberToIdentifierContinuation( - Math.floor(n / NUMBER_OF_IDENTIFIER_CONTINUATION_CHARS) - ) - ); - } - - // lower case - if (n < DELTA_A_TO_Z) { - return String.fromCharCode(START_LOWERCASE_ALPHABET_CODE + n); + identifier() { + if (this.layer === null) { + if (this.type === "javascript/auto") { + return this.request; + } else { + return `${this.type}|${this.request}`; + } + } else { + return `${this.type}|${this.request}|${this.layer}`; } - n -= DELTA_A_TO_Z; + } - // upper case - if (n < DELTA_A_TO_Z) { - return String.fromCharCode(START_UPPERCASE_ALPHABET_CODE + n); - } - n -= DELTA_A_TO_Z; + /** + * @param {RequestShortener} requestShortener the request shortener + * @returns {string} a user readable identifier of the module + */ + readableIdentifier(requestShortener) { + return requestShortener.shorten(this.userRequest); + } - // numbers - if (n < 10) { - return `${n}`; - } + /** + * @param {LibIdentOptions} options options + * @returns {string | null} an identifier for library inclusion + */ + libIdent(options) { + return contextify( + options.context, + this.userRequest, + options.associatedObjectForCache + ); + } - if (n === 10) return "_"; - return "$"; + /** + * @returns {string | null} absolute path which should be used for condition matching (usually the resource path) + */ + nameForCondition() { + const resource = this.matchResource || this.resource; + const idx = resource.indexOf("?"); + if (idx >= 0) return resource.substr(0, idx); + return resource; } /** - * - * @param {string | string[]} s string to convert to identity - * @returns {string} converted identity + * Assuming this module is in the cache. Update the (cached) module with + * the fresh module from the factory. Usually updates internal references + * and properties. + * @param {Module} module fresh module + * @returns {void} */ - static indent(s) { - if (Array.isArray(s)) { - return s.map(Template.indent).join("\n"); - } else { - const str = s.trimRight(); - if (!str) return ""; - const ind = str[0] === "\n" ? "" : "\t"; - return ind + str.replace(/\n([^\n])/g, "\n\t$1"); - } + updateCacheModule(module) { + super.updateCacheModule(module); + const m = /** @type {NormalModule} */ (module); + this.binary = m.binary; + this.request = m.request; + this.userRequest = m.userRequest; + this.rawRequest = m.rawRequest; + this.parser = m.parser; + this.parserOptions = m.parserOptions; + this.generator = m.generator; + this.generatorOptions = m.generatorOptions; + this.resource = m.resource; + this.resourceResolveData = m.resourceResolveData; + this.context = m.context; + this.matchResource = m.matchResource; + this.loaders = m.loaders; } /** - * - * @param {string|string[]} s string to create prefix for - * @param {string} prefix prefix to compose - * @returns {string} returns new prefix string + * Assuming this module is in the cache. Remove internal references to allow freeing some memory. */ - static prefix(s, prefix) { - const str = Template.asString(s).trim(); - if (!str) return ""; - const ind = str[0] === "\n" ? "" : prefix; - return ind + str.replace(/\n([^\n])/g, "\n" + prefix + "$1"); + cleanupForCache() { + // Make sure to cache types and sizes before cleanup when this module has been built + // They are accessed by the stats and we don't want them to crash after cleanup + // TODO reconsider this for webpack 6 + if (this.buildInfo) { + if (this._sourceTypes === undefined) this.getSourceTypes(); + for (const type of this._sourceTypes) { + this.size(type); + } + } + super.cleanupForCache(); + this.parser = undefined; + this.parserOptions = undefined; + this.generator = undefined; + this.generatorOptions = undefined; } /** - * - * @param {string|string[]} str string or string collection - * @returns {string} returns a single string from array + * Module should be unsafe cached. Get data that's needed for that. + * This data will be passed to restoreFromUnsafeCache later. + * @returns {object} cached data */ - static asString(str) { - if (Array.isArray(str)) { - return str.join("\n"); - } - return str; + getUnsafeCacheData() { + const data = super.getUnsafeCacheData(); + data.parserOptions = this.parserOptions; + data.generatorOptions = this.generatorOptions; + return data; + } + + restoreFromUnsafeCache(unsafeCacheData, normalModuleFactory) { + this._restoreFromUnsafeCache(unsafeCacheData, normalModuleFactory); } /** - * @typedef {Object} WithId - * @property {string|number} id + * restore unsafe cache data + * @param {object} unsafeCacheData data from getUnsafeCacheData + * @param {NormalModuleFactory} normalModuleFactory the normal module factory handling the unsafe caching */ + _restoreFromUnsafeCache(unsafeCacheData, normalModuleFactory) { + super._restoreFromUnsafeCache(unsafeCacheData, normalModuleFactory); + this.parserOptions = unsafeCacheData.parserOptions; + this.parser = normalModuleFactory.getParser(this.type, this.parserOptions); + this.generatorOptions = unsafeCacheData.generatorOptions; + this.generator = normalModuleFactory.getGenerator( + this.type, + this.generatorOptions + ); + // we assume the generator behaves identically and keep cached sourceTypes/Sizes + } /** - * @param {WithId[]} modules a collection of modules to get array bounds for - * @returns {[number, number] | false} returns the upper and lower array bounds - * or false if not every module has a number based id + * @param {string} context the compilation context + * @param {string} name the asset name + * @param {string} content the content + * @param {string | TODO} sourceMap an optional source map + * @param {Object=} associatedObjectForCache object for caching + * @returns {Source} the created source */ - static getModulesArrayBounds(modules) { - let maxId = -Infinity; - let minId = Infinity; - for (const module of modules) { - const moduleId = module.id; - if (typeof moduleId !== "number") return false; - if (maxId < moduleId) maxId = moduleId; - if (minId > moduleId) minId = moduleId; - } - if (minId < 16 + ("" + minId).length) { - // add minId x ',' instead of 'Array(minId).concat(…)' - minId = 0; - } - // start with -1 because the first module needs no comma - let objectOverhead = -1; - for (const module of modules) { - // module id + colon + comma - objectOverhead += `${module.id}`.length + 2; + createSourceForAsset( + context, + name, + content, + sourceMap, + associatedObjectForCache + ) { + if (sourceMap) { + if ( + typeof sourceMap === "string" && + (this.useSourceMap || this.useSimpleSourceMap) + ) { + return new OriginalSource( + content, + contextifySourceUrl(context, sourceMap, associatedObjectForCache) + ); + } + + if (this.useSourceMap) { + return new SourceMapSource( + content, + name, + contextifySourceMap(context, sourceMap, associatedObjectForCache) + ); + } } - // number of commas, or when starting non-zero the length of Array(minId).concat() - const arrayOverhead = minId === 0 ? maxId : 16 + `${minId}`.length + maxId; - return arrayOverhead < objectOverhead ? [minId, maxId] : false; + + return new RawSource(content); } /** - * @param {ChunkRenderContext} renderContext render context - * @param {Module[]} modules modules to render (should be ordered by identifier) - * @param {function(Module): Source} renderModule function to render a module - * @param {string=} prefix applying prefix strings - * @returns {Source} rendered chunk modules in a Source object + * @param {ResolverWithOptions} resolver a resolver + * @param {WebpackOptions} options webpack options + * @param {Compilation} compilation the compilation + * @param {InputFileSystem} fs file system from reading + * @param {NormalModuleCompilationHooks} hooks the hooks + * @returns {NormalModuleLoaderContext} loader context */ - static renderChunkModules(renderContext, modules, renderModule, prefix = "") { - const { chunkGraph } = renderContext; - var source = new ConcatSource(); - if (modules.length === 0) { - return null; - } - /** @type {{id: string|number, source: Source|string}[]} */ - const allModules = modules.map(module => { + _createLoaderContext(resolver, options, compilation, fs, hooks) { + const { requestShortener } = compilation.runtimeTemplate; + const getCurrentLoaderName = () => { + const currentLoader = this.getCurrentLoader(loaderContext); + if (!currentLoader) return "(not in loader scope)"; + return requestShortener.shorten(currentLoader.loader); + }; + const getResolveContext = () => { return { - id: chunkGraph.getModuleId(module), - source: renderModule(module) || "false" + fileDependencies: { + add: d => loaderContext.addDependency(d) + }, + contextDependencies: { + add: d => loaderContext.addContextDependency(d) + }, + missingDependencies: { + add: d => loaderContext.addMissingDependency(d) + } }; - }); - const bounds = Template.getModulesArrayBounds(allModules); - if (bounds) { - // Render a spare array - const minId = bounds[0]; - const maxId = bounds[1]; - if (minId !== 0) { - source.add(`Array(${minId}).concat(`); - } - source.add("[\n"); - /** @type {Map} */ - const modules = new Map(); - for (const module of allModules) { - modules.set(module.id, module); + }; + const getAbsolutify = memoize(() => + absolutify.bindCache(compilation.compiler.root) + ); + const getAbsolutifyInContext = memoize(() => + absolutify.bindContextCache(this.context, compilation.compiler.root) + ); + const getContextify = memoize(() => + contextify.bindCache(compilation.compiler.root) + ); + const getContextifyInContext = memoize(() => + contextify.bindContextCache(this.context, compilation.compiler.root) + ); + const utils = { + absolutify: (context, request) => { + return context === this.context + ? getAbsolutifyInContext()(request) + : getAbsolutify()(context, request); + }, + contextify: (context, request) => { + return context === this.context + ? getContextifyInContext()(request) + : getContextify()(context, request); + }, + createHash: type => { + return createHash(type || compilation.outputOptions.hashFunction); } - for (let idx = minId; idx <= maxId; idx++) { - const module = modules.get(idx); - if (idx !== minId) { - source.add(",\n"); + }; + const loaderContext = { + version: 2, + getOptions: schema => { + const loader = this.getCurrentLoader(loaderContext); + + let { options } = loader; + + if (typeof options === "string") { + if (options.substr(0, 1) === "{" && options.substr(-1) === "}") { + try { + options = parseJson(options); + } catch (e) { + throw new Error(`Cannot parse string options: ${e.message}`); + } + } else { + options = querystring.parse(options, "&", "=", { + maxKeys: 0 + }); + } } - source.add(`/* ${idx} */`); - if (module) { - source.add("\n"); - source.add(module.source); + + if (options === null || options === undefined) { + options = {}; } - } - source.add("\n" + prefix + "]"); - if (minId !== 0) { - source.add(")"); - } - } else { - // Render an object - source.add("{\n"); - for (let i = 0; i < allModules.length; i++) { - const module = allModules[i]; - if (i !== 0) { - source.add(",\n"); + + if (schema) { + let name = "Loader"; + let baseDataPath = "options"; + let match; + if (schema.title && (match = /^(.+) (.+)$/.exec(schema.title))) { + [, name, baseDataPath] = match; + } + getValidate()(schema, options, { + name, + baseDataPath + }); } - source.add(`\n/***/ ${JSON.stringify(module.id)}:\n`); - source.add(module.source); - } - source.add(`\n\n${prefix}}`); - } - return source; - } - /** - * @param {RuntimeModule[]} runtimeModules array of runtime modules in order - * @param {RenderContext & { codeGenerationResults?: CodeGenerationResults }} renderContext render context - * @returns {Source} rendered runtime modules in a Source object - */ - static renderRuntimeModules(runtimeModules, renderContext) { - const source = new ConcatSource(); - for (const module of runtimeModules) { - const codeGenerationResults = renderContext.codeGenerationResults; - let runtimeSource; - if (codeGenerationResults) { - runtimeSource = codeGenerationResults.getSource( - module, - renderContext.chunk.runtime, - "runtime" + return options; + }, + emitWarning: warning => { + if (!(warning instanceof Error)) { + warning = new NonErrorEmittedError(warning); + } + this.addWarning( + new ModuleWarning(warning, { + from: getCurrentLoaderName() + }) ); - } else { - const codeGenResult = module.codeGeneration({ - chunkGraph: renderContext.chunkGraph, - dependencyTemplates: renderContext.dependencyTemplates, - moduleGraph: renderContext.moduleGraph, - runtimeTemplate: renderContext.runtimeTemplate, - runtime: renderContext.chunk.runtime - }); - if (!codeGenResult) continue; - runtimeSource = codeGenResult.sources.get("runtime"); - } - if (runtimeSource) { - source.add(Template.toNormalComment(module.identifier()) + "\n"); - if (!module.shouldIsolate()) { - source.add(runtimeSource); - source.add("\n\n"); - } else if (renderContext.runtimeTemplate.supportsArrowFunction()) { - source.add("(() => {\n"); - source.add(new PrefixSource("\t", runtimeSource)); - source.add("\n})();\n\n"); - } else { - source.add("!function() {\n"); - source.add(new PrefixSource("\t", runtimeSource)); - source.add("\n}();\n\n"); + }, + emitError: error => { + if (!(error instanceof Error)) { + error = new NonErrorEmittedError(error); } - } + this.addError( + new ModuleError(error, { + from: getCurrentLoaderName() + }) + ); + }, + getLogger: name => { + const currentLoader = this.getCurrentLoader(loaderContext); + return compilation.getLogger(() => + [currentLoader && currentLoader.loader, name, this.identifier()] + .filter(Boolean) + .join("|") + ); + }, + resolve(context, request, callback) { + resolver.resolve({}, context, request, getResolveContext(), callback); + }, + getResolve(options) { + const child = options ? resolver.withOptions(options) : resolver; + return (context, request, callback) => { + if (callback) { + child.resolve({}, context, request, getResolveContext(), callback); + } else { + return new Promise((resolve, reject) => { + child.resolve( + {}, + context, + request, + getResolveContext(), + (err, result) => { + if (err) reject(err); + else resolve(result); + } + ); + }); + } + }; + }, + emitFile: (name, content, sourceMap, assetInfo) => { + if (!this.buildInfo.assets) { + this.buildInfo.assets = Object.create(null); + this.buildInfo.assetsInfo = new Map(); + } + this.buildInfo.assets[name] = this.createSourceForAsset( + options.context, + name, + content, + sourceMap, + compilation.compiler.root + ); + this.buildInfo.assetsInfo.set(name, assetInfo); + }, + addBuildDependency: dep => { + if (this.buildInfo.buildDependencies === undefined) { + this.buildInfo.buildDependencies = new LazySet(); + } + this.buildInfo.buildDependencies.add(dep); + }, + utils, + rootContext: options.context, + webpack: true, + sourceMap: !!this.useSourceMap, + mode: options.mode || "production", + _module: this, + _compilation: compilation, + _compiler: compilation.compiler, + fs: fs + }; + + Object.assign(loaderContext, options.loader); + + hooks.loader.call(loaderContext, this); + + return loaderContext; + } + + getCurrentLoader(loaderContext, index = loaderContext.loaderIndex) { + if ( + this.loaders && + this.loaders.length && + index < this.loaders.length && + index >= 0 && + this.loaders[index] + ) { + return this.loaders[index]; } - return source; + return null; } /** - * @param {RuntimeModule[]} runtimeModules array of runtime modules in order - * @param {RenderContext} renderContext render context - * @returns {Source} rendered chunk runtime modules in a Source object + * @param {string} context the compilation context + * @param {string | Buffer} content the content + * @param {string | TODO} sourceMap an optional source map + * @param {Object=} associatedObjectForCache object for caching + * @returns {Source} the created source */ - static renderChunkRuntimeModules(runtimeModules, renderContext) { - return new PrefixSource( - "/******/ ", - new ConcatSource( - "function(__webpack_require__) { // webpackRuntimeModules\n", - this.renderRuntimeModules(runtimeModules, renderContext), - "}\n" - ) - ); - } -} - -module.exports = Template; -module.exports.NUMBER_OF_IDENTIFIER_START_CHARS = - NUMBER_OF_IDENTIFIER_START_CHARS; -module.exports.NUMBER_OF_IDENTIFIER_CONTINUATION_CHARS = - NUMBER_OF_IDENTIFIER_CONTINUATION_CHARS; - + createSource(context, content, sourceMap, associatedObjectForCache) { + if (Buffer.isBuffer(content)) { + return new RawSource(content); + } -/***/ }), + // if there is no identifier return raw source + if (!this.identifier) { + return new RawSource(content); + } -/***/ 54642: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + // from here on we assume we have an identifier + const identifier = this.identifier(); -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Jason Anderson @diurnalist -*/ + if (this.useSourceMap && sourceMap) { + return new SourceMapSource( + content, + contextifySourceUrl(context, identifier, associatedObjectForCache), + contextifySourceMap(context, sourceMap, associatedObjectForCache) + ); + } + if (this.useSourceMap || this.useSimpleSourceMap) { + return new OriginalSource( + content, + contextifySourceUrl(context, identifier, associatedObjectForCache) + ); + } + return new RawSource(content); + } -const { basename, extname } = __webpack_require__(85622); -const util = __webpack_require__(31669); -const Chunk = __webpack_require__(65574); -const Module = __webpack_require__(85887); -const { parseResource } = __webpack_require__(96236); + /** + * @param {WebpackOptions} options webpack options + * @param {Compilation} compilation the compilation + * @param {ResolverWithOptions} resolver the resolver + * @param {InputFileSystem} fs the file system + * @param {NormalModuleCompilationHooks} hooks the hooks + * @param {function(WebpackError=): void} callback callback function + * @returns {void} + */ + _doBuild(options, compilation, resolver, fs, hooks, callback) { + const loaderContext = this._createLoaderContext( + resolver, + options, + compilation, + fs, + hooks + ); -/** @typedef {import("./Compilation").AssetInfo} AssetInfo */ -/** @typedef {import("./Compilation").PathData} PathData */ -/** @typedef {import("./Compiler")} Compiler */ + const processResult = (err, result) => { + if (err) { + if (!(err instanceof Error)) { + err = new NonErrorEmittedError(err); + } + const currentLoader = this.getCurrentLoader(loaderContext); + const error = new ModuleBuildError(err, { + from: + currentLoader && + compilation.runtimeTemplate.requestShortener.shorten( + currentLoader.loader + ) + }); + return callback(error); + } -const REGEXP = /\[\\*([\w:]+)\\*\]/gi; + const source = result[0]; + const sourceMap = result.length >= 1 ? result[1] : null; + const extraInfo = result.length >= 2 ? result[2] : null; -const prepareId = id => { - if (typeof id !== "string") return id; + if (!Buffer.isBuffer(source) && typeof source !== "string") { + const currentLoader = this.getCurrentLoader(loaderContext, 0); + const err = new Error( + `Final loader (${ + currentLoader + ? compilation.runtimeTemplate.requestShortener.shorten( + currentLoader.loader + ) + : "unknown" + }) didn't return a Buffer or String` + ); + const error = new ModuleBuildError(err); + return callback(error); + } - if (/^"\s\+*.*\+\s*"$/.test(id)) { - const match = /^"\s\+*\s*(.*)\s*\+\s*"$/.exec(id); + this._source = this.createSource( + options.context, + this.binary ? asBuffer(source) : asString(source), + sourceMap, + compilation.compiler.root + ); + if (this._sourceSizes !== undefined) this._sourceSizes.clear(); + this._ast = + typeof extraInfo === "object" && + extraInfo !== null && + extraInfo.webpackAST !== undefined + ? extraInfo.webpackAST + : null; + return callback(); + }; - return `" + (${match[1]} + "").replace(/(^[.-]|[^a-zA-Z0-9_-])+/g, "_") + "`; - } + this.buildInfo.fileDependencies = new LazySet(); + this.buildInfo.contextDependencies = new LazySet(); + this.buildInfo.missingDependencies = new LazySet(); + this.buildInfo.cacheable = true; - return id.replace(/(^[.-]|[^a-zA-Z0-9_-])+/g, "_"); -}; + try { + hooks.beforeLoaders.call(this.loaders, this, loaderContext); + } catch (err) { + processResult(err); + return; + } -const hashLength = (replacer, handler, assetInfo, hashName) => { - const fn = (match, arg, input) => { - let result; - const length = arg && parseInt(arg, 10); + if (this.loaders.length > 0) { + this.buildInfo.buildDependencies = new LazySet(); + } - if (length && handler) { - result = handler(length); - } else { - const hash = replacer(match, arg, input); + runLoaders( + { + resource: this.resource, + loaders: this.loaders, + context: loaderContext, + processResource: (loaderContext, resourcePath, callback) => { + const resource = loaderContext.resource; + const scheme = getScheme(resource); + hooks.readResource + .for(scheme) + .callAsync(loaderContext, (err, result) => { + if (err) return callback(err); + if (typeof result !== "string" && !result) { + return callback(new UnhandledSchemeError(scheme, resource)); + } + return callback(null, result); + }); + } + }, + (err, result) => { + // Cleanup loaderContext to avoid leaking memory in ICs + loaderContext._compilation = + loaderContext._compiler = + loaderContext._module = + loaderContext.fs = + undefined; - result = length ? hash.slice(0, length) : hash; - } - if (assetInfo) { - assetInfo.immutable = true; - if (Array.isArray(assetInfo[hashName])) { - assetInfo[hashName] = [...assetInfo[hashName], result]; - } else if (assetInfo[hashName]) { - assetInfo[hashName] = [assetInfo[hashName], result]; - } else { - assetInfo[hashName] = result; + if (!result) { + this.buildInfo.cacheable = false; + return processResult( + err || new Error("No result from loader-runner processing"), + null + ); + } + this.buildInfo.fileDependencies.addAll(result.fileDependencies); + this.buildInfo.contextDependencies.addAll(result.contextDependencies); + this.buildInfo.missingDependencies.addAll(result.missingDependencies); + for (const loader of this.loaders) { + this.buildInfo.buildDependencies.add(loader.loader); + } + this.buildInfo.cacheable = this.buildInfo.cacheable && result.cacheable; + processResult(err, result.result); } - } - return result; - }; + ); + } - return fn; -}; + /** + * @param {WebpackError} error the error + * @returns {void} + */ + markModuleAsErrored(error) { + // Restore build meta from successful build to keep importing state + this.buildMeta = { ...this._lastSuccessfulBuildMeta }; + this.error = error; + this.addError(error); + } -const replacer = (value, allowEmpty) => { - const fn = (match, arg, input) => { - if (typeof value === "function") { - value = value(); + applyNoParseRule(rule, content) { + // must start with "rule" if rule is a string + if (typeof rule === "string") { + return content.startsWith(rule); } - if (value === null || value === undefined) { - if (!allowEmpty) { - throw new Error( - `Path variable ${match} not implemented in this context: ${input}` - ); - } - return ""; - } else { - return `${value}`; + if (typeof rule === "function") { + return rule(content); } - }; - - return fn; -}; - -const deprecationCache = new Map(); -const deprecatedFunction = (() => () => {})(); -const deprecated = (fn, message, code) => { - let d = deprecationCache.get(message); - if (d === undefined) { - d = util.deprecate(deprecatedFunction, message, code); - deprecationCache.set(message, d); + // we assume rule is a regexp + return rule.test(content); } - return (...args) => { - d(); - return fn(...args); - }; -}; - -/** - * @param {string | function(PathData, AssetInfo=): string} path the raw path - * @param {PathData} data context data - * @param {AssetInfo} assetInfo extra info about the asset (will be written to) - * @returns {string} the interpolated path - */ -const replacePathVariables = (path, data, assetInfo) => { - const chunkGraph = data.chunkGraph; - /** @type {Map} */ - const replacements = new Map(); - - // Filename context - // - // Placeholders - // - // for /some/path/file.js?query#fragment: - // [file] - /some/path/file.js - // [query] - ?query - // [fragment] - #fragment - // [base] - file.js - // [path] - /some/path/ - // [name] - file - // [ext] - .js - if (typeof data.filename === "string") { - const { path: file, query, fragment } = parseResource(data.filename); + // check if module should not be parsed + // returns "true" if the module should !not! be parsed + // returns "false" if the module !must! be parsed + shouldPreventParsing(noParseRule, request) { + // if no noParseRule exists, return false + // the module !must! be parsed. + if (!noParseRule) { + return false; + } - const ext = extname(file); - const base = basename(file); - const name = base.slice(0, base.length - ext.length); - const path = file.slice(0, file.length - base.length); + // we only have one rule to check + if (!Array.isArray(noParseRule)) { + // returns "true" if the module is !not! to be parsed + return this.applyNoParseRule(noParseRule, request); + } - replacements.set("file", replacer(file)); - replacements.set("query", replacer(query, true)); - replacements.set("fragment", replacer(fragment, true)); - replacements.set("path", replacer(path, true)); - replacements.set("base", replacer(base)); - replacements.set("name", replacer(name)); - replacements.set("ext", replacer(ext, true)); - // Legacy - replacements.set( - "filebase", - deprecated( - replacer(base), - "[filebase] is now [base]", - "DEP_WEBPACK_TEMPLATE_PATH_PLUGIN_REPLACE_PATH_VARIABLES_FILENAME" - ) - ); + for (let i = 0; i < noParseRule.length; i++) { + const rule = noParseRule[i]; + // early exit on first truthy match + // this module is !not! to be parsed + if (this.applyNoParseRule(rule, request)) { + return true; + } + } + // no match found, so this module !should! be parsed + return false; } - // Compilation context - // - // Placeholders - // - // [fullhash] - data.hash (3a4b5c6e7f) - // - // Legacy Placeholders - // - // [hash] - data.hash (3a4b5c6e7f) - if (data.hash) { - const hashReplacer = hashLength( - replacer(data.hash), - data.hashWithLength, - assetInfo, - "fullhash" - ); - - replacements.set("fullhash", hashReplacer); - - // Legacy - replacements.set( - "hash", - deprecated( - hashReplacer, - "[hash] is now [fullhash] (also consider using [chunkhash] or [contenthash], see documentation for details)", - "DEP_WEBPACK_TEMPLATE_PATH_PLUGIN_REPLACE_PATH_VARIABLES_HASH" - ) - ); + _initBuildHash(compilation) { + const hash = createHash(compilation.outputOptions.hashFunction); + if (this._source) { + hash.update("source"); + this._source.updateHash(hash); + } + hash.update("meta"); + hash.update(JSON.stringify(this.buildMeta)); + this.buildInfo.hash = /** @type {string} */ (hash.digest("hex")); } - // Chunk Context - // - // Placeholders - // - // [id] - chunk.id (0.js) - // [name] - chunk.name (app.js) - // [chunkhash] - chunk.hash (7823t4t4.js) - // [contenthash] - chunk.contentHash[type] (3256u3zg.js) - if (data.chunk) { - const chunk = data.chunk; + /** + * @param {WebpackOptions} options webpack options + * @param {Compilation} compilation the compilation + * @param {ResolverWithOptions} resolver the resolver + * @param {InputFileSystem} fs the file system + * @param {function(WebpackError=): void} callback callback function + * @returns {void} + */ + build(options, compilation, resolver, fs, callback) { + this._forceBuild = false; + this._source = null; + if (this._sourceSizes !== undefined) this._sourceSizes.clear(); + this._sourceTypes = undefined; + this._ast = null; + this.error = null; + this.clearWarningsAndErrors(); + this.clearDependenciesAndBlocks(); + this.buildMeta = {}; + this.buildInfo = { + cacheable: false, + parsed: true, + fileDependencies: undefined, + contextDependencies: undefined, + missingDependencies: undefined, + buildDependencies: undefined, + valueDependencies: undefined, + hash: undefined, + assets: undefined, + assetsInfo: undefined + }; - const contentHashType = data.contentHashType; + const startTime = compilation.compiler.fsStartTime || Date.now(); - const idReplacer = replacer(chunk.id); - const nameReplacer = replacer(chunk.name || chunk.id); - const chunkhashReplacer = hashLength( - replacer(chunk instanceof Chunk ? chunk.renderedHash : chunk.hash), - "hashWithLength" in chunk ? chunk.hashWithLength : undefined, - assetInfo, - "chunkhash" - ); - const contenthashReplacer = hashLength( - replacer( - data.contentHash || - (contentHashType && - chunk.contentHash && - chunk.contentHash[contentHashType]) - ), - data.contentHashWithLength || - ("contentHashWithLength" in chunk && chunk.contentHashWithLength - ? chunk.contentHashWithLength[contentHashType] - : undefined), - assetInfo, - "contenthash" - ); + const hooks = NormalModule.getCompilationHooks(compilation); - replacements.set("id", idReplacer); - replacements.set("name", nameReplacer); - replacements.set("chunkhash", chunkhashReplacer); - replacements.set("contenthash", contenthashReplacer); - } + return this._doBuild(options, compilation, resolver, fs, hooks, err => { + // if we have an error mark module as failed and exit + if (err) { + this.markModuleAsErrored(err); + this._initBuildHash(compilation); + return callback(); + } - // Module Context - // - // Placeholders - // - // [id] - module.id (2.png) - // [hash] - module.hash (6237543873.png) - // - // Legacy Placeholders - // - // [moduleid] - module.id (2.png) - // [modulehash] - module.hash (6237543873.png) - if (data.module) { - const module = data.module; + const handleParseError = e => { + const source = this._source.source(); + const loaders = this.loaders.map(item => + contextify(options.context, item.loader, compilation.compiler.root) + ); + const error = new ModuleParseError(source, e, loaders, this.type); + this.markModuleAsErrored(error); + this._initBuildHash(compilation); + return callback(); + }; - const idReplacer = replacer(() => - prepareId( - module instanceof Module ? chunkGraph.getModuleId(module) : module.id - ) - ); - const moduleHashReplacer = hashLength( - replacer(() => - module instanceof Module - ? chunkGraph.getRenderedModuleHash(module, data.runtime) - : module.hash - ), - "hashWithLength" in module ? module.hashWithLength : undefined, - assetInfo, - "modulehash" - ); - const contentHashReplacer = hashLength( - replacer(data.contentHash), - undefined, - assetInfo, - "contenthash" - ); + const handleParseResult = result => { + this.dependencies.sort( + concatComparators( + compareSelect(a => a.loc, compareLocations), + keepOriginalOrder(this.dependencies) + ) + ); + this._initBuildHash(compilation); + this._lastSuccessfulBuildMeta = this.buildMeta; + return handleBuildDone(); + }; - replacements.set("id", idReplacer); - replacements.set("modulehash", moduleHashReplacer); - replacements.set("contenthash", contentHashReplacer); - replacements.set( - "hash", - data.contentHash ? contentHashReplacer : moduleHashReplacer - ); - // Legacy - replacements.set( - "moduleid", - deprecated( - idReplacer, - "[moduleid] is now [id]", - "DEP_WEBPACK_TEMPLATE_PATH_PLUGIN_REPLACE_PATH_VARIABLES_MODULE_ID" - ) - ); - } + const handleBuildDone = () => { + try { + hooks.beforeSnapshot.call(this); + } catch (err) { + this.markModuleAsErrored(err); + return callback(); + } + + const snapshotOptions = compilation.options.snapshot.module; + if (!this.buildInfo.cacheable || !snapshotOptions) { + return callback(); + } + // add warning for all non-absolute paths in fileDependencies, etc + // This makes it easier to find problems with watching and/or caching + let nonAbsoluteDependencies = undefined; + const checkDependencies = deps => { + for (const dep of deps) { + if (!ABSOLUTE_PATH_REGEX.test(dep)) { + if (nonAbsoluteDependencies === undefined) + nonAbsoluteDependencies = new Set(); + nonAbsoluteDependencies.add(dep); + deps.delete(dep); + try { + const depWithoutGlob = dep.replace(/[\\/]?\*.*$/, ""); + const absolute = join( + compilation.fileSystemInfo.fs, + this.context, + depWithoutGlob + ); + if (absolute !== dep && ABSOLUTE_PATH_REGEX.test(absolute)) { + (depWithoutGlob !== dep + ? this.buildInfo.contextDependencies + : deps + ).add(absolute); + } + } catch (e) { + // ignore + } + } + } + }; + checkDependencies(this.buildInfo.fileDependencies); + checkDependencies(this.buildInfo.missingDependencies); + checkDependencies(this.buildInfo.contextDependencies); + if (nonAbsoluteDependencies !== undefined) { + const InvalidDependenciesModuleWarning = + getInvalidDependenciesModuleWarning(); + this.addWarning( + new InvalidDependenciesModuleWarning(this, nonAbsoluteDependencies) + ); + } + // convert file/context/missingDependencies into filesystem snapshot + compilation.fileSystemInfo.createSnapshot( + startTime, + this.buildInfo.fileDependencies, + this.buildInfo.contextDependencies, + this.buildInfo.missingDependencies, + snapshotOptions, + (err, snapshot) => { + if (err) { + this.markModuleAsErrored(err); + return; + } + this.buildInfo.fileDependencies = undefined; + this.buildInfo.contextDependencies = undefined; + this.buildInfo.missingDependencies = undefined; + this.buildInfo.snapshot = snapshot; + return callback(); + } + ); + }; - // Other things - if (data.url) { - replacements.set("url", replacer(data.url)); - } - if (typeof data.runtime === "string") { - replacements.set( - "runtime", - replacer(() => prepareId(data.runtime)) - ); - } else { - replacements.set("runtime", replacer("_")); + try { + hooks.beforeParse.call(this); + } catch (err) { + this.markModuleAsErrored(err); + this._initBuildHash(compilation); + return callback(); + } + + // check if this module should !not! be parsed. + // if so, exit here; + const noParseRule = options.module && options.module.noParse; + if (this.shouldPreventParsing(noParseRule, this.request)) { + // We assume that we need module and exports + this.buildInfo.parsed = false; + this._initBuildHash(compilation); + return handleBuildDone(); + } + + let result; + try { + const source = this._source.source(); + result = this.parser.parse(this._ast || source, { + source, + current: this, + module: this, + compilation: compilation, + options: options + }); + } catch (e) { + handleParseError(e); + return; + } + handleParseResult(result); + }); } - if (typeof path === "function") { - path = path(data, assetInfo); + /** + * @param {ConcatenationBailoutReasonContext} context context + * @returns {string | undefined} reason why this module can't be concatenated, undefined when it can be concatenated + */ + getConcatenationBailoutReason(context) { + return this.generator.getConcatenationBailoutReason(this, context); } - path = path.replace(REGEXP, (match, content) => { - if (content.length + 2 === match.length) { - const contentMatch = /^(\w+)(?::(\w+))?$/.exec(content); - if (!contentMatch) return match; - const [, kind, arg] = contentMatch; - const replacer = replacements.get(kind); - if (replacer !== undefined) { - return replacer(match, arg, path); + /** + * @param {ModuleGraph} moduleGraph the module graph + * @returns {ConnectionState} how this module should be connected to referencing modules when consumed for side-effects only + */ + getSideEffectsConnectionState(moduleGraph) { + if (this.factoryMeta !== undefined) { + if (this.factoryMeta.sideEffectFree) return false; + if (this.factoryMeta.sideEffectFree === false) return true; + } + if (this.buildMeta !== undefined && this.buildMeta.sideEffectFree) { + if (this._isEvaluatingSideEffects) + return ModuleGraphConnection.CIRCULAR_CONNECTION; + this._isEvaluatingSideEffects = true; + /** @type {ConnectionState} */ + let current = false; + for (const dep of this.dependencies) { + const state = dep.getModuleEvaluationSideEffectsState(moduleGraph); + if (state === true) { + if ( + this._addedSideEffectsBailout === undefined + ? ((this._addedSideEffectsBailout = new WeakSet()), true) + : !this._addedSideEffectsBailout.has(moduleGraph) + ) { + this._addedSideEffectsBailout.add(moduleGraph); + moduleGraph + .getOptimizationBailout(this) + .push( + () => + `Dependency (${ + dep.type + }) with side effects at ${formatLocation(dep.loc)}` + ); + } + this._isEvaluatingSideEffects = false; + return true; + } else if (state !== ModuleGraphConnection.CIRCULAR_CONNECTION) { + current = ModuleGraphConnection.addConnectionStates(current, state); + } } - } else if (match.startsWith("[\\") && match.endsWith("\\]")) { - return `[${match.slice(2, -2)}]`; + this._isEvaluatingSideEffects = false; + // When caching is implemented here, make sure to not cache when + // at least one circular connection was in the loop above + return current; + } else { + return true; } - return match; - }); - - return path; -}; - -const plugin = "TemplatedPathPlugin"; + } -class TemplatedPathPlugin { /** - * Apply the plugin - * @param {Compiler} compiler the compiler instance - * @returns {void} + * @returns {Set} types available (do not mutate) */ - apply(compiler) { - compiler.hooks.compilation.tap(plugin, compilation => { - compilation.hooks.assetPath.tap(plugin, replacePathVariables); - }); + getSourceTypes() { + if (this._sourceTypes === undefined) { + this._sourceTypes = this.generator.getTypes(this); + } + return this._sourceTypes; } -} -module.exports = TemplatedPathPlugin; - - -/***/ }), + /** + * @param {CodeGenerationContext} context context for code generation + * @returns {CodeGenerationResult} result + */ + codeGeneration({ + dependencyTemplates, + runtimeTemplate, + moduleGraph, + chunkGraph, + runtime, + concatenationScope + }) { + /** @type {Set} */ + const runtimeRequirements = new Set(); -/***/ 63859: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + if (!this.buildInfo.parsed) { + runtimeRequirements.add(RuntimeGlobals.module); + runtimeRequirements.add(RuntimeGlobals.exports); + runtimeRequirements.add(RuntimeGlobals.thisAsExports); + } -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Ivan Kopeykin @vankop -*/ + /** @type {Map} */ + let data; + const getData = () => { + if (data === undefined) data = new Map(); + return data; + }; + const sources = new Map(); + for (const type of this.generator.getTypes(this)) { + const source = this.error + ? new RawSource( + "throw new Error(" + JSON.stringify(this.error.message) + ");" + ) + : this.generator.generate(this, { + dependencyTemplates, + runtimeTemplate, + moduleGraph, + chunkGraph, + runtimeRequirements, + runtime, + concatenationScope, + getData, + type + }); + if (source) { + sources.set(type, new CachedSource(source)); + } + } -const WebpackError = __webpack_require__(68422); -const makeSerializable = __webpack_require__(26522); + /** @type {CodeGenerationResult} */ + const resultEntry = { + sources, + runtimeRequirements, + data + }; + return resultEntry; + } -class UnhandledSchemeError extends WebpackError { /** - * @param {string} scheme scheme - * @param {string} resource resource + * @returns {Source | null} the original source for the module before webpack transformation */ - constructor(scheme, resource) { - super( - `Reading from "${resource}" is not handled by plugins (Unhandled scheme).` + - '\nWebpack supports "data:" and "file:" URIs by default.' + - `\nYou may need an additional plugin to handle "${scheme}:" URIs.` - ); - this.file = resource; - this.name = "UnhandledSchemeError"; + originalSource() { + return this._source; } -} - -makeSerializable( - UnhandledSchemeError, - "webpack/lib/UnhandledSchemeError", - "UnhandledSchemeError" -); - -module.exports = UnhandledSchemeError; - - -/***/ }), - -/***/ 9532: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ - - - -const WebpackError = __webpack_require__(68422); -const makeSerializable = __webpack_require__(26522); - -/** @typedef {import("./Dependency").DependencyLocation} DependencyLocation */ -class UnsupportedFeatureWarning extends WebpackError { /** - * @param {string} message description of warning - * @param {DependencyLocation} loc location start and end positions of the module + * @returns {void} */ - constructor(message, loc) { - super(message); - - this.name = "UnsupportedFeatureWarning"; - this.loc = loc; - this.hideStack = true; + invalidateBuild() { + this._forceBuild = true; } -} - -makeSerializable( - UnsupportedFeatureWarning, - "webpack/lib/UnsupportedFeatureWarning" -); - -module.exports = UnsupportedFeatureWarning; + /** + * @param {NeedBuildContext} context context info + * @param {function(WebpackError=, boolean=): void} callback callback function, returns true, if the module needs a rebuild + * @returns {void} + */ + needBuild(context, callback) { + const { fileSystemInfo, compilation, valueCacheVersions } = context; + // build if enforced + if (this._forceBuild) return callback(null, true); -/***/ }), + // always try to build in case of an error + if (this.error) return callback(null, true); -/***/ 15466: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + // always build when module is not cacheable + if (!this.buildInfo.cacheable) return callback(null, true); -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ + // build when there is no snapshot to check + if (!this.buildInfo.snapshot) return callback(null, true); + // build when valueDependencies have changed + /** @type {Map>} */ + const valueDependencies = this.buildInfo.valueDependencies; + if (valueDependencies) { + if (!valueCacheVersions) return callback(null, true); + for (const [key, value] of valueDependencies) { + if (value === undefined) return callback(null, true); + const current = valueCacheVersions.get(key); + if ( + value !== current && + (typeof value === "string" || + typeof current === "string" || + current === undefined || + !isSubset(value, current)) + ) { + return callback(null, true); + } + } + } + // check snapshot for validity + fileSystemInfo.checkSnapshotValid(this.buildInfo.snapshot, (err, valid) => { + if (err) return callback(err); + if (!valid) return callback(null, true); + const hooks = NormalModule.getCompilationHooks(compilation); + hooks.needBuild.callAsync(this, context, (err, needBuild) => { + if (err) { + return callback( + HookWebpackError.makeWebpackError( + err, + "NormalModule.getCompilationHooks().needBuild" + ) + ); + } + callback(null, !!needBuild); + }); + }); + } -const ConstDependency = __webpack_require__(60864); + /** + * @param {string=} type the source type for which the size should be estimated + * @returns {number} the estimated size of the module (must be non-zero) + */ + size(type) { + const cachedSize = + this._sourceSizes === undefined ? undefined : this._sourceSizes.get(type); + if (cachedSize !== undefined) { + return cachedSize; + } + const size = Math.max(1, this.generator.getSize(this, type)); + if (this._sourceSizes === undefined) { + this._sourceSizes = new Map(); + } + this._sourceSizes.set(type, size); + return size; + } -/** @typedef {import("./Compiler")} Compiler */ + /** + * @param {LazySet} fileDependencies set where file dependencies are added to + * @param {LazySet} contextDependencies set where context dependencies are added to + * @param {LazySet} missingDependencies set where missing dependencies are added to + * @param {LazySet} buildDependencies set where build dependencies are added to + */ + addCacheDependencies( + fileDependencies, + contextDependencies, + missingDependencies, + buildDependencies + ) { + const { snapshot, buildDependencies: buildDeps } = this.buildInfo; + if (snapshot) { + fileDependencies.addAll(snapshot.getFileIterable()); + contextDependencies.addAll(snapshot.getContextIterable()); + missingDependencies.addAll(snapshot.getMissingIterable()); + } else { + const { + fileDependencies: fileDeps, + contextDependencies: contextDeps, + missingDependencies: missingDeps + } = this.buildInfo; + if (fileDeps !== undefined) fileDependencies.addAll(fileDeps); + if (contextDeps !== undefined) contextDependencies.addAll(contextDeps); + if (missingDeps !== undefined) missingDependencies.addAll(missingDeps); + } + if (buildDeps !== undefined) { + buildDependencies.addAll(buildDeps); + } + } -class UseStrictPlugin { /** - * Apply the plugin - * @param {Compiler} compiler the compiler instance + * @param {Hash} hash the hash used to track dependencies + * @param {UpdateHashContext} context context * @returns {void} */ - apply(compiler) { - compiler.hooks.compilation.tap( - "UseStrictPlugin", - (compilation, { normalModuleFactory }) => { - const handler = parser => { - parser.hooks.program.tap("UseStrictPlugin", ast => { - const firstNode = ast.body[0]; - if ( - firstNode && - firstNode.type === "ExpressionStatement" && - firstNode.expression.type === "Literal" && - firstNode.expression.value === "use strict" - ) { - // Remove "use strict" expression. It will be added later by the renderer again. - // This is necessary in order to not break the strict mode when webpack prepends code. - // @see https://github.com/webpack/webpack/issues/1970 - const dep = new ConstDependency("", firstNode.range); - dep.loc = firstNode.loc; - parser.state.module.addPresentationalDependency(dep); - parser.state.module.buildInfo.strict = true; - } - }); - }; - - normalModuleFactory.hooks.parser - .for("javascript/auto") - .tap("UseStrictPlugin", handler); - normalModuleFactory.hooks.parser - .for("javascript/dynamic") - .tap("UseStrictPlugin", handler); - normalModuleFactory.hooks.parser - .for("javascript/esm") - .tap("UseStrictPlugin", handler); - } - ); + updateHash(hash, context) { + hash.update(this.buildInfo.hash); + this.generator.updateHash(hash, { + module: this, + ...context + }); + super.updateHash(hash, context); } -} - -module.exports = UseStrictPlugin; - - -/***/ }), - -/***/ 33304: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ - + serialize(context) { + const { write } = context; + // deserialize + write(this._source); + write(this.error); + write(this._lastSuccessfulBuildMeta); + write(this._forceBuild); + super.serialize(context); + } -const CaseSensitiveModulesWarning = __webpack_require__(42444); - -/** @typedef {import("./Compiler")} Compiler */ -/** @typedef {import("./Module")} Module */ + static deserialize(context) { + const obj = new NormalModule({ + // will be deserialized by Module + layer: null, + type: "", + // will be filled by updateCacheModule + resource: "", + context: "", + request: null, + userRequest: null, + rawRequest: null, + loaders: null, + matchResource: null, + parser: null, + parserOptions: null, + generator: null, + generatorOptions: null, + resolveOptions: null + }); + obj.deserialize(context); + return obj; + } -class WarnCaseSensitiveModulesPlugin { - /** - * Apply the plugin - * @param {Compiler} compiler the compiler instance - * @returns {void} - */ - apply(compiler) { - compiler.hooks.compilation.tap( - "WarnCaseSensitiveModulesPlugin", - compilation => { - compilation.hooks.seal.tap("WarnCaseSensitiveModulesPlugin", () => { - /** @type {Map>} */ - const moduleWithoutCase = new Map(); - for (const module of compilation.modules) { - const identifier = module.identifier(); - const lowerIdentifier = identifier.toLowerCase(); - let map = moduleWithoutCase.get(lowerIdentifier); - if (map === undefined) { - map = new Map(); - moduleWithoutCase.set(lowerIdentifier, map); - } - map.set(identifier, module); - } - for (const pair of moduleWithoutCase) { - const map = pair[1]; - if (map.size > 1) { - compilation.warnings.push( - new CaseSensitiveModulesWarning( - map.values(), - compilation.moduleGraph - ) - ); - } - } - }); - } - ); + deserialize(context) { + const { read } = context; + this._source = read(); + this.error = read(); + this._lastSuccessfulBuildMeta = read(); + this._forceBuild = read(); + super.deserialize(context); } } -module.exports = WarnCaseSensitiveModulesPlugin; +makeSerializable(NormalModule, "webpack/lib/NormalModule"); + +module.exports = NormalModule; /***/ }), -/***/ 85024: +/***/ 99063: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; /* MIT License http://www.opensource.org/licenses/mit-license.php - Author Florent Cailhol @ooflorent + Author Tobias Koppers @sokra */ -const WebpackError = __webpack_require__(68422); +const { getContext } = __webpack_require__(67578); +const asyncLib = __webpack_require__(36386); +const { + AsyncSeriesBailHook, + SyncWaterfallHook, + SyncBailHook, + SyncHook, + HookMap +} = __webpack_require__(34718); +const ChunkGraph = __webpack_require__(97860); +const Module = __webpack_require__(85887); +const ModuleFactory = __webpack_require__(61574); +const ModuleGraph = __webpack_require__(20258); +const NormalModule = __webpack_require__(11026); +const BasicEffectRulePlugin = __webpack_require__(70119); +const BasicMatcherRulePlugin = __webpack_require__(99083); +const ObjectMatcherRulePlugin = __webpack_require__(61166); +const RuleSetCompiler = __webpack_require__(23246); +const UseEffectRulePlugin = __webpack_require__(42541); +const LazySet = __webpack_require__(59534); +const { getScheme } = __webpack_require__(49606); +const { cachedCleverMerge, cachedSetProperty } = __webpack_require__(11217); +const { join } = __webpack_require__(93204); +const { parseResource } = __webpack_require__(96236); -/** @typedef {import("./Compiler")} Compiler */ +/** @typedef {import("../declarations/WebpackOptions").ModuleOptionsNormalized} ModuleOptions */ +/** @typedef {import("./Generator")} Generator */ +/** @typedef {import("./ModuleFactory").ModuleFactoryCreateData} ModuleFactoryCreateData */ +/** @typedef {import("./ModuleFactory").ModuleFactoryResult} ModuleFactoryResult */ +/** @typedef {import("./Parser")} Parser */ +/** @typedef {import("./ResolverFactory")} ResolverFactory */ +/** @typedef {import("./dependencies/ModuleDependency")} ModuleDependency */ +/** @typedef {import("./util/fs").InputFileSystem} InputFileSystem */ -class WarnDeprecatedOptionPlugin { - /** - * Create an instance of the plugin - * @param {string} option the target option - * @param {string | number} value the deprecated option value - * @param {string} suggestion the suggestion replacement - */ - constructor(option, value, suggestion) { - this.option = option; - this.value = value; - this.suggestion = suggestion; - } +/** + * @typedef {Object} ResolveData + * @property {ModuleFactoryCreateData["contextInfo"]} contextInfo + * @property {ModuleFactoryCreateData["resolveOptions"]} resolveOptions + * @property {string} context + * @property {string} request + * @property {Record | undefined} assertions + * @property {ModuleDependency[]} dependencies + * @property {string} dependencyType + * @property {Object} createData + * @property {LazySet} fileDependencies + * @property {LazySet} missingDependencies + * @property {LazySet} contextDependencies + * @property {boolean} cacheable allow to use the unsafe cache + */ - /** - * Apply the plugin - * @param {Compiler} compiler the compiler instance - * @returns {void} - */ - apply(compiler) { - compiler.hooks.thisCompilation.tap( - "WarnDeprecatedOptionPlugin", - compilation => { - compilation.warnings.push( - new DeprecatedOptionWarning(this.option, this.value, this.suggestion) - ); - } - ); - } -} +/** + * @typedef {Object} ResourceData + * @property {string} resource + * @property {string} path + * @property {string} query + * @property {string} fragment + * @property {string=} context + */ -class DeprecatedOptionWarning extends WebpackError { - constructor(option, value, suggestion) { - super(); +/** @typedef {ResourceData & { data: Record }} ResourceDataWithData */ - this.name = "DeprecatedOptionWarning"; - this.message = - "configuration\n" + - `The value '${value}' for option '${option}' is deprecated. ` + - `Use '${suggestion}' instead.`; - } -} +const EMPTY_RESOLVE_OPTIONS = {}; +const EMPTY_PARSER_OPTIONS = {}; +const EMPTY_GENERATOR_OPTIONS = {}; +const EMPTY_ELEMENTS = []; -module.exports = WarnDeprecatedOptionPlugin; +const MATCH_RESOURCE_REGEX = /^([^!]+)!=!/; +const loaderToIdent = data => { + if (!data.options) { + return data.loader; + } + if (typeof data.options === "string") { + return data.loader + "?" + data.options; + } + if (typeof data.options !== "object") { + throw new Error("loader options must be string or object"); + } + if (data.ident) { + return data.loader + "??" + data.ident; + } + return data.loader + "?" + JSON.stringify(data.options); +}; -/***/ }), +const stringifyLoadersAndResource = (loaders, resource) => { + let str = ""; + for (const loader of loaders) { + str += loaderToIdent(loader) + "!"; + } + return str + resource; +}; -/***/ 70308: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { +/** + * @param {string} resultString resultString + * @returns {{loader: string, options: string|undefined}} parsed loader request + */ +const identToLoaderRequest = resultString => { + const idx = resultString.indexOf("?"); + if (idx >= 0) { + const loader = resultString.substr(0, idx); + const options = resultString.substr(idx + 1); + return { + loader, + options + }; + } else { + return { + loader: resultString, + options: undefined + }; + } +}; -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ +const needCalls = (times, callback) => { + return err => { + if (--times === 0) { + return callback(err); + } + if (err && times > 0) { + times = NaN; + return callback(err); + } + }; +}; +const mergeGlobalOptions = (globalOptions, type, localOptions) => { + const parts = type.split("/"); + let result; + let current = ""; + for (const part of parts) { + current = current ? `${current}/${part}` : part; + const options = globalOptions[current]; + if (typeof options === "object") { + if (result === undefined) { + result = options; + } else { + result = cachedCleverMerge(result, options); + } + } + } + if (result === undefined) { + return localOptions; + } else { + return cachedCleverMerge(result, localOptions); + } +}; +// TODO webpack 6 remove +const deprecationChangedHookMessage = (name, hook) => { + const names = hook.taps + .map(tapped => { + return tapped.name; + }) + .join(", "); -const NoModeWarning = __webpack_require__(84991); + return ( + `NormalModuleFactory.${name} (${names}) is no longer a waterfall hook, but a bailing hook instead. ` + + "Do not return the passed object, but modify it instead. " + + "Returning false will ignore the request and results in no module created." + ); +}; -/** @typedef {import("./Compiler")} Compiler */ +const ruleSetCompiler = new RuleSetCompiler([ + new BasicMatcherRulePlugin("test", "resource"), + new BasicMatcherRulePlugin("scheme"), + new BasicMatcherRulePlugin("mimetype"), + new BasicMatcherRulePlugin("dependency"), + new BasicMatcherRulePlugin("include", "resource"), + new BasicMatcherRulePlugin("exclude", "resource", true), + new BasicMatcherRulePlugin("resource"), + new BasicMatcherRulePlugin("resourceQuery"), + new BasicMatcherRulePlugin("resourceFragment"), + new BasicMatcherRulePlugin("realResource"), + new BasicMatcherRulePlugin("issuer"), + new BasicMatcherRulePlugin("compiler"), + new BasicMatcherRulePlugin("issuerLayer"), + new ObjectMatcherRulePlugin("assert", "assertions"), + new ObjectMatcherRulePlugin("descriptionData"), + new BasicEffectRulePlugin("type"), + new BasicEffectRulePlugin("sideEffects"), + new BasicEffectRulePlugin("parser"), + new BasicEffectRulePlugin("resolve"), + new BasicEffectRulePlugin("generator"), + new BasicEffectRulePlugin("layer"), + new UseEffectRulePlugin() +]); -class WarnNoModeSetPlugin { +class NormalModuleFactory extends ModuleFactory { /** - * Apply the plugin - * @param {Compiler} compiler the compiler instance - * @returns {void} + * @param {Object} param params + * @param {string=} param.context context + * @param {InputFileSystem} param.fs file system + * @param {ResolverFactory} param.resolverFactory resolverFactory + * @param {ModuleOptions} param.options options + * @param {Object=} param.associatedObjectForCache an object to which the cache will be attached + * @param {boolean=} param.layers enable layers */ - apply(compiler) { - compiler.hooks.thisCompilation.tap("WarnNoModeSetPlugin", compilation => { - compilation.warnings.push(new NoModeWarning()); + constructor({ + context, + fs, + resolverFactory, + options, + associatedObjectForCache, + layers = false + }) { + super(); + this.hooks = Object.freeze({ + /** @type {AsyncSeriesBailHook<[ResolveData], TODO>} */ + resolve: new AsyncSeriesBailHook(["resolveData"]), + /** @type {HookMap>} */ + resolveForScheme: new HookMap( + () => new AsyncSeriesBailHook(["resourceData", "resolveData"]) + ), + /** @type {HookMap>} */ + resolveInScheme: new HookMap( + () => new AsyncSeriesBailHook(["resourceData", "resolveData"]) + ), + /** @type {AsyncSeriesBailHook<[ResolveData], TODO>} */ + factorize: new AsyncSeriesBailHook(["resolveData"]), + /** @type {AsyncSeriesBailHook<[ResolveData], TODO>} */ + beforeResolve: new AsyncSeriesBailHook(["resolveData"]), + /** @type {AsyncSeriesBailHook<[ResolveData], TODO>} */ + afterResolve: new AsyncSeriesBailHook(["resolveData"]), + /** @type {AsyncSeriesBailHook<[ResolveData["createData"], ResolveData], TODO>} */ + createModule: new AsyncSeriesBailHook(["createData", "resolveData"]), + /** @type {SyncWaterfallHook<[Module, ResolveData["createData"], ResolveData], TODO>} */ + module: new SyncWaterfallHook(["module", "createData", "resolveData"]), + createParser: new HookMap(() => new SyncBailHook(["parserOptions"])), + parser: new HookMap(() => new SyncHook(["parser", "parserOptions"])), + createGenerator: new HookMap( + () => new SyncBailHook(["generatorOptions"]) + ), + generator: new HookMap( + () => new SyncHook(["generator", "generatorOptions"]) + ) }); - } -} - -module.exports = WarnNoModeSetPlugin; - - -/***/ }), - -/***/ 90187: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + this.resolverFactory = resolverFactory; + this.ruleSet = ruleSetCompiler.compile([ + { + rules: options.defaultRules + }, + { + rules: options.rules + } + ]); + this.context = context || ""; + this.fs = fs; + this._globalParserOptions = options.parser; + this._globalGeneratorOptions = options.generator; + /** @type {Map>} */ + this.parserCache = new Map(); + /** @type {Map>} */ + this.generatorCache = new Map(); + /** @type {Set} */ + this._restoredUnsafeCacheEntries = new Set(); -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ + const cacheParseResource = parseResource.bindCache( + associatedObjectForCache + ); + this.hooks.factorize.tapAsync( + { + name: "NormalModuleFactory", + stage: 100 + }, + (resolveData, callback) => { + this.hooks.resolve.callAsync(resolveData, (err, result) => { + if (err) return callback(err); + // Ignored + if (result === false) return callback(); -const { groupBy } = __webpack_require__(21537); -const createSchemaValidation = __webpack_require__(77695); + // direct module + if (result instanceof Module) return callback(null, result); -/** @typedef {import("../declarations/plugins/WatchIgnorePlugin").WatchIgnorePluginOptions} WatchIgnorePluginOptions */ -/** @typedef {import("./Compiler")} Compiler */ -/** @typedef {import("./util/fs").WatchFileSystem} WatchFileSystem */ + if (typeof result === "object") + throw new Error( + deprecationChangedHookMessage("resolve", this.hooks.resolve) + + " Returning a Module object will result in this module used as result." + ); -const validate = createSchemaValidation( - __webpack_require__(16779), - () => __webpack_require__(66489), - { - name: "Watch Ignore Plugin", - baseDataPath: "options" - } -); + this.hooks.afterResolve.callAsync(resolveData, (err, result) => { + if (err) return callback(err); -const IGNORE_TIME_ENTRY = "ignore"; + if (typeof result === "object") + throw new Error( + deprecationChangedHookMessage( + "afterResolve", + this.hooks.afterResolve + ) + ); -class IgnoringWatchFileSystem { - /** - * @param {WatchFileSystem} wfs original file system - * @param {(string|RegExp)[]} paths ignored paths - */ - constructor(wfs, paths) { - this.wfs = wfs; - this.paths = paths; - } + // Ignored + if (result === false) return callback(); - watch(files, dirs, missing, startTime, options, callback, callbackUndelayed) { - files = Array.from(files); - dirs = Array.from(dirs); - const ignored = path => - this.paths.some(p => - p instanceof RegExp ? p.test(path) : path.indexOf(p) === 0 - ); + const createData = resolveData.createData; - const [ignoredFiles, notIgnoredFiles] = groupBy(files, ignored); - const [ignoredDirs, notIgnoredDirs] = groupBy(dirs, ignored); + this.hooks.createModule.callAsync( + createData, + resolveData, + (err, createdModule) => { + if (!createdModule) { + if (!resolveData.request) { + return callback(new Error("Empty dependency (no request)")); + } - const watcher = this.wfs.watch( - notIgnoredFiles, - notIgnoredDirs, - missing, - startTime, - options, - (err, fileTimestamps, dirTimestamps, changedFiles, removedFiles) => { - if (err) return callback(err); - for (const path of ignoredFiles) { - fileTimestamps.set(path, IGNORE_TIME_ENTRY); - } + createdModule = new NormalModule(createData); + } - for (const path of ignoredDirs) { - dirTimestamps.set(path, IGNORE_TIME_ENTRY); - } + createdModule = this.hooks.module.call( + createdModule, + createData, + resolveData + ); - callback( - err, - fileTimestamps, - dirTimestamps, - changedFiles, - removedFiles - ); - }, - callbackUndelayed + return callback(null, createdModule); + } + ); + }); + }); + } ); - - return { - close: () => watcher.close(), - pause: () => watcher.pause(), - getContextTimeInfoEntries: () => { - const dirTimestamps = watcher.getContextTimeInfoEntries(); - for (const path of ignoredDirs) { - dirTimestamps.set(path, IGNORE_TIME_ENTRY); - } - return dirTimestamps; + this.hooks.resolve.tapAsync( + { + name: "NormalModuleFactory", + stage: 100 }, - getFileTimeInfoEntries: () => { - const fileTimestamps = watcher.getFileTimeInfoEntries(); - for (const path of ignoredFiles) { - fileTimestamps.set(path, IGNORE_TIME_ENTRY); - } - return fileTimestamps; - } - }; - } -} - -class WatchIgnorePlugin { - /** - * @param {WatchIgnorePluginOptions} options options - */ - constructor(options) { - validate(options); - this.paths = options.paths; - } - - /** - * Apply the plugin - * @param {Compiler} compiler the compiler instance - * @returns {void} - */ - apply(compiler) { - compiler.hooks.afterEnvironment.tap("WatchIgnorePlugin", () => { - compiler.watchFileSystem = new IgnoringWatchFileSystem( - compiler.watchFileSystem, - this.paths - ); - }); - } -} - -module.exports = WatchIgnorePlugin; + (data, callback) => { + const { + contextInfo, + context, + dependencies, + dependencyType, + request, + assertions, + resolveOptions, + fileDependencies, + missingDependencies, + contextDependencies + } = data; + const loaderResolver = this.getResolver("loader"); + /** @type {ResourceData | undefined} */ + let matchResourceData = undefined; + /** @type {string} */ + let unresolvedResource; + /** @type {{loader: string, options: string|undefined}[]} */ + let elements; + let noPreAutoLoaders = false; + let noAutoLoaders = false; + let noPrePostAutoLoaders = false; -/***/ }), + const contextScheme = getScheme(context); + /** @type {string | undefined} */ + let scheme = getScheme(request); -/***/ 49819: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + if (!scheme) { + /** @type {string} */ + let requestWithoutMatchResource = request; + const matchResourceMatch = MATCH_RESOURCE_REGEX.exec(request); + if (matchResourceMatch) { + let matchResource = matchResourceMatch[1]; + if (matchResource.charCodeAt(0) === 46) { + // 46 === ".", 47 === "/" + const secondChar = matchResource.charCodeAt(1); + if ( + secondChar === 47 || + (secondChar === 46 && matchResource.charCodeAt(2) === 47) + ) { + // if matchResources startsWith ../ or ./ + matchResource = join(this.fs, context, matchResource); + } + } + matchResourceData = { + resource: matchResource, + ...cacheParseResource(matchResource) + }; + requestWithoutMatchResource = request.substr( + matchResourceMatch[0].length + ); + } -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ + scheme = getScheme(requestWithoutMatchResource); + if (!scheme && !contextScheme) { + const firstChar = requestWithoutMatchResource.charCodeAt(0); + const secondChar = requestWithoutMatchResource.charCodeAt(1); + noPreAutoLoaders = firstChar === 45 && secondChar === 33; // startsWith "-!" + noAutoLoaders = noPreAutoLoaders || firstChar === 33; // startsWith "!" + noPrePostAutoLoaders = firstChar === 33 && secondChar === 33; // startsWith "!!"; + const rawElements = requestWithoutMatchResource + .slice( + noPreAutoLoaders || noPrePostAutoLoaders + ? 2 + : noAutoLoaders + ? 1 + : 0 + ) + .split(/!+/); + unresolvedResource = rawElements.pop(); + elements = rawElements.map(identToLoaderRequest); + scheme = getScheme(unresolvedResource); + } else { + unresolvedResource = requestWithoutMatchResource; + elements = EMPTY_ELEMENTS; + } + } else { + unresolvedResource = request; + elements = EMPTY_ELEMENTS; + } + const resolveContext = { + fileDependencies, + missingDependencies, + contextDependencies + }; -const Stats = __webpack_require__(87797); + /** @type {ResourceDataWithData} */ + let resourceData; -/** @typedef {import("../declarations/WebpackOptions").WatchOptions} WatchOptions */ -/** @typedef {import("./Compilation")} Compilation */ -/** @typedef {import("./Compiler")} Compiler */ -/** @typedef {import("./FileSystemInfo").FileSystemInfoEntry} FileSystemInfoEntry */ + let loaders; -/** - * @template T - * @callback Callback - * @param {Error=} err - * @param {T=} result - */ + const continueCallback = needCalls(2, err => { + if (err) return callback(err); -class Watching { - /** - * @param {Compiler} compiler the compiler - * @param {WatchOptions} watchOptions options - * @param {Callback} handler completion handler - */ - constructor(compiler, watchOptions, handler) { - this.startTime = null; - this.invalid = false; - this.handler = handler; - /** @type {Callback[]} */ - this.callbacks = []; - /** @type {Callback[] | undefined} */ - this._closeCallbacks = undefined; - this.closed = false; - this.suspended = false; - this.blocked = false; - this._isBlocked = () => false; - this._onChange = () => {}; - this._onInvalid = () => {}; - if (typeof watchOptions === "number") { - this.watchOptions = { - aggregateTimeout: watchOptions - }; - } else if (watchOptions && typeof watchOptions === "object") { - this.watchOptions = { ...watchOptions }; - } else { - this.watchOptions = {}; - } - if (typeof this.watchOptions.aggregateTimeout !== "number") { - this.watchOptions.aggregateTimeout = 200; - } - this.compiler = compiler; - this.running = false; - this._initial = true; - this._invalidReported = true; - this._needRecords = true; - this.watcher = undefined; - this.pausedWatcher = undefined; - /** @type {Set} */ - this._collectedChangedFiles = undefined; - /** @type {Set} */ - this._collectedRemovedFiles = undefined; - this._done = this._done.bind(this); - process.nextTick(() => { - if (this._initial) this._invalidate(); - }); - } + // translate option idents + try { + for (const item of loaders) { + if (typeof item.options === "string" && item.options[0] === "?") { + const ident = item.options.substr(1); + if (ident === "[[missing ident]]") { + throw new Error( + "No ident is provided by referenced loader. " + + "When using a function for Rule.use in config you need to " + + "provide an 'ident' property for referenced loader options." + ); + } + item.options = this.ruleSet.references.get(ident); + if (item.options === undefined) { + throw new Error( + "Invalid ident is provided by referenced loader" + ); + } + item.ident = ident; + } + } + } catch (e) { + return callback(e); + } - /** - * @param {ReadonlySet} changedFiles changed files - * @param {ReadonlySet} removedFiles removed files - */ - _mergeWithCollected(changedFiles, removedFiles) { - if (!changedFiles) return; - if (!this._collectedChangedFiles) { - this._collectedChangedFiles = new Set(changedFiles); - this._collectedRemovedFiles = new Set(removedFiles); - } else { - for (const file of changedFiles) { - this._collectedChangedFiles.add(file); - this._collectedRemovedFiles.delete(file); - } - for (const file of removedFiles) { - this._collectedChangedFiles.delete(file); - this._collectedRemovedFiles.add(file); - } - } - } + if (!resourceData) { + // ignored + return callback(null, dependencies[0].createIgnoredModule(context)); + } - /** - * @param {ReadonlyMap=} fileTimeInfoEntries info for files - * @param {ReadonlyMap=} contextTimeInfoEntries info for directories - * @param {ReadonlySet=} changedFiles changed files - * @param {ReadonlySet=} removedFiles removed files - * @returns {void} - */ - _go(fileTimeInfoEntries, contextTimeInfoEntries, changedFiles, removedFiles) { - this._initial = false; - if (this.startTime === null) this.startTime = Date.now(); - this.running = true; - if (this.watcher) { - this.pausedWatcher = this.watcher; - this.lastWatcherStartTime = Date.now(); - this.watcher.pause(); - this.watcher = null; - } else if (!this.lastWatcherStartTime) { - this.lastWatcherStartTime = Date.now(); - } - this.compiler.fsStartTime = Date.now(); - this._mergeWithCollected( - changedFiles || - (this.pausedWatcher && - this.pausedWatcher.getAggregatedChanges && - this.pausedWatcher.getAggregatedChanges()), - (this.compiler.removedFiles = - removedFiles || - (this.pausedWatcher && - this.pausedWatcher.getAggregatedRemovals && - this.pausedWatcher.getAggregatedRemovals())) - ); + const userRequest = + (matchResourceData !== undefined + ? `${matchResourceData.resource}!=!` + : "") + + stringifyLoadersAndResource(loaders, resourceData.resource); - this.compiler.modifiedFiles = this._collectedChangedFiles; - this._collectedChangedFiles = undefined; - this.compiler.removedFiles = this._collectedRemovedFiles; - this._collectedRemovedFiles = undefined; + const settings = {}; + const useLoadersPost = []; + const useLoaders = []; + const useLoadersPre = []; - this.compiler.fileTimestamps = - fileTimeInfoEntries || - (this.pausedWatcher && this.pausedWatcher.getFileTimeInfoEntries()); - this.compiler.contextTimestamps = - contextTimeInfoEntries || - (this.pausedWatcher && this.pausedWatcher.getContextTimeInfoEntries()); + // handle .webpack[] suffix + let resource; + let match; + if ( + matchResourceData && + typeof (resource = matchResourceData.resource) === "string" && + (match = /\.webpack\[([^\]]+)\]$/.exec(resource)) + ) { + settings.type = match[1]; + matchResourceData.resource = matchResourceData.resource.slice( + 0, + -settings.type.length - 10 + ); + } else { + settings.type = "javascript/auto"; + const resourceDataForRules = matchResourceData || resourceData; + const result = this.ruleSet.exec({ + resource: resourceDataForRules.path, + realResource: resourceData.path, + resourceQuery: resourceDataForRules.query, + resourceFragment: resourceDataForRules.fragment, + scheme, + assertions, + mimetype: matchResourceData + ? "" + : resourceData.data.mimetype || "", + dependency: dependencyType, + descriptionData: matchResourceData + ? undefined + : resourceData.data.descriptionFileData, + issuer: contextInfo.issuer, + compiler: contextInfo.compiler, + issuerLayer: contextInfo.issuerLayer || "" + }); + for (const r of result) { + if (r.type === "use") { + if (!noAutoLoaders && !noPrePostAutoLoaders) { + useLoaders.push(r.value); + } + } else if (r.type === "use-post") { + if (!noPrePostAutoLoaders) { + useLoadersPost.push(r.value); + } + } else if (r.type === "use-pre") { + if (!noPreAutoLoaders && !noPrePostAutoLoaders) { + useLoadersPre.push(r.value); + } + } else if ( + typeof r.value === "object" && + r.value !== null && + typeof settings[r.type] === "object" && + settings[r.type] !== null + ) { + settings[r.type] = cachedCleverMerge(settings[r.type], r.value); + } else { + settings[r.type] = r.value; + } + } + } - const run = () => { - if (this.compiler.idle) { - return this.compiler.cache.endIdle(err => { - if (err) return this._done(err); - this.compiler.idle = false; - run(); - }); - } - if (this._needRecords) { - return this.compiler.readRecords(err => { - if (err) return this._done(err); + let postLoaders, normalLoaders, preLoaders; - this._needRecords = false; - run(); + const continueCallback = needCalls(3, err => { + if (err) { + return callback(err); + } + const allLoaders = postLoaders; + if (matchResourceData === undefined) { + for (const loader of loaders) allLoaders.push(loader); + for (const loader of normalLoaders) allLoaders.push(loader); + } else { + for (const loader of normalLoaders) allLoaders.push(loader); + for (const loader of loaders) allLoaders.push(loader); + } + for (const loader of preLoaders) allLoaders.push(loader); + let type = settings.type; + const resolveOptions = settings.resolve; + const layer = settings.layer; + if (layer !== undefined && !layers) { + return callback( + new Error( + "'Rule.layer' is only allowed when 'experiments.layers' is enabled" + ) + ); + } + try { + Object.assign(data.createData, { + layer: + layer === undefined ? contextInfo.issuerLayer || null : layer, + request: stringifyLoadersAndResource( + allLoaders, + resourceData.resource + ), + userRequest, + rawRequest: request, + loaders: allLoaders, + resource: resourceData.resource, + context: + resourceData.context || getContext(resourceData.resource), + matchResource: matchResourceData + ? matchResourceData.resource + : undefined, + resourceResolveData: resourceData.data, + settings, + type, + parser: this.getParser(type, settings.parser), + parserOptions: settings.parser, + generator: this.getGenerator(type, settings.generator), + generatorOptions: settings.generator, + resolveOptions + }); + } catch (e) { + return callback(e); + } + callback(); + }); + this.resolveRequestArray( + contextInfo, + this.context, + useLoadersPost, + loaderResolver, + resolveContext, + (err, result) => { + postLoaders = result; + continueCallback(err); + } + ); + this.resolveRequestArray( + contextInfo, + this.context, + useLoaders, + loaderResolver, + resolveContext, + (err, result) => { + normalLoaders = result; + continueCallback(err); + } + ); + this.resolveRequestArray( + contextInfo, + this.context, + useLoadersPre, + loaderResolver, + resolveContext, + (err, result) => { + preLoaders = result; + continueCallback(err); + } + ); }); - } - this.invalid = false; - this._invalidReported = false; - this.compiler.hooks.watchRun.callAsync(this.compiler, err => { - if (err) return this._done(err); - const onCompiled = (err, compilation) => { - if (err) return this._done(err, compilation); - if (this.invalid) return this._done(null, compilation); - if (this.compiler.hooks.shouldEmit.call(compilation) === false) { - return this._done(null, compilation); + this.resolveRequestArray( + contextInfo, + contextScheme ? this.context : context, + elements, + loaderResolver, + resolveContext, + (err, result) => { + if (err) return continueCallback(err); + loaders = result; + continueCallback(); } + ); - process.nextTick(() => { - const logger = compilation.getLogger("webpack.Compiler"); - logger.time("emitAssets"); - this.compiler.emitAssets(compilation, err => { - logger.timeEnd("emitAssets"); - if (err) return this._done(err, compilation); - if (this.invalid) return this._done(null, compilation); - - logger.time("emitRecords"); - this.compiler.emitRecords(err => { - logger.timeEnd("emitRecords"); - if (err) return this._done(err, compilation); + const defaultResolve = context => { + if (/^($|\?)/.test(unresolvedResource)) { + resourceData = { + resource: unresolvedResource, + data: {}, + ...cacheParseResource(unresolvedResource) + }; + continueCallback(); + } - if (compilation.hooks.needAdditionalPass.call()) { - compilation.needAdditionalPass = true; + // resource without scheme and with path + else { + const normalResolver = this.getResolver( + "normal", + dependencyType + ? cachedSetProperty( + resolveOptions || EMPTY_RESOLVE_OPTIONS, + "dependencyType", + dependencyType + ) + : resolveOptions + ); + this.resolveResource( + contextInfo, + context, + unresolvedResource, + normalResolver, + resolveContext, + (err, resolvedResource, resolvedResourceResolveData) => { + if (err) return continueCallback(err); + if (resolvedResource !== false) { + resourceData = { + resource: resolvedResource, + data: resolvedResourceResolveData, + ...cacheParseResource(resolvedResource) + }; + } + continueCallback(); + } + ); + } + }; - compilation.startTime = this.startTime; - compilation.endTime = Date.now(); - logger.time("done hook"); - const stats = new Stats(compilation); - this.compiler.hooks.done.callAsync(stats, err => { - logger.timeEnd("done hook"); - if (err) return this._done(err, compilation); + // resource with scheme + if (scheme) { + resourceData = { + resource: unresolvedResource, + data: {}, + path: undefined, + query: undefined, + fragment: undefined, + context: undefined + }; + this.hooks.resolveForScheme + .for(scheme) + .callAsync(resourceData, data, err => { + if (err) return continueCallback(err); + continueCallback(); + }); + } - this.compiler.hooks.additionalPass.callAsync(err => { - if (err) return this._done(err, compilation); - this.compiler.compile(onCompiled); - }); - }); - return; - } - return this._done(null, compilation); - }); + // resource within scheme + else if (contextScheme) { + resourceData = { + resource: unresolvedResource, + data: {}, + path: undefined, + query: undefined, + fragment: undefined, + context: undefined + }; + this.hooks.resolveInScheme + .for(contextScheme) + .callAsync(resourceData, data, (err, handled) => { + if (err) return continueCallback(err); + if (!handled) return defaultResolve(this.context); + continueCallback(); }); - }); - }; - this.compiler.compile(onCompiled); - }); - }; + } - run(); + // resource without scheme and without path + else defaultResolve(context); + } + ); } - /** - * @param {Compilation} compilation the compilation - * @returns {Stats} the compilation stats - */ - _getStats(compilation) { - const stats = new Stats(compilation); - return stats; + cleanupForCache() { + for (const module of this._restoredUnsafeCacheEntries) { + ChunkGraph.clearChunkGraphForModule(module); + ModuleGraph.clearModuleGraphForModule(module); + module.cleanupForCache(); + } } /** - * @param {Error=} err an optional error - * @param {Compilation=} compilation the compilation + * @param {ModuleFactoryCreateData} data data object + * @param {function(Error=, ModuleFactoryResult=): void} callback callback * @returns {void} */ - _done(err, compilation) { - this.running = false; - - const logger = compilation && compilation.getLogger("webpack.Watching"); - - let stats = null; - - const handleError = (err, cbs) => { - this.compiler.hooks.failed.call(err); - this.compiler.cache.beginIdle(); - this.compiler.idle = true; - this.handler(err, stats); - if (!cbs) { - cbs = this.callbacks; - this.callbacks = []; - } - for (const cb of cbs) cb(err); + create(data, callback) { + const dependencies = /** @type {ModuleDependency[]} */ (data.dependencies); + const context = data.context || this.context; + const resolveOptions = data.resolveOptions || EMPTY_RESOLVE_OPTIONS; + const dependency = dependencies[0]; + const request = dependency.request; + const assertions = dependency.assertions; + const contextInfo = data.contextInfo; + const fileDependencies = new LazySet(); + const missingDependencies = new LazySet(); + const contextDependencies = new LazySet(); + const dependencyType = + (dependencies.length > 0 && dependencies[0].category) || ""; + /** @type {ResolveData} */ + const resolveData = { + contextInfo, + resolveOptions, + context, + request, + assertions, + dependencies, + dependencyType, + fileDependencies, + missingDependencies, + contextDependencies, + createData: {}, + cacheable: true }; + this.hooks.beforeResolve.callAsync(resolveData, (err, result) => { + if (err) { + return callback(err, { + fileDependencies, + missingDependencies, + contextDependencies, + cacheable: false + }); + } - if ( - this.invalid && - !this.suspended && - !this.blocked && - !(this._isBlocked() && (this.blocked = true)) - ) { - if (compilation) { - logger.time("storeBuildDependencies"); - this.compiler.cache.storeBuildDependencies( - compilation.buildDependencies, - err => { - logger.timeEnd("storeBuildDependencies"); - if (err) return handleError(err); - this._go(); - } - ); - } else { - this._go(); + // Ignored + if (result === false) { + return callback(null, { + fileDependencies, + missingDependencies, + contextDependencies, + cacheable: resolveData.cacheable + }); } - return; - } - if (compilation) { - compilation.startTime = this.startTime; - compilation.endTime = Date.now(); - stats = new Stats(compilation); - } - this.startTime = null; - if (err) return handleError(err); + if (typeof result === "object") + throw new Error( + deprecationChangedHookMessage( + "beforeResolve", + this.hooks.beforeResolve + ) + ); - const cbs = this.callbacks; - this.callbacks = []; - logger.time("done hook"); - this.compiler.hooks.done.callAsync(stats, err => { - logger.timeEnd("done hook"); - if (err) return handleError(err, cbs); - this.handler(null, stats); - logger.time("storeBuildDependencies"); - this.compiler.cache.storeBuildDependencies( - compilation.buildDependencies, - err => { - logger.timeEnd("storeBuildDependencies"); - if (err) return handleError(err, cbs); - logger.time("beginIdle"); - this.compiler.cache.beginIdle(); - this.compiler.idle = true; - logger.timeEnd("beginIdle"); - process.nextTick(() => { - if (!this.closed) { - this.watch( - compilation.fileDependencies, - compilation.contextDependencies, - compilation.missingDependencies - ); - } + this.hooks.factorize.callAsync(resolveData, (err, module) => { + if (err) { + return callback(err, { + fileDependencies, + missingDependencies, + contextDependencies, + cacheable: false }); - for (const cb of cbs) cb(null); - this.compiler.hooks.afterDone.call(stats); } - ); + + const factoryResult = { + module, + fileDependencies, + missingDependencies, + contextDependencies, + cacheable: resolveData.cacheable + }; + + callback(null, factoryResult); + }); }); } - /** - * @param {Iterable} files watched files - * @param {Iterable} dirs watched directories - * @param {Iterable} missing watched existence entries - * @returns {void} - */ - watch(files, dirs, missing) { - this.pausedWatcher = null; - this.watcher = this.compiler.watchFileSystem.watch( - files, - dirs, - missing, - this.lastWatcherStartTime, - this.watchOptions, - ( - err, - fileTimeInfoEntries, - contextTimeInfoEntries, - changedFiles, - removedFiles - ) => { + resolveResource( + contextInfo, + context, + unresolvedResource, + resolver, + resolveContext, + callback + ) { + resolver.resolve( + contextInfo, + context, + unresolvedResource, + resolveContext, + (err, resolvedResource, resolvedResourceResolveData) => { if (err) { - this.compiler.modifiedFiles = undefined; - this.compiler.removedFiles = undefined; - this.compiler.fileTimestamps = undefined; - this.compiler.contextTimestamps = undefined; - this.compiler.fsStartTime = undefined; - return this.handler(err); + return this._resolveResourceErrorHints( + err, + contextInfo, + context, + unresolvedResource, + resolver, + resolveContext, + (err2, hints) => { + if (err2) { + err.message += ` +An fatal error happened during resolving additional hints for this error: ${err2.message}`; + err.stack += ` + +An fatal error happened during resolving additional hints for this error: +${err2.stack}`; + return callback(err); + } + if (hints && hints.length > 0) { + err.message += ` +${hints.join("\n\n")}`; + } + callback(err); + } + ); } - this._invalidate( - fileTimeInfoEntries, - contextTimeInfoEntries, - changedFiles, - removedFiles - ); - this._onChange(); - }, - (fileName, changeTime) => { - if (!this._invalidReported) { - this._invalidReported = true; - this.compiler.hooks.invalid.call(fileName, changeTime); + callback(err, resolvedResource, resolvedResourceResolveData); + } + ); + } + + _resolveResourceErrorHints( + error, + contextInfo, + context, + unresolvedResource, + resolver, + resolveContext, + callback + ) { + asyncLib.parallel( + [ + callback => { + if (!resolver.options.fullySpecified) return callback(); + resolver + .withOptions({ + fullySpecified: false + }) + .resolve( + contextInfo, + context, + unresolvedResource, + resolveContext, + (err, resolvedResource) => { + if (!err && resolvedResource) { + const resource = parseResource(resolvedResource).path.replace( + /^.*[\\/]/, + "" + ); + return callback( + null, + `Did you mean '${resource}'? +BREAKING CHANGE: The request '${unresolvedResource}' failed to resolve only because it was resolved as fully specified +(probably because the origin is strict EcmaScript Module, e. g. a module with javascript mimetype, a '*.mjs' file, or a '*.js' file where the package.json contains '"type": "module"'). +The extension in the request is mandatory for it to be fully specified. +Add the extension to the request.` + ); + } + callback(); + } + ); + }, + callback => { + if (!resolver.options.enforceExtension) return callback(); + resolver + .withOptions({ + enforceExtension: false, + extensions: [] + }) + .resolve( + contextInfo, + context, + unresolvedResource, + resolveContext, + (err, resolvedResource) => { + if (!err && resolvedResource) { + let hint = ""; + const match = /(\.[^.]+)(\?|$)/.exec(unresolvedResource); + if (match) { + const fixedRequest = unresolvedResource.replace( + /(\.[^.]+)(\?|$)/, + "$2" + ); + if (resolver.options.extensions.has(match[1])) { + hint = `Did you mean '${fixedRequest}'?`; + } else { + hint = `Did you mean '${fixedRequest}'? Also note that '${match[1]}' is not in 'resolve.extensions' yet and need to be added for this to work?`; + } + } else { + hint = `Did you mean to omit the extension or to remove 'resolve.enforceExtension'?`; + } + return callback( + null, + `The request '${unresolvedResource}' failed to resolve only because 'resolve.enforceExtension' was specified. +${hint} +Including the extension in the request is no longer possible. Did you mean to enforce including the extension in requests with 'resolve.extensions: []' instead?` + ); + } + callback(); + } + ); + }, + callback => { + if ( + /^\.\.?\//.test(unresolvedResource) || + resolver.options.preferRelative + ) { + return callback(); + } + resolver.resolve( + contextInfo, + context, + `./${unresolvedResource}`, + resolveContext, + (err, resolvedResource) => { + if (err || !resolvedResource) return callback(); + const moduleDirectories = resolver.options.modules + .map(m => (Array.isArray(m) ? m.join(", ") : m)) + .join(", "); + callback( + null, + `Did you mean './${unresolvedResource}'? +Requests that should resolve in the current directory need to start with './'. +Requests that start with a name are treated as module requests and resolve within module directories (${moduleDirectories}). +If changing the source code is not an option there is also a resolve options called 'preferRelative' which tries to resolve these kind of requests in the current directory too.` + ); + } + ); } - this._onInvalid(); + ], + (err, hints) => { + if (err) return callback(err); + callback(null, hints.filter(Boolean)); } ); } + resolveRequestArray( + contextInfo, + context, + array, + resolver, + resolveContext, + callback + ) { + if (array.length === 0) return callback(null, array); + asyncLib.map( + array, + (item, callback) => { + resolver.resolve( + contextInfo, + context, + item.loader, + resolveContext, + (err, result) => { + if ( + err && + /^[^/]*$/.test(item.loader) && + !/-loader$/.test(item.loader) + ) { + return resolver.resolve( + contextInfo, + context, + item.loader + "-loader", + resolveContext, + err2 => { + if (!err2) { + err.message = + err.message + + "\n" + + "BREAKING CHANGE: It's no longer allowed to omit the '-loader' suffix when using loaders.\n" + + ` You need to specify '${item.loader}-loader' instead of '${item.loader}',\n` + + " see https://webpack.js.org/migrate/3/#automatic-loader-module-name-extension-removed"; + } + callback(err); + } + ); + } + if (err) return callback(err); + + const parsedResult = identToLoaderRequest(result); + const resolved = { + loader: parsedResult.loader, + options: + item.options === undefined + ? parsedResult.options + : item.options, + ident: item.options === undefined ? undefined : item.ident + }; + return callback(null, resolved); + } + ); + }, + callback + ); + } + + getParser(type, parserOptions = EMPTY_PARSER_OPTIONS) { + let cache = this.parserCache.get(type); + + if (cache === undefined) { + cache = new WeakMap(); + this.parserCache.set(type, cache); + } + + let parser = cache.get(parserOptions); + + if (parser === undefined) { + parser = this.createParser(type, parserOptions); + cache.set(parserOptions, parser); + } + + return parser; + } + /** - * @param {Callback=} callback signals when the build has completed again - * @returns {void} + * @param {string} type type + * @param {{[k: string]: any}} parserOptions parser options + * @returns {Parser} parser */ - invalidate(callback) { - if (callback) { - this.callbacks.push(callback); + createParser(type, parserOptions = {}) { + parserOptions = mergeGlobalOptions( + this._globalParserOptions, + type, + parserOptions + ); + const parser = this.hooks.createParser.for(type).call(parserOptions); + if (!parser) { + throw new Error(`No parser registered for ${type}`); } - if (!this._invalidReported) { - this._invalidReported = true; - this.compiler.hooks.invalid.call(null, Date.now()); + this.hooks.parser.for(type).call(parser, parserOptions); + return parser; + } + + getGenerator(type, generatorOptions = EMPTY_GENERATOR_OPTIONS) { + let cache = this.generatorCache.get(type); + + if (cache === undefined) { + cache = new WeakMap(); + this.generatorCache.set(type, cache); } - this._onChange(); - this._invalidate(); + + let generator = cache.get(generatorOptions); + + if (generator === undefined) { + generator = this.createGenerator(type, generatorOptions); + cache.set(generatorOptions, generator); + } + + return generator; } - _invalidate( - fileTimeInfoEntries, - contextTimeInfoEntries, - changedFiles, - removedFiles - ) { - if (this.suspended || (this._isBlocked() && (this.blocked = true))) { - this._mergeWithCollected(changedFiles, removedFiles); - return; + createGenerator(type, generatorOptions = {}) { + generatorOptions = mergeGlobalOptions( + this._globalGeneratorOptions, + type, + generatorOptions + ); + const generator = this.hooks.createGenerator + .for(type) + .call(generatorOptions); + if (!generator) { + throw new Error(`No generator registered for ${type}`); } + this.hooks.generator.for(type).call(generator, generatorOptions); + return generator; + } + + getResolver(type, resolveOptions) { + return this.resolverFactory.get(type, resolveOptions); + } +} + +module.exports = NormalModuleFactory; + + +/***/ }), + +/***/ 12747: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ - if (this.running) { - this._mergeWithCollected(changedFiles, removedFiles); - this.invalid = true; - } else { - this._go( - fileTimeInfoEntries, - contextTimeInfoEntries, - changedFiles, - removedFiles - ); - } - } - suspend() { - this.suspended = true; - } - resume() { - if (this.suspended) { - this.suspended = false; - this._invalidate(); - } +const { join, dirname } = __webpack_require__(93204); + +/** @typedef {import("./Compiler")} Compiler */ +/** @typedef {function(TODO): void} ModuleReplacer */ + +class NormalModuleReplacementPlugin { + /** + * Create an instance of the plugin + * @param {RegExp} resourceRegExp the resource matcher + * @param {string|ModuleReplacer} newResource the resource replacement + */ + constructor(resourceRegExp, newResource) { + this.resourceRegExp = resourceRegExp; + this.newResource = newResource; } /** - * @param {Callback} callback signals when the watcher is closed + * Apply the plugin + * @param {Compiler} compiler the compiler instance * @returns {void} */ - close(callback) { - if (this._closeCallbacks) { - if (callback) { - this._closeCallbacks.push(callback); - } - return; - } - const finalCallback = (err, compilation) => { - this.running = false; - this.compiler.running = false; - this.compiler.watching = undefined; - this.compiler.watchMode = false; - this.compiler.modifiedFiles = undefined; - this.compiler.removedFiles = undefined; - this.compiler.fileTimestamps = undefined; - this.compiler.contextTimestamps = undefined; - this.compiler.fsStartTime = undefined; - const shutdown = err => { - this.compiler.hooks.watchClose.call(); - const closeCallbacks = this._closeCallbacks; - this._closeCallbacks = undefined; - for (const cb of closeCallbacks) cb(err); - }; - if (compilation) { - const logger = compilation.getLogger("webpack.Watching"); - logger.time("storeBuildDependencies"); - this.compiler.cache.storeBuildDependencies( - compilation.buildDependencies, - err2 => { - logger.timeEnd("storeBuildDependencies"); - shutdown(err || err2); + apply(compiler) { + const resourceRegExp = this.resourceRegExp; + const newResource = this.newResource; + compiler.hooks.normalModuleFactory.tap( + "NormalModuleReplacementPlugin", + nmf => { + nmf.hooks.beforeResolve.tap("NormalModuleReplacementPlugin", result => { + if (resourceRegExp.test(result.request)) { + if (typeof newResource === "function") { + newResource(result); + } else { + result.request = newResource; + } } - ); - } else { - shutdown(err); + }); + nmf.hooks.afterResolve.tap("NormalModuleReplacementPlugin", result => { + const createData = result.createData; + if (resourceRegExp.test(createData.resource)) { + if (typeof newResource === "function") { + newResource(result); + } else { + const fs = compiler.inputFileSystem; + if ( + newResource.startsWith("/") || + (newResource.length > 1 && newResource[1] === ":") + ) { + createData.resource = newResource; + } else { + createData.resource = join( + fs, + dirname(fs, createData.resource), + newResource + ); + } + } + } + }); } - }; - - this.closed = true; - if (this.watcher) { - this.watcher.close(); - this.watcher = null; - } - if (this.pausedWatcher) { - this.pausedWatcher.close(); - this.pausedWatcher = null; - } - this._closeCallbacks = []; - if (callback) { - this._closeCallbacks.push(callback); - } - if (this.running) { - this.invalid = true; - this._done = finalCallback; - } else { - finalCallback(); - } + ); } } -module.exports = Watching; +module.exports = NormalModuleReplacementPlugin; /***/ }), -/***/ 68422: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { +/***/ 68145: +/***/ (function(__unused_webpack_module, exports) { "use strict"; /* MIT License http://www.opensource.org/licenses/mit-license.php - Author Jarid Margolin @jaridmargolin + Author Florent Cailhol @ooflorent */ -const inspect = __webpack_require__(31669).inspect.custom; -const makeSerializable = __webpack_require__(26522); +exports.STAGE_BASIC = -10; +exports.STAGE_DEFAULT = 0; +exports.STAGE_ADVANCED = 10; -/** @typedef {import("./Chunk")} Chunk */ -/** @typedef {import("./Dependency").DependencyLocation} DependencyLocation */ -/** @typedef {import("./Module")} Module */ -class WebpackError extends Error { - /** - * Creates an instance of WebpackError. - * @param {string=} message error message - */ - constructor(message) { - super(message); +/***/ }), - this.details = undefined; - /** @type {Module} */ - this.module = undefined; - /** @type {DependencyLocation} */ - this.loc = undefined; - /** @type {boolean} */ - this.hideStack = undefined; - /** @type {Chunk} */ - this.chunk = undefined; - /** @type {string} */ - this.file = undefined; - } +/***/ 88104: +/***/ (function(module) { - [inspect]() { - return this.stack + (this.details ? `\n${this.details}` : ""); - } +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ - serialize({ write }) { - write(this.name); - write(this.message); - write(this.stack); - write(this.details); - write(this.loc); - write(this.hideStack); - } - deserialize({ read }) { - this.name = read(); - this.message = read(); - this.stack = read(); - this.details = read(); - this.loc = read(); - this.hideStack = read(); - } + +class OptionsApply { + process(options, compiler) {} } +module.exports = OptionsApply; -makeSerializable(WebpackError, "webpack/lib/WebpackError"); -module.exports = WebpackError; +/***/ }), + +/***/ 68214: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ + + + +/** @typedef {import("./Compilation")} Compilation */ +/** @typedef {import("./NormalModule")} NormalModule */ + +/** @typedef {Record} PreparsedAst */ + +/** + * @typedef {Object} ParserStateBase + * @property {string | Buffer} source + * @property {NormalModule} current + * @property {NormalModule} module + * @property {Compilation} compilation + * @property {{[k: string]: any}} options + */ + +/** @typedef {Record & ParserStateBase} ParserState */ + +class Parser { + /* istanbul ignore next */ + /** + * @abstract + * @param {string | Buffer | PreparsedAst} source the source to parse + * @param {ParserState} state the parser state + * @returns {ParserState} the parser state + */ + parse(source, state) { + const AbstractMethodError = __webpack_require__(570); + throw new AbstractMethodError(); + } +} + +module.exports = Parser; /***/ }), -/***/ 60823: +/***/ 34652: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; /* MIT License http://www.opensource.org/licenses/mit-license.php - Author Ivan Kopeykin @vankop + Author Tobias Koppers @sokra */ -const IgnoreErrorModuleFactory = __webpack_require__(91471); -const WebpackIsIncludedDependency = __webpack_require__(41744); -const { - toConstantDependency -} = __webpack_require__(28723); +const PrefetchDependency = __webpack_require__(39986); -/** @typedef {import("enhanced-resolve/lib/Resolver")} Resolver */ /** @typedef {import("./Compiler")} Compiler */ -/** @typedef {import("./Module")} Module */ -/** @typedef {import("./javascript/JavascriptParser")} JavascriptParser */ -class WebpackIsIncludedPlugin { +class PrefetchPlugin { + constructor(context, request) { + if (request) { + this.context = context; + this.request = request; + } else { + this.context = null; + this.request = context; + } + } + /** + * Apply the plugin * @param {Compiler} compiler the compiler instance * @returns {void} */ apply(compiler) { compiler.hooks.compilation.tap( - "WebpackIsIncludedPlugin", + "PrefetchPlugin", (compilation, { normalModuleFactory }) => { compilation.dependencyFactories.set( - WebpackIsIncludedDependency, - new IgnoreErrorModuleFactory(normalModuleFactory) - ); - compilation.dependencyTemplates.set( - WebpackIsIncludedDependency, - new WebpackIsIncludedDependency.Template() + PrefetchDependency, + normalModuleFactory ); - - /** - * @param {JavascriptParser} parser the parser - * @returns {void} - */ - const handler = parser => { - parser.hooks.call - .for("__webpack_is_included__") - .tap("WebpackIsIncludedPlugin", expr => { - if ( - expr.type !== "CallExpression" || - expr.arguments.length !== 1 || - expr.arguments[0].type === "SpreadElement" - ) - return; - - const request = parser.evaluateExpression(expr.arguments[0]); - - if (!request.isString()) return; - - const dep = new WebpackIsIncludedDependency( - request.string, - expr.range - ); - dep.loc = expr.loc; - parser.state.module.addDependency(dep); - return true; - }); - parser.hooks.typeof - .for("__webpack_is_included__") - .tap( - "WebpackIsIncludedPlugin", - toConstantDependency(parser, JSON.stringify("function")) - ); - }; - normalModuleFactory.hooks.parser - .for("javascript/auto") - .tap("WebpackIsIncludedPlugin", handler); - normalModuleFactory.hooks.parser - .for("javascript/dynamic") - .tap("WebpackIsIncludedPlugin", handler); - normalModuleFactory.hooks.parser - .for("javascript/esm") - .tap("WebpackIsIncludedPlugin", handler); } ); + compiler.hooks.make.tapAsync("PrefetchPlugin", (compilation, callback) => { + compilation.addModuleChain( + this.context || compiler.context, + new PrefetchDependency(this.request), + err => { + callback(err); + } + ); + }); } } -module.exports = WebpackIsIncludedPlugin; +module.exports = PrefetchPlugin; /***/ }), -/***/ 44137: +/***/ 41306: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; @@ -62641,657 +58544,705 @@ module.exports = WebpackIsIncludedPlugin; -const OptionsApply = __webpack_require__(88104); - -const AssetModulesPlugin = __webpack_require__(42553); -const JavascriptModulesPlugin = __webpack_require__(76767); -const JsonModulesPlugin = __webpack_require__(8841); - -const ChunkPrefetchPreloadPlugin = __webpack_require__(17839); +const Compiler = __webpack_require__(11777); +const MultiCompiler = __webpack_require__(73663); +const NormalModule = __webpack_require__(11026); +const createSchemaValidation = __webpack_require__(77695); +const { contextify } = __webpack_require__(96236); -const EntryOptionPlugin = __webpack_require__(59526); -const RecordIdsPlugin = __webpack_require__(64122); +/** @typedef {import("../declarations/plugins/ProgressPlugin").HandlerFunction} HandlerFunction */ +/** @typedef {import("../declarations/plugins/ProgressPlugin").ProgressPluginArgument} ProgressPluginArgument */ +/** @typedef {import("../declarations/plugins/ProgressPlugin").ProgressPluginOptions} ProgressPluginOptions */ -const RuntimePlugin = __webpack_require__(86809); +const validate = createSchemaValidation( + __webpack_require__(67916), + () => __webpack_require__(98777), + { + name: "Progress Plugin", + baseDataPath: "options" + } +); +const median3 = (a, b, c) => { + return a + b + c - Math.max(a, b, c) - Math.min(a, b, c); +}; -const APIPlugin = __webpack_require__(46806); -const CompatibilityPlugin = __webpack_require__(27847); -const ConstPlugin = __webpack_require__(53042); -const ExportsInfoApiPlugin = __webpack_require__(75529); -const WebpackIsIncludedPlugin = __webpack_require__(60823); +const createDefaultHandler = (profile, logger) => { + /** @type {{ value: string, time: number }[]} */ + const lastStateInfo = []; -const TemplatedPathPlugin = __webpack_require__(54642); -const UseStrictPlugin = __webpack_require__(15466); -const WarnCaseSensitiveModulesPlugin = __webpack_require__(33304); + const defaultHandler = (percentage, msg, ...args) => { + if (profile) { + if (percentage === 0) { + lastStateInfo.length = 0; + } + const fullState = [msg, ...args]; + const state = fullState.map(s => s.replace(/\d+\/\d+ /g, "")); + const now = Date.now(); + const len = Math.max(state.length, lastStateInfo.length); + for (let i = len; i >= 0; i--) { + const stateItem = i < state.length ? state[i] : undefined; + const lastStateItem = + i < lastStateInfo.length ? lastStateInfo[i] : undefined; + if (lastStateItem) { + if (stateItem !== lastStateItem.value) { + const diff = now - lastStateItem.time; + if (lastStateItem.value) { + let reportState = lastStateItem.value; + if (i > 0) { + reportState = lastStateInfo[i - 1].value + " > " + reportState; + } + const stateMsg = `${" | ".repeat(i)}${diff} ms ${reportState}`; + const d = diff; + // This depends on timing so we ignore it for coverage + /* istanbul ignore next */ + { + if (d > 10000) { + logger.error(stateMsg); + } else if (d > 1000) { + logger.warn(stateMsg); + } else if (d > 10) { + logger.info(stateMsg); + } else if (d > 5) { + logger.log(stateMsg); + } else { + logger.debug(stateMsg); + } + } + } + if (stateItem === undefined) { + lastStateInfo.length = i; + } else { + lastStateItem.value = stateItem; + lastStateItem.time = now; + lastStateInfo.length = i + 1; + } + } + } else { + lastStateInfo[i] = { + value: stateItem, + time: now + }; + } + } + } + logger.status(`${Math.floor(percentage * 100)}%`, msg, ...args); + if (percentage === 1 || (!msg && args.length === 0)) logger.status(); + }; -const DataUriPlugin = __webpack_require__(71276); -const FileUriPlugin = __webpack_require__(75275); + return defaultHandler; +}; -const ResolverCachePlugin = __webpack_require__(11740); +/** + * @callback ReportProgress + * @param {number} p + * @param {...string[]} [args] + * @returns {void} + */ -const CommonJsPlugin = __webpack_require__(8615); -const HarmonyModulesPlugin = __webpack_require__(73365); -const ImportMetaPlugin = __webpack_require__(81841); -const ImportPlugin = __webpack_require__(77199); -const LoaderPlugin = __webpack_require__(34204); -const RequireContextPlugin = __webpack_require__(30738); -const RequireEnsurePlugin = __webpack_require__(66697); -const RequireIncludePlugin = __webpack_require__(83683); -const SystemPlugin = __webpack_require__(88768); -const URLPlugin = __webpack_require__(97950); -const WorkerPlugin = __webpack_require__(93493); +/** @type {WeakMap} */ +const progressReporters = new WeakMap(); -const InferAsyncModulesPlugin = __webpack_require__(79471); +class ProgressPlugin { + /** + * @param {Compiler} compiler the current compiler + * @returns {ReportProgress} a progress reporter, if any + */ + static getReporter(compiler) { + return progressReporters.get(compiler); + } -const JavascriptMetaInfoPlugin = __webpack_require__(38197); -const DefaultStatsFactoryPlugin = __webpack_require__(91293); -const DefaultStatsPresetPlugin = __webpack_require__(2130); -const DefaultStatsPrinterPlugin = __webpack_require__(78303); + /** + * @param {ProgressPluginArgument} options options + */ + constructor(options = {}) { + if (typeof options === "function") { + options = { + handler: options + }; + } -const { cleverMerge } = __webpack_require__(11217); + validate(options); + options = { ...ProgressPlugin.defaultOptions, ...options }; -/** @typedef {import("../declarations/WebpackOptions").WebpackOptionsNormalized} WebpackOptions */ -/** @typedef {import("./Compiler")} Compiler */ + this.profile = options.profile; + this.handler = options.handler; + this.modulesCount = options.modulesCount; + this.dependenciesCount = options.dependenciesCount; + this.showEntries = options.entries; + this.showModules = options.modules; + this.showDependencies = options.dependencies; + this.showActiveModules = options.activeModules; + this.percentBy = options.percentBy; + } -class WebpackOptionsApply extends OptionsApply { - constructor() { - super(); + /** + * @param {Compiler | MultiCompiler} compiler webpack compiler + * @returns {void} + */ + apply(compiler) { + const handler = + this.handler || + createDefaultHandler( + this.profile, + compiler.getInfrastructureLogger("webpack.Progress") + ); + if (compiler instanceof MultiCompiler) { + this._applyOnMultiCompiler(compiler, handler); + } else if (compiler instanceof Compiler) { + this._applyOnCompiler(compiler, handler); + } } /** - * @param {WebpackOptions} options options object - * @param {Compiler} compiler compiler object - * @returns {WebpackOptions} options object + * @param {MultiCompiler} compiler webpack multi-compiler + * @param {HandlerFunction} handler function that executes for every progress step + * @returns {void} */ - process(options, compiler) { - compiler.outputPath = options.output.path; - compiler.recordsInputPath = options.recordsInputPath || null; - compiler.recordsOutputPath = options.recordsOutputPath || null; - compiler.name = options.name; + _applyOnMultiCompiler(compiler, handler) { + const states = compiler.compilers.map( + () => /** @type {[number, ...string[]]} */ ([0]) + ); + compiler.compilers.forEach((compiler, idx) => { + new ProgressPlugin((p, msg, ...args) => { + states[idx] = [p, msg, ...args]; + let sum = 0; + for (const [p] of states) sum += p; + handler(sum / states.length, `[${idx}] ${msg}`, ...args); + }).apply(compiler); + }); + } - if (options.externals) { - //@ts-expect-error https://github.com/microsoft/TypeScript/issues/41697 - const ExternalsPlugin = __webpack_require__(361); - new ExternalsPlugin(options.externalsType, options.externals).apply( - compiler - ); - } + /** + * @param {Compiler} compiler webpack compiler + * @param {HandlerFunction} handler function that executes for every progress step + * @returns {void} + */ + _applyOnCompiler(compiler, handler) { + const showEntries = this.showEntries; + const showModules = this.showModules; + const showDependencies = this.showDependencies; + const showActiveModules = this.showActiveModules; + let lastActiveModule = ""; + let currentLoader = ""; + let lastModulesCount = 0; + let lastDependenciesCount = 0; + let lastEntriesCount = 0; + let modulesCount = 0; + let dependenciesCount = 0; + let entriesCount = 1; + let doneModules = 0; + let doneDependencies = 0; + let doneEntries = 0; + const activeModules = new Set(); + let lastUpdate = 0; - if (options.externalsPresets.node) { - const NodeTargetPlugin = __webpack_require__(28037); - new NodeTargetPlugin().apply(compiler); - } - if (options.externalsPresets.electronMain) { - //@ts-expect-error https://github.com/microsoft/TypeScript/issues/41697 - const ElectronTargetPlugin = __webpack_require__(88362); - new ElectronTargetPlugin("main").apply(compiler); - } - if (options.externalsPresets.electronPreload) { - //@ts-expect-error https://github.com/microsoft/TypeScript/issues/41697 - const ElectronTargetPlugin = __webpack_require__(88362); - new ElectronTargetPlugin("preload").apply(compiler); - } - if (options.externalsPresets.electronRenderer) { - //@ts-expect-error https://github.com/microsoft/TypeScript/issues/41697 - const ElectronTargetPlugin = __webpack_require__(88362); - new ElectronTargetPlugin("renderer").apply(compiler); - } - if ( - options.externalsPresets.electron && - !options.externalsPresets.electronMain && - !options.externalsPresets.electronPreload && - !options.externalsPresets.electronRenderer - ) { - //@ts-expect-error https://github.com/microsoft/TypeScript/issues/41697 - const ElectronTargetPlugin = __webpack_require__(88362); - new ElectronTargetPlugin().apply(compiler); - } - if (options.externalsPresets.nwjs) { - //@ts-expect-error https://github.com/microsoft/TypeScript/issues/41697 - const ExternalsPlugin = __webpack_require__(361); - new ExternalsPlugin("node-commonjs", "nw.gui").apply(compiler); - } - if (options.externalsPresets.webAsync) { - //@ts-expect-error https://github.com/microsoft/TypeScript/issues/41697 - const ExternalsPlugin = __webpack_require__(361); - new ExternalsPlugin("import", /^(https?:\/\/|std:)/).apply(compiler); - } else if (options.externalsPresets.web) { - //@ts-expect-error https://github.com/microsoft/TypeScript/issues/41697 - const ExternalsPlugin = __webpack_require__(361); - new ExternalsPlugin("module", /^(https?:\/\/|std:)/).apply(compiler); - } + const updateThrottled = () => { + if (lastUpdate + 500 < Date.now()) update(); + }; - new ChunkPrefetchPreloadPlugin().apply(compiler); + const update = () => { + /** @type {string[]} */ + const items = []; + const percentByModules = + doneModules / + Math.max(lastModulesCount || this.modulesCount || 1, modulesCount); + const percentByEntries = + doneEntries / + Math.max(lastEntriesCount || this.dependenciesCount || 1, entriesCount); + const percentByDependencies = + doneDependencies / + Math.max(lastDependenciesCount || 1, dependenciesCount); + let percentageFactor; - if (typeof options.output.chunkFormat === "string") { - switch (options.output.chunkFormat) { - case "array-push": { - const ArrayPushCallbackChunkFormatPlugin = __webpack_require__(86189); - new ArrayPushCallbackChunkFormatPlugin().apply(compiler); + switch (this.percentBy) { + case "entries": + percentageFactor = percentByEntries; break; - } - case "commonjs": { - const CommonJsChunkFormatPlugin = __webpack_require__(57634); - new CommonJsChunkFormatPlugin().apply(compiler); + case "dependencies": + percentageFactor = percentByDependencies; break; - } - case "module": { - const ModuleChunkFormatPlugin = __webpack_require__(29181); - new ModuleChunkFormatPlugin().apply(compiler); + case "modules": + percentageFactor = percentByModules; break; - } default: - throw new Error( - "Unsupported chunk format '" + options.output.chunkFormat + "'." + percentageFactor = median3( + percentByModules, + percentByEntries, + percentByDependencies ); } - } - if (options.output.enabledChunkLoadingTypes.length > 0) { - for (const type of options.output.enabledChunkLoadingTypes) { - const EnableChunkLoadingPlugin = __webpack_require__(34726); - new EnableChunkLoadingPlugin(type).apply(compiler); + const percentage = 0.1 + percentageFactor * 0.55; + + if (currentLoader) { + items.push( + `import loader ${contextify( + compiler.context, + currentLoader, + compiler.root + )}` + ); + } else { + const statItems = []; + if (showEntries) { + statItems.push(`${doneEntries}/${entriesCount} entries`); + } + if (showDependencies) { + statItems.push( + `${doneDependencies}/${dependenciesCount} dependencies` + ); + } + if (showModules) { + statItems.push(`${doneModules}/${modulesCount} modules`); + } + if (showActiveModules) { + statItems.push(`${activeModules.size} active`); + } + if (statItems.length > 0) { + items.push(statItems.join(" ")); + } + if (showActiveModules) { + items.push(lastActiveModule); + } } - } + handler(percentage, "building", ...items); + lastUpdate = Date.now(); + }; - if (options.output.enabledWasmLoadingTypes.length > 0) { - for (const type of options.output.enabledWasmLoadingTypes) { - const EnableWasmLoadingPlugin = __webpack_require__(93943); - new EnableWasmLoadingPlugin(type).apply(compiler); + const factorizeAdd = () => { + dependenciesCount++; + if (dependenciesCount < 50 || dependenciesCount % 100 === 0) + updateThrottled(); + }; + + const factorizeDone = () => { + doneDependencies++; + if (doneDependencies < 50 || doneDependencies % 100 === 0) + updateThrottled(); + }; + + const moduleAdd = () => { + modulesCount++; + if (modulesCount < 50 || modulesCount % 100 === 0) updateThrottled(); + }; + + // only used when showActiveModules is set + const moduleBuild = module => { + const ident = module.identifier(); + if (ident) { + activeModules.add(ident); + lastActiveModule = ident; + update(); } - } + }; - if (options.output.enabledLibraryTypes.length > 0) { - for (const type of options.output.enabledLibraryTypes) { - const EnableLibraryPlugin = __webpack_require__(35613); - new EnableLibraryPlugin(type).apply(compiler); + const entryAdd = (entry, options) => { + entriesCount++; + if (entriesCount < 5 || entriesCount % 10 === 0) updateThrottled(); + }; + + const moduleDone = module => { + doneModules++; + if (showActiveModules) { + const ident = module.identifier(); + if (ident) { + activeModules.delete(ident); + if (lastActiveModule === ident) { + lastActiveModule = ""; + for (const m of activeModules) { + lastActiveModule = m; + } + update(); + return; + } + } } - } + if (doneModules < 50 || doneModules % 100 === 0) updateThrottled(); + }; - if (options.output.pathinfo) { - const ModuleInfoHeaderPlugin = __webpack_require__(45095); - new ModuleInfoHeaderPlugin(options.output.pathinfo !== true).apply( - compiler + const entryDone = (entry, options) => { + doneEntries++; + update(); + }; + + const cache = compiler + .getCache("ProgressPlugin") + .getItemCache("counts", null); + + let cacheGetPromise; + + compiler.hooks.beforeCompile.tap("ProgressPlugin", () => { + if (!cacheGetPromise) { + cacheGetPromise = cache.getPromise().then( + data => { + if (data) { + lastModulesCount = lastModulesCount || data.modulesCount; + lastDependenciesCount = + lastDependenciesCount || data.dependenciesCount; + } + return data; + }, + err => { + // Ignore error + } + ); + } + }); + + compiler.hooks.afterCompile.tapPromise("ProgressPlugin", compilation => { + if (compilation.compiler.isChild()) return Promise.resolve(); + return cacheGetPromise.then(async oldData => { + if ( + !oldData || + oldData.modulesCount !== modulesCount || + oldData.dependenciesCount !== dependenciesCount + ) { + await cache.storePromise({ modulesCount, dependenciesCount }); + } + }); + }); + + compiler.hooks.compilation.tap("ProgressPlugin", compilation => { + if (compilation.compiler.isChild()) return; + lastModulesCount = modulesCount; + lastEntriesCount = entriesCount; + lastDependenciesCount = dependenciesCount; + modulesCount = dependenciesCount = entriesCount = 0; + doneModules = doneDependencies = doneEntries = 0; + + compilation.factorizeQueue.hooks.added.tap( + "ProgressPlugin", + factorizeAdd + ); + compilation.factorizeQueue.hooks.result.tap( + "ProgressPlugin", + factorizeDone ); - } - if (options.output.clean) { - const CleanPlugin = __webpack_require__(49129); - new CleanPlugin( - options.output.clean === true ? {} : options.output.clean - ).apply(compiler); - } + compilation.addModuleQueue.hooks.added.tap("ProgressPlugin", moduleAdd); + compilation.processDependenciesQueue.hooks.result.tap( + "ProgressPlugin", + moduleDone + ); - if (options.devtool) { - if (options.devtool.includes("source-map")) { - const hidden = options.devtool.includes("hidden"); - const inline = options.devtool.includes("inline"); - const evalWrapped = options.devtool.includes("eval"); - const cheap = options.devtool.includes("cheap"); - const moduleMaps = options.devtool.includes("module"); - const noSources = options.devtool.includes("nosources"); - const Plugin = evalWrapped - ? __webpack_require__(42053) - : __webpack_require__(79917); - new Plugin({ - filename: inline ? null : options.output.sourceMapFilename, - moduleFilenameTemplate: options.output.devtoolModuleFilenameTemplate, - fallbackModuleFilenameTemplate: - options.output.devtoolFallbackModuleFilenameTemplate, - append: hidden ? false : undefined, - module: moduleMaps ? true : cheap ? false : true, - columns: cheap ? false : true, - noSources: noSources, - namespace: options.output.devtoolNamespace - }).apply(compiler); - } else if (options.devtool.includes("eval")) { - const EvalDevToolModulePlugin = __webpack_require__(4125); - new EvalDevToolModulePlugin({ - moduleFilenameTemplate: options.output.devtoolModuleFilenameTemplate, - namespace: options.output.devtoolNamespace - }).apply(compiler); + if (showActiveModules) { + compilation.hooks.buildModule.tap("ProgressPlugin", moduleBuild); } - } - new JavascriptModulesPlugin().apply(compiler); - new JsonModulesPlugin().apply(compiler); - new AssetModulesPlugin().apply(compiler); + compilation.hooks.addEntry.tap("ProgressPlugin", entryAdd); + compilation.hooks.failedEntry.tap("ProgressPlugin", entryDone); + compilation.hooks.succeedEntry.tap("ProgressPlugin", entryDone); - if (!options.experiments.outputModule) { - if (options.output.module) { - throw new Error( - "'output.module: true' is only allowed when 'experiments.outputModule' is enabled" - ); + // avoid dynamic require if bundled with webpack + // @ts-expect-error + if (false) {} + + const hooks = { + finishModules: "finish module graph", + seal: "plugins", + optimizeDependencies: "dependencies optimization", + afterOptimizeDependencies: "after dependencies optimization", + beforeChunks: "chunk graph", + afterChunks: "after chunk graph", + optimize: "optimizing", + optimizeModules: "module optimization", + afterOptimizeModules: "after module optimization", + optimizeChunks: "chunk optimization", + afterOptimizeChunks: "after chunk optimization", + optimizeTree: "module and chunk tree optimization", + afterOptimizeTree: "after module and chunk tree optimization", + optimizeChunkModules: "chunk modules optimization", + afterOptimizeChunkModules: "after chunk modules optimization", + reviveModules: "module reviving", + beforeModuleIds: "before module ids", + moduleIds: "module ids", + optimizeModuleIds: "module id optimization", + afterOptimizeModuleIds: "module id optimization", + reviveChunks: "chunk reviving", + beforeChunkIds: "before chunk ids", + chunkIds: "chunk ids", + optimizeChunkIds: "chunk id optimization", + afterOptimizeChunkIds: "after chunk id optimization", + recordModules: "record modules", + recordChunks: "record chunks", + beforeModuleHash: "module hashing", + beforeCodeGeneration: "code generation", + beforeRuntimeRequirements: "runtime requirements", + beforeHash: "hashing", + afterHash: "after hashing", + recordHash: "record hash", + beforeModuleAssets: "module assets processing", + beforeChunkAssets: "chunk assets processing", + processAssets: "asset processing", + afterProcessAssets: "after asset optimization", + record: "recording", + afterSeal: "after seal" + }; + const numberOfHooks = Object.keys(hooks).length; + Object.keys(hooks).forEach((name, idx) => { + const title = hooks[name]; + const percentage = (idx / numberOfHooks) * 0.25 + 0.7; + compilation.hooks[name].intercept({ + name: "ProgressPlugin", + call() { + handler(percentage, "sealing", title); + }, + done() { + progressReporters.set(compiler, undefined); + handler(percentage, "sealing", title); + }, + result() { + handler(percentage, "sealing", title); + }, + error() { + handler(percentage, "sealing", title); + }, + tap(tap) { + // p is percentage from 0 to 1 + // args is any number of messages in a hierarchical matter + progressReporters.set(compilation.compiler, (p, ...args) => { + handler(percentage, "sealing", title, tap.name, ...args); + }); + handler(percentage, "sealing", title, tap.name); + } + }); + }); + }); + compiler.hooks.make.intercept({ + name: "ProgressPlugin", + call() { + handler(0.1, "building"); + }, + done() { + handler(0.65, "building"); } - if (options.output.enabledLibraryTypes.includes("module")) { - throw new Error( - "library type \"module\" is only allowed when 'experiments.outputModule' is enabled" - ); + }); + const interceptHook = (hook, progress, category, name) => { + hook.intercept({ + name: "ProgressPlugin", + call() { + handler(progress, category, name); + }, + done() { + progressReporters.set(compiler, undefined); + handler(progress, category, name); + }, + result() { + handler(progress, category, name); + }, + error() { + handler(progress, category, name); + }, + tap(tap) { + progressReporters.set(compiler, (p, ...args) => { + handler(progress, category, name, tap.name, ...args); + }); + handler(progress, category, name, tap.name); + } + }); + }; + compiler.cache.hooks.endIdle.intercept({ + name: "ProgressPlugin", + call() { + handler(0, ""); + } + }); + interceptHook(compiler.cache.hooks.endIdle, 0.01, "cache", "end idle"); + compiler.hooks.initialize.intercept({ + name: "ProgressPlugin", + call() { + handler(0, ""); + } + }); + interceptHook(compiler.hooks.initialize, 0.01, "setup", "initialize"); + interceptHook(compiler.hooks.beforeRun, 0.02, "setup", "before run"); + interceptHook(compiler.hooks.run, 0.03, "setup", "run"); + interceptHook(compiler.hooks.watchRun, 0.03, "setup", "watch run"); + interceptHook( + compiler.hooks.normalModuleFactory, + 0.04, + "setup", + "normal module factory" + ); + interceptHook( + compiler.hooks.contextModuleFactory, + 0.05, + "setup", + "context module factory" + ); + interceptHook( + compiler.hooks.beforeCompile, + 0.06, + "setup", + "before compile" + ); + interceptHook(compiler.hooks.compile, 0.07, "setup", "compile"); + interceptHook(compiler.hooks.thisCompilation, 0.08, "setup", "compilation"); + interceptHook(compiler.hooks.compilation, 0.09, "setup", "compilation"); + interceptHook(compiler.hooks.finishMake, 0.69, "building", "finish"); + interceptHook(compiler.hooks.emit, 0.95, "emitting", "emit"); + interceptHook(compiler.hooks.afterEmit, 0.98, "emitting", "after emit"); + interceptHook(compiler.hooks.done, 0.99, "done", "plugins"); + compiler.hooks.done.intercept({ + name: "ProgressPlugin", + done() { + handler(0.99, ""); } - if (options.externalsType === "module") { - throw new Error( - "'externalsType: \"module\"' is only allowed when 'experiments.outputModule' is enabled" - ); + }); + interceptHook( + compiler.cache.hooks.storeBuildDependencies, + 0.99, + "cache", + "store build dependencies" + ); + interceptHook(compiler.cache.hooks.shutdown, 0.99, "cache", "shutdown"); + interceptHook(compiler.cache.hooks.beginIdle, 0.99, "cache", "begin idle"); + interceptHook( + compiler.hooks.watchClose, + 0.99, + "end", + "closing watch compilation" + ); + compiler.cache.hooks.beginIdle.intercept({ + name: "ProgressPlugin", + done() { + handler(1, ""); } - } - - if (options.experiments.syncWebAssembly) { - const WebAssemblyModulesPlugin = __webpack_require__(93813); - new WebAssemblyModulesPlugin({ - mangleImports: options.optimization.mangleWasmImports - }).apply(compiler); - } - - if (options.experiments.asyncWebAssembly) { - const AsyncWebAssemblyModulesPlugin = __webpack_require__(13804); - new AsyncWebAssemblyModulesPlugin({ - mangleImports: options.optimization.mangleWasmImports - }).apply(compiler); - } - - if (options.experiments.lazyCompilation) { - const LazyCompilationPlugin = __webpack_require__(70839); - const lazyOptions = - typeof options.experiments.lazyCompilation === "object" - ? options.experiments.lazyCompilation - : null; - new LazyCompilationPlugin({ - backend: - typeof lazyOptions.backend === "function" - ? lazyOptions.backend - : __webpack_require__(46574)({ - ...lazyOptions.backend, - client: - (lazyOptions.backend && lazyOptions.backend.client) || - options.externalsPresets.node ? __webpack_require__.ab + "lazy-compilation-node.js" : __webpack_require__.ab + "lazy-compilation-web.js" - }), - entries: !lazyOptions || lazyOptions.entries !== false, - imports: !lazyOptions || lazyOptions.imports !== false, - test: (lazyOptions && lazyOptions.test) || undefined - }).apply(compiler); - } - - if (options.experiments.buildHttp) { - const HttpUriPlugin = __webpack_require__(34747); - const httpOptions = options.experiments.buildHttp; - new HttpUriPlugin(httpOptions).apply(compiler); - } - - new EntryOptionPlugin().apply(compiler); - compiler.hooks.entryOption.call(options.context, options.entry); - - new RuntimePlugin().apply(compiler); - - new InferAsyncModulesPlugin().apply(compiler); + }); + compiler.cache.hooks.shutdown.intercept({ + name: "ProgressPlugin", + done() { + handler(1, ""); + } + }); + } +} - new DataUriPlugin().apply(compiler); - new FileUriPlugin().apply(compiler); +ProgressPlugin.defaultOptions = { + profile: false, + modulesCount: 5000, + dependenciesCount: 10000, + modules: true, + dependencies: true, + activeModules: false, + entries: true +}; - new CompatibilityPlugin().apply(compiler); - new HarmonyModulesPlugin({ - topLevelAwait: options.experiments.topLevelAwait - }).apply(compiler); - if (options.amd !== false) { - const AMDPlugin = __webpack_require__(82916); - const RequireJsStuffPlugin = __webpack_require__(81898); - new AMDPlugin(options.amd || {}).apply(compiler); - new RequireJsStuffPlugin().apply(compiler); - } - new CommonJsPlugin().apply(compiler); - new LoaderPlugin({}).apply(compiler); - if (options.node !== false) { - const NodeStuffPlugin = __webpack_require__(14290); - new NodeStuffPlugin(options.node).apply(compiler); - } - new APIPlugin().apply(compiler); - new ExportsInfoApiPlugin().apply(compiler); - new WebpackIsIncludedPlugin().apply(compiler); - new ConstPlugin().apply(compiler); - new UseStrictPlugin().apply(compiler); - new RequireIncludePlugin().apply(compiler); - new RequireEnsurePlugin().apply(compiler); - new RequireContextPlugin().apply(compiler); - new ImportPlugin().apply(compiler); - new SystemPlugin().apply(compiler); - new ImportMetaPlugin().apply(compiler); - new URLPlugin().apply(compiler); - new WorkerPlugin( - options.output.workerChunkLoading, - options.output.workerWasmLoading, - options.output.module - ).apply(compiler); +module.exports = ProgressPlugin; - new DefaultStatsFactoryPlugin().apply(compiler); - new DefaultStatsPresetPlugin().apply(compiler); - new DefaultStatsPrinterPlugin().apply(compiler); - new JavascriptMetaInfoPlugin().apply(compiler); +/***/ }), - if (typeof options.mode !== "string") { - const WarnNoModeSetPlugin = __webpack_require__(70308); - new WarnNoModeSetPlugin().apply(compiler); - } +/***/ 18067: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - const EnsureChunkConditionsPlugin = __webpack_require__(91120); - new EnsureChunkConditionsPlugin().apply(compiler); - if (options.optimization.removeAvailableModules) { - const RemoveParentModulesPlugin = __webpack_require__(75072); - new RemoveParentModulesPlugin().apply(compiler); - } - if (options.optimization.removeEmptyChunks) { - const RemoveEmptyChunksPlugin = __webpack_require__(66290); - new RemoveEmptyChunksPlugin().apply(compiler); - } - if (options.optimization.mergeDuplicateChunks) { - const MergeDuplicateChunksPlugin = __webpack_require__(54450); - new MergeDuplicateChunksPlugin().apply(compiler); - } - if (options.optimization.flagIncludedChunks) { - const FlagIncludedChunksPlugin = __webpack_require__(48424); - new FlagIncludedChunksPlugin().apply(compiler); - } - if (options.optimization.sideEffects) { - const SideEffectsFlagPlugin = __webpack_require__(47844); - new SideEffectsFlagPlugin( - options.optimization.sideEffects === true - ).apply(compiler); - } - if (options.optimization.providedExports) { - const FlagDependencyExportsPlugin = __webpack_require__(395); - new FlagDependencyExportsPlugin().apply(compiler); - } - if (options.optimization.usedExports) { - const FlagDependencyUsagePlugin = __webpack_require__(13104); - new FlagDependencyUsagePlugin( - options.optimization.usedExports === "global" - ).apply(compiler); - } - if (options.optimization.innerGraph) { - const InnerGraphPlugin = __webpack_require__(57997); - new InnerGraphPlugin().apply(compiler); - } - if (options.optimization.mangleExports) { - const MangleExportsPlugin = __webpack_require__(7281); - new MangleExportsPlugin( - options.optimization.mangleExports !== "size" - ).apply(compiler); - } - if (options.optimization.concatenateModules) { - const ModuleConcatenationPlugin = __webpack_require__(29585); - new ModuleConcatenationPlugin().apply(compiler); - } - if (options.optimization.splitChunks) { - const SplitChunksPlugin = __webpack_require__(57073); - new SplitChunksPlugin(options.optimization.splitChunks).apply(compiler); - } - if (options.optimization.runtimeChunk) { - const RuntimeChunkPlugin = __webpack_require__(23821); - new RuntimeChunkPlugin(options.optimization.runtimeChunk).apply(compiler); - } - if (!options.optimization.emitOnErrors) { - const NoEmitOnErrorsPlugin = __webpack_require__(70760); - new NoEmitOnErrorsPlugin().apply(compiler); - } - if (options.optimization.realContentHash) { - const RealContentHashPlugin = __webpack_require__(6669); - new RealContentHashPlugin({ - hashFunction: options.output.hashFunction, - hashDigest: options.output.hashDigest - }).apply(compiler); - } - if (options.optimization.checkWasmTypes) { - const WasmFinalizeExportsPlugin = __webpack_require__(12995); - new WasmFinalizeExportsPlugin().apply(compiler); - } - const moduleIds = options.optimization.moduleIds; - if (moduleIds) { - switch (moduleIds) { - case "natural": { - const NaturalModuleIdsPlugin = __webpack_require__(96338); - new NaturalModuleIdsPlugin().apply(compiler); - break; - } - case "named": { - const NamedModuleIdsPlugin = __webpack_require__(88514); - new NamedModuleIdsPlugin().apply(compiler); - break; - } - case "hashed": { - const WarnDeprecatedOptionPlugin = __webpack_require__(85024); - const HashedModuleIdsPlugin = __webpack_require__(83635); - new WarnDeprecatedOptionPlugin( - "optimization.moduleIds", - "hashed", - "deterministic" - ).apply(compiler); - new HashedModuleIdsPlugin({ - hashFunction: options.output.hashFunction - }).apply(compiler); - break; - } - case "deterministic": { - const DeterministicModuleIdsPlugin = __webpack_require__(84965); - new DeterministicModuleIdsPlugin().apply(compiler); - break; - } - case "size": { - const OccurrenceModuleIdsPlugin = __webpack_require__(128); - new OccurrenceModuleIdsPlugin({ - prioritiseInitial: true - }).apply(compiler); - break; - } - default: - throw new Error( - `webpack bug: moduleIds: ${moduleIds} is not implemented` - ); - } - } - const chunkIds = options.optimization.chunkIds; - if (chunkIds) { - switch (chunkIds) { - case "natural": { - const NaturalChunkIdsPlugin = __webpack_require__(18326); - new NaturalChunkIdsPlugin().apply(compiler); - break; - } - case "named": { - const NamedChunkIdsPlugin = __webpack_require__(30483); - new NamedChunkIdsPlugin().apply(compiler); - break; - } - case "deterministic": { - const DeterministicChunkIdsPlugin = __webpack_require__(64801); - new DeterministicChunkIdsPlugin().apply(compiler); - break; - } - case "size": { - //@ts-expect-error https://github.com/microsoft/TypeScript/issues/41697 - const OccurrenceChunkIdsPlugin = __webpack_require__(98702); - new OccurrenceChunkIdsPlugin({ - prioritiseInitial: true - }).apply(compiler); - break; - } - case "total-size": { - //@ts-expect-error https://github.com/microsoft/TypeScript/issues/41697 - const OccurrenceChunkIdsPlugin = __webpack_require__(98702); - new OccurrenceChunkIdsPlugin({ - prioritiseInitial: false - }).apply(compiler); - break; - } - default: - throw new Error( - `webpack bug: chunkIds: ${chunkIds} is not implemented` - ); - } - } - if (options.optimization.nodeEnv) { - const DefinePlugin = __webpack_require__(46754); - new DefinePlugin({ - "process.env.NODE_ENV": JSON.stringify(options.optimization.nodeEnv) - }).apply(compiler); - } - if (options.optimization.minimize) { - for (const minimizer of options.optimization.minimizer) { - if (typeof minimizer === "function") { - minimizer.call(compiler, compiler); - } else if (minimizer !== "...") { - minimizer.apply(compiler); - } - } - } +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ - if (options.performance) { - const SizeLimitsPlugin = __webpack_require__(64025); - new SizeLimitsPlugin(options.performance).apply(compiler); - } - new TemplatedPathPlugin().apply(compiler); - new RecordIdsPlugin({ - portableIds: options.optimization.portableRecords - }).apply(compiler); +const ConstDependency = __webpack_require__(60864); +const ProvidedDependency = __webpack_require__(88915); +const { approve } = __webpack_require__(28723); - new WarnCaseSensitiveModulesPlugin().apply(compiler); +/** @typedef {import("./Compiler")} Compiler */ - const AddManagedPathsPlugin = __webpack_require__(19724); - new AddManagedPathsPlugin( - options.snapshot.managedPaths, - options.snapshot.immutablePaths - ).apply(compiler); +class ProvidePlugin { + /** + * @param {Record} definitions the provided identifiers + */ + constructor(definitions) { + this.definitions = definitions; + } - if (options.cache && typeof options.cache === "object") { - const cacheOptions = options.cache; - switch (cacheOptions.type) { - case "memory": { - if (isFinite(cacheOptions.maxGenerations)) { - //@ts-expect-error https://github.com/microsoft/TypeScript/issues/41697 - const MemoryWithGcCachePlugin = __webpack_require__(34854); - new MemoryWithGcCachePlugin({ - maxGenerations: cacheOptions.maxGenerations - }).apply(compiler); - } else { - //@ts-expect-error https://github.com/microsoft/TypeScript/issues/41697 - const MemoryCachePlugin = __webpack_require__(4045); - new MemoryCachePlugin().apply(compiler); - } - if (cacheOptions.cacheUnaffected) { - if (!options.experiments.cacheUnaffected) { - throw new Error( - "'cache.cacheUnaffected: true' is only allowed when 'experiments.cacheUnaffected' is enabled" - ); - } - compiler.moduleMemCaches = new Map(); - } - break; - } - case "filesystem": { - const AddBuildDependenciesPlugin = __webpack_require__(30743); - for (const key in cacheOptions.buildDependencies) { - const list = cacheOptions.buildDependencies[key]; - new AddBuildDependenciesPlugin(list).apply(compiler); - } - if (!isFinite(cacheOptions.maxMemoryGenerations)) { - //@ts-expect-error https://github.com/microsoft/TypeScript/issues/41697 - const MemoryCachePlugin = __webpack_require__(4045); - new MemoryCachePlugin().apply(compiler); - } else if (cacheOptions.maxMemoryGenerations !== 0) { - //@ts-expect-error https://github.com/microsoft/TypeScript/issues/41697 - const MemoryWithGcCachePlugin = __webpack_require__(34854); - new MemoryWithGcCachePlugin({ - maxGenerations: cacheOptions.maxMemoryGenerations - }).apply(compiler); - } - if (cacheOptions.memoryCacheUnaffected) { - if (!options.experiments.cacheUnaffected) { - throw new Error( - "'cache.memoryCacheUnaffected: true' is only allowed when 'experiments.cacheUnaffected' is enabled" - ); - } - compiler.moduleMemCaches = new Map(); - } - switch (cacheOptions.store) { - case "pack": { - const IdleFileCachePlugin = __webpack_require__(26277); - const PackFileCacheStrategy = __webpack_require__(46810); - new IdleFileCachePlugin( - new PackFileCacheStrategy({ - compiler, - fs: compiler.intermediateFileSystem, - context: options.context, - cacheLocation: cacheOptions.cacheLocation, - version: cacheOptions.version, - logger: compiler.getInfrastructureLogger( - "webpack.cache.PackFileCacheStrategy" - ), - snapshot: options.snapshot, - maxAge: cacheOptions.maxAge, - profile: cacheOptions.profile, - allowCollectingMemory: cacheOptions.allowCollectingMemory, - compression: cacheOptions.compression - }), - cacheOptions.idleTimeout, - cacheOptions.idleTimeoutForInitialStore, - cacheOptions.idleTimeoutAfterLargeChanges - ).apply(compiler); - break; + /** + * Apply the plugin + * @param {Compiler} compiler the compiler instance + * @returns {void} + */ + apply(compiler) { + const definitions = this.definitions; + compiler.hooks.compilation.tap( + "ProvidePlugin", + (compilation, { normalModuleFactory }) => { + compilation.dependencyTemplates.set( + ConstDependency, + new ConstDependency.Template() + ); + compilation.dependencyFactories.set( + ProvidedDependency, + normalModuleFactory + ); + compilation.dependencyTemplates.set( + ProvidedDependency, + new ProvidedDependency.Template() + ); + const handler = (parser, parserOptions) => { + Object.keys(definitions).forEach(name => { + const request = [].concat(definitions[name]); + const splittedName = name.split("."); + if (splittedName.length > 0) { + splittedName.slice(1).forEach((_, i) => { + const name = splittedName.slice(0, i + 1).join("."); + parser.hooks.canRename.for(name).tap("ProvidePlugin", approve); + }); } - default: - throw new Error("Unhandled value for cache.store"); - } - break; - } - default: - // @ts-expect-error Property 'type' does not exist on type 'never'. ts(2339) - throw new Error(`Unknown cache type ${cacheOptions.type}`); - } - } - new ResolverCachePlugin().apply(compiler); - if (options.ignoreWarnings && options.ignoreWarnings.length > 0) { - const IgnoreWarningsPlugin = __webpack_require__(18913); - new IgnoreWarningsPlugin(options.ignoreWarnings).apply(compiler); - } + parser.hooks.expression.for(name).tap("ProvidePlugin", expr => { + const nameIdentifier = name.includes(".") + ? `__webpack_provided_${name.replace(/\./g, "_dot_")}` + : name; + const dep = new ProvidedDependency( + request[0], + nameIdentifier, + request.slice(1), + expr.range + ); + dep.loc = expr.loc; + parser.state.module.addDependency(dep); + return true; + }); - compiler.hooks.afterPlugins.call(compiler); - if (!compiler.inputFileSystem) { - throw new Error("No input filesystem provided"); - } - compiler.resolverFactory.hooks.resolveOptions - .for("normal") - .tap("WebpackOptionsApply", resolveOptions => { - resolveOptions = cleverMerge(options.resolve, resolveOptions); - resolveOptions.fileSystem = compiler.inputFileSystem; - return resolveOptions; - }); - compiler.resolverFactory.hooks.resolveOptions - .for("context") - .tap("WebpackOptionsApply", resolveOptions => { - resolveOptions = cleverMerge(options.resolve, resolveOptions); - resolveOptions.fileSystem = compiler.inputFileSystem; - resolveOptions.resolveToContext = true; - return resolveOptions; - }); - compiler.resolverFactory.hooks.resolveOptions - .for("loader") - .tap("WebpackOptionsApply", resolveOptions => { - resolveOptions = cleverMerge(options.resolveLoader, resolveOptions); - resolveOptions.fileSystem = compiler.inputFileSystem; - return resolveOptions; - }); - compiler.hooks.afterResolvers.call(compiler); - return options; + parser.hooks.call.for(name).tap("ProvidePlugin", expr => { + const nameIdentifier = name.includes(".") + ? `__webpack_provided_${name.replace(/\./g, "_dot_")}` + : name; + const dep = new ProvidedDependency( + request[0], + nameIdentifier, + request.slice(1), + expr.callee.range + ); + dep.loc = expr.callee.loc; + parser.state.module.addDependency(dep); + parser.walkExpressions(expr.arguments); + return true; + }); + }); + }; + normalModuleFactory.hooks.parser + .for("javascript/auto") + .tap("ProvidePlugin", handler); + normalModuleFactory.hooks.parser + .for("javascript/dynamic") + .tap("ProvidePlugin", handler); + normalModuleFactory.hooks.parser + .for("javascript/esm") + .tap("ProvidePlugin", handler); + } + ); } } -module.exports = WebpackOptionsApply; +module.exports = ProvidePlugin; /***/ }), -/***/ 547: +/***/ 82329: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; @@ -63302,435 +59253,463 @@ module.exports = WebpackOptionsApply; -const { applyWebpackOptionsDefaults } = __webpack_require__(27057); -const { getNormalizedWebpackOptions } = __webpack_require__(52975); +const { OriginalSource, RawSource } = __webpack_require__(96192); +const Module = __webpack_require__(85887); +const makeSerializable = __webpack_require__(26522); -class WebpackOptionsDefaulter { - process(options) { - options = getNormalizedWebpackOptions(options); - applyWebpackOptionsDefaults(options); - return options; +/** @typedef {import("webpack-sources").Source} Source */ +/** @typedef {import("../declarations/WebpackOptions").WebpackOptionsNormalized} WebpackOptions */ +/** @typedef {import("./ChunkGraph")} ChunkGraph */ +/** @typedef {import("./Compilation")} Compilation */ +/** @typedef {import("./Dependency").UpdateHashContext} UpdateHashContext */ +/** @typedef {import("./DependencyTemplates")} DependencyTemplates */ +/** @typedef {import("./Module").CodeGenerationContext} CodeGenerationContext */ +/** @typedef {import("./Module").CodeGenerationResult} CodeGenerationResult */ +/** @typedef {import("./Module").NeedBuildContext} NeedBuildContext */ +/** @typedef {import("./RequestShortener")} RequestShortener */ +/** @typedef {import("./ResolverFactory").ResolverWithOptions} ResolverWithOptions */ +/** @typedef {import("./RuntimeTemplate")} RuntimeTemplate */ +/** @typedef {import("./WebpackError")} WebpackError */ +/** @typedef {import("./util/Hash")} Hash */ +/** @typedef {import("./util/fs").InputFileSystem} InputFileSystem */ + +const TYPES = new Set(["javascript"]); + +class RawModule extends Module { + /** + * @param {string} source source code + * @param {string} identifier unique identifier + * @param {string=} readableIdentifier readable identifier + * @param {ReadonlySet=} runtimeRequirements runtime requirements needed for the source code + */ + constructor(source, identifier, readableIdentifier, runtimeRequirements) { + super("javascript/dynamic", null); + this.sourceStr = source; + this.identifierStr = identifier || this.sourceStr; + this.readableIdentifierStr = readableIdentifier || this.identifierStr; + this.runtimeRequirements = runtimeRequirements || null; + } + + /** + * @returns {Set} types available (do not mutate) + */ + getSourceTypes() { + return TYPES; + } + + /** + * @returns {string} a unique identifier of the module + */ + identifier() { + return this.identifierStr; + } + + /** + * @param {string=} type the source type for which the size should be estimated + * @returns {number} the estimated size of the module (must be non-zero) + */ + size(type) { + return Math.max(1, this.sourceStr.length); + } + + /** + * @param {RequestShortener} requestShortener the request shortener + * @returns {string} a user readable identifier of the module + */ + readableIdentifier(requestShortener) { + return requestShortener.shorten(this.readableIdentifierStr); + } + + /** + * @param {NeedBuildContext} context context info + * @param {function(WebpackError=, boolean=): void} callback callback function, returns true, if the module needs a rebuild + * @returns {void} + */ + needBuild(context, callback) { + return callback(null, !this.buildMeta); + } + + /** + * @param {WebpackOptions} options webpack options + * @param {Compilation} compilation the compilation + * @param {ResolverWithOptions} resolver the resolver + * @param {InputFileSystem} fs the file system + * @param {function(WebpackError=): void} callback callback function + * @returns {void} + */ + build(options, compilation, resolver, fs, callback) { + this.buildMeta = {}; + this.buildInfo = { + cacheable: true + }; + callback(); + } + + /** + * @param {CodeGenerationContext} context context for code generation + * @returns {CodeGenerationResult} result + */ + codeGeneration(context) { + const sources = new Map(); + if (this.useSourceMap || this.useSimpleSourceMap) { + sources.set( + "javascript", + new OriginalSource(this.sourceStr, this.identifier()) + ); + } else { + sources.set("javascript", new RawSource(this.sourceStr)); + } + return { sources, runtimeRequirements: this.runtimeRequirements }; + } + + /** + * @param {Hash} hash the hash used to track dependencies + * @param {UpdateHashContext} context context + * @returns {void} + */ + updateHash(hash, context) { + hash.update(this.sourceStr); + super.updateHash(hash, context); + } + + serialize(context) { + const { write } = context; + + write(this.sourceStr); + write(this.identifierStr); + write(this.readableIdentifierStr); + write(this.runtimeRequirements); + + super.serialize(context); + } + + deserialize(context) { + const { read } = context; + + this.sourceStr = read(); + this.identifierStr = read(); + this.readableIdentifierStr = read(); + this.runtimeRequirements = read(); + + super.deserialize(context); } } -module.exports = WebpackOptionsDefaulter; +makeSerializable(RawModule, "webpack/lib/RawModule"); + +module.exports = RawModule; /***/ }), -/***/ 18764: +/***/ 64122: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; /* MIT License http://www.opensource.org/licenses/mit-license.php - Author Sergey Melyukov @smelukov + Author Tobias Koppers @sokra */ -const mimeTypes = __webpack_require__(19338); -const path = __webpack_require__(85622); -const { RawSource } = __webpack_require__(96192); -const Generator = __webpack_require__(1826); -const RuntimeGlobals = __webpack_require__(49404); -const createHash = __webpack_require__(24123); -const { makePathsRelative } = __webpack_require__(96236); - -/** @typedef {import("webpack-sources").Source} Source */ -/** @typedef {import("../../declarations/WebpackOptions").AssetGeneratorOptions} AssetGeneratorOptions */ -/** @typedef {import("../../declarations/WebpackOptions").RawPublicPath} RawPublicPath */ -/** @typedef {import("../Compilation")} Compilation */ -/** @typedef {import("../Compiler")} Compiler */ -/** @typedef {import("../Generator").GenerateContext} GenerateContext */ -/** @typedef {import("../Generator").UpdateHashContext} UpdateHashContext */ -/** @typedef {import("../Module")} Module */ -/** @typedef {import("../NormalModule")} NormalModule */ -/** @typedef {import("../RuntimeTemplate")} RuntimeTemplate */ -/** @typedef {import("../util/Hash")} Hash */ +const { compareNumbers } = __webpack_require__(26296); +const identifierUtils = __webpack_require__(96236); -const mergeMaybeArrays = (a, b) => { - const set = new Set(); - if (Array.isArray(a)) for (const item of a) set.add(item); - else set.add(a); - if (Array.isArray(b)) for (const item of b) set.add(item); - else set.add(b); - return Array.from(set); -}; +/** @typedef {import("./Chunk")} Chunk */ +/** @typedef {import("./Compiler")} Compiler */ +/** @typedef {import("./Module")} Module */ -const mergeAssetInfo = (a, b) => { - const result = { ...a, ...b }; - for (const key of Object.keys(a)) { - if (key in b) { - if (a[key] === b[key]) continue; - switch (key) { - case "fullhash": - case "chunkhash": - case "modulehash": - case "contenthash": - result[key] = mergeMaybeArrays(a[key], b[key]); - break; - case "immutable": - case "development": - case "hotModuleReplacement": - case "javascriptModule ": - result[key] = a[key] || b[key]; - break; - case "related": - result[key] = mergeRelatedInfo(a[key], b[key]); - break; - default: - throw new Error(`Can't handle conflicting asset info for ${key}`); - } - } - } - return result; -}; +/** + * @typedef {Object} RecordsChunks + * @property {Record=} byName + * @property {Record=} bySource + * @property {number[]=} usedIds + */ -const mergeRelatedInfo = (a, b) => { - const result = { ...a, ...b }; - for (const key of Object.keys(a)) { - if (key in b) { - if (a[key] === b[key]) continue; - result[key] = mergeMaybeArrays(a[key], b[key]); - } - } - return result; -}; +/** + * @typedef {Object} RecordsModules + * @property {Record=} byIdentifier + * @property {Record=} bySource + * @property {number[]=} usedIds + */ -const JS_TYPES = new Set(["javascript"]); -const JS_AND_ASSET_TYPES = new Set(["javascript", "asset"]); +/** + * @typedef {Object} Records + * @property {RecordsChunks=} chunks + * @property {RecordsModules=} modules + */ -class AssetGenerator extends Generator { +class RecordIdsPlugin { /** - * @param {AssetGeneratorOptions["dataUrl"]=} dataUrlOptions the options for the data url - * @param {string=} filename override for output.assetModuleFilename - * @param {RawPublicPath=} publicPath override for output.assetModulePublicPath - * @param {boolean=} emit generate output asset + * @param {Object} options Options object + * @param {boolean=} options.portableIds true, when ids need to be portable */ - constructor(dataUrlOptions, filename, publicPath, emit) { - super(); - this.dataUrlOptions = dataUrlOptions; - this.filename = filename; - this.publicPath = publicPath; - this.emit = emit; + constructor(options) { + this.options = options || {}; } /** - * @param {NormalModule} module module for which the code should be generated - * @param {GenerateContext} generateContext context for generate - * @returns {Source} generated code + * @param {Compiler} compiler the Compiler + * @returns {void} */ - generate( - module, - { runtime, chunkGraph, runtimeTemplate, runtimeRequirements, type, getData } - ) { - switch (type) { - case "asset": - return module.originalSource(); - default: { - runtimeRequirements.add(RuntimeGlobals.module); + apply(compiler) { + const portableIds = this.options.portableIds; - const originalSource = module.originalSource(); - if (module.buildInfo.dataUrl) { - let encodedSource; - if (typeof this.dataUrlOptions === "function") { - encodedSource = this.dataUrlOptions.call( - null, - originalSource.source(), - { - filename: module.matchResource || module.resource, - module - } - ); - } else { - /** @type {string | false | undefined} */ - let encoding = this.dataUrlOptions.encoding; - if (encoding === undefined) { - if ( - module.resourceResolveData && - module.resourceResolveData.encoding !== undefined - ) { - encoding = module.resourceResolveData.encoding; - } - } - if (encoding === undefined) { - encoding = "base64"; - } - let ext; - let mimeType = this.dataUrlOptions.mimetype; - if (mimeType === undefined) { - ext = path.extname(module.nameForCondition()); - if ( - module.resourceResolveData && - module.resourceResolveData.mimetype !== undefined - ) { - mimeType = - module.resourceResolveData.mimetype + - module.resourceResolveData.parameters; - } else if (ext) { - mimeType = mimeTypes.lookup(ext); - } - } - if (typeof mimeType !== "string") { - throw new Error( - "DataUrl can't be generated automatically, " + - `because there is no mimetype for "${ext}" in mimetype database. ` + - 'Either pass a mimetype via "generator.mimetype" or ' + - 'use type: "asset/resource" to create a resource file instead of a DataUrl' - ); - } + const makePathsRelative = + identifierUtils.makePathsRelative.bindContextCache( + compiler.context, + compiler.root + ); - let encodedContent; - if ( - module.resourceResolveData && - module.resourceResolveData.encoding === encoding - ) { - encodedContent = module.resourceResolveData.encodedContent; - } else { - switch (encoding) { - case "base64": { - encodedContent = originalSource.buffer().toString("base64"); - break; - } - case false: { - const content = originalSource.source(); + /** + * @param {Module} module the module + * @returns {string} the (portable) identifier + */ + const getModuleIdentifier = module => { + if (portableIds) { + return makePathsRelative(module.identifier()); + } + return module.identifier(); + }; - if (typeof content !== "string") { - encodedContent = content.toString("utf-8"); - } + compiler.hooks.compilation.tap("RecordIdsPlugin", compilation => { + compilation.hooks.recordModules.tap( + "RecordIdsPlugin", + /** + * @param {Module[]} modules the modules array + * @param {Records} records the records object + * @returns {void} + */ + (modules, records) => { + const chunkGraph = compilation.chunkGraph; + if (!records.modules) records.modules = {}; + if (!records.modules.byIdentifier) records.modules.byIdentifier = {}; + /** @type {Set} */ + const usedIds = new Set(); + for (const module of modules) { + const moduleId = chunkGraph.getModuleId(module); + if (typeof moduleId !== "number") continue; + const identifier = getModuleIdentifier(module); + records.modules.byIdentifier[identifier] = moduleId; + usedIds.add(moduleId); + } + records.modules.usedIds = Array.from(usedIds).sort(compareNumbers); + } + ); + compilation.hooks.reviveModules.tap( + "RecordIdsPlugin", + /** + * @param {Module[]} modules the modules array + * @param {Records} records the records object + * @returns {void} + */ + (modules, records) => { + if (!records.modules) return; + if (records.modules.byIdentifier) { + const chunkGraph = compilation.chunkGraph; + /** @type {Set} */ + const usedIds = new Set(); + for (const module of modules) { + const moduleId = chunkGraph.getModuleId(module); + if (moduleId !== null) continue; + const identifier = getModuleIdentifier(module); + const id = records.modules.byIdentifier[identifier]; + if (id === undefined) continue; + if (usedIds.has(id)) continue; + usedIds.add(id); + chunkGraph.setModuleId(module, id); + } + } + if (Array.isArray(records.modules.usedIds)) { + compilation.usedModuleIds = new Set(records.modules.usedIds); + } + } + ); - encodedContent = encodeURIComponent(encodedContent).replace( - /[!'()*]/g, - character => "%" + character.codePointAt(0).toString(16) + /** + * @param {Chunk} chunk the chunk + * @returns {string[]} sources of the chunk + */ + const getChunkSources = chunk => { + /** @type {string[]} */ + const sources = []; + for (const chunkGroup of chunk.groupsIterable) { + const index = chunkGroup.chunks.indexOf(chunk); + if (chunkGroup.name) { + sources.push(`${index} ${chunkGroup.name}`); + } else { + for (const origin of chunkGroup.origins) { + if (origin.module) { + if (origin.request) { + sources.push( + `${index} ${getModuleIdentifier(origin.module)} ${ + origin.request + }` + ); + } else if (typeof origin.loc === "string") { + sources.push( + `${index} ${getModuleIdentifier(origin.module)} ${ + origin.loc + }` + ); + } else if ( + origin.loc && + typeof origin.loc === "object" && + "start" in origin.loc + ) { + sources.push( + `${index} ${getModuleIdentifier( + origin.module + )} ${JSON.stringify(origin.loc.start)}` ); - break; } - default: - throw new Error(`Unsupported encoding '${encoding}'`); } } - - encodedSource = `data:${mimeType}${ - encoding ? `;${encoding}` : "" - },${encodedContent}`; - } - return new RawSource( - `${RuntimeGlobals.module}.exports = ${JSON.stringify( - encodedSource - )};` - ); - } else { - const assetModuleFilename = - this.filename || runtimeTemplate.outputOptions.assetModuleFilename; - const hash = createHash(runtimeTemplate.outputOptions.hashFunction); - if (runtimeTemplate.outputOptions.hashSalt) { - hash.update(runtimeTemplate.outputOptions.hashSalt); } - hash.update(originalSource.buffer()); - const fullHash = /** @type {string} */ ( - hash.digest(runtimeTemplate.outputOptions.hashDigest) - ); - const contentHash = fullHash.slice( - 0, - runtimeTemplate.outputOptions.hashDigestLength - ); - module.buildInfo.fullContentHash = fullHash; - const sourceFilename = makePathsRelative( - runtimeTemplate.compilation.compiler.context, - module.matchResource || module.resource, - runtimeTemplate.compilation.compiler.root - ).replace(/^\.\//, ""); - let { path: filename, info: assetInfo } = - runtimeTemplate.compilation.getAssetPathWithInfo( - assetModuleFilename, - { - module, - runtime, - filename: sourceFilename, - chunkGraph, - contentHash + } + return sources; + }; + + compilation.hooks.recordChunks.tap( + "RecordIdsPlugin", + /** + * @param {Chunk[]} chunks the chunks array + * @param {Records} records the records object + * @returns {void} + */ + (chunks, records) => { + if (!records.chunks) records.chunks = {}; + if (!records.chunks.byName) records.chunks.byName = {}; + if (!records.chunks.bySource) records.chunks.bySource = {}; + /** @type {Set} */ + const usedIds = new Set(); + for (const chunk of chunks) { + if (typeof chunk.id !== "number") continue; + const name = chunk.name; + if (name) records.chunks.byName[name] = chunk.id; + const sources = getChunkSources(chunk); + for (const source of sources) { + records.chunks.bySource[source] = chunk.id; + } + usedIds.add(chunk.id); + } + records.chunks.usedIds = Array.from(usedIds).sort(compareNumbers); + } + ); + compilation.hooks.reviveChunks.tap( + "RecordIdsPlugin", + /** + * @param {Chunk[]} chunks the chunks array + * @param {Records} records the records object + * @returns {void} + */ + (chunks, records) => { + if (!records.chunks) return; + /** @type {Set} */ + const usedIds = new Set(); + if (records.chunks.byName) { + for (const chunk of chunks) { + if (chunk.id !== null) continue; + if (!chunk.name) continue; + const id = records.chunks.byName[chunk.name]; + if (id === undefined) continue; + if (usedIds.has(id)) continue; + usedIds.add(id); + chunk.id = id; + chunk.ids = [id]; + } + } + if (records.chunks.bySource) { + for (const chunk of chunks) { + if (chunk.id !== null) continue; + const sources = getChunkSources(chunk); + for (const source of sources) { + const id = records.chunks.bySource[source]; + if (id === undefined) continue; + if (usedIds.has(id)) continue; + usedIds.add(id); + chunk.id = id; + chunk.ids = [id]; + break; } - ); - let publicPath; - if (this.publicPath !== undefined) { - const { path, info } = - runtimeTemplate.compilation.getAssetPathWithInfo( - this.publicPath, - { - module, - runtime, - filename: sourceFilename, - chunkGraph, - contentHash - } - ); - publicPath = JSON.stringify(path); - assetInfo = mergeAssetInfo(assetInfo, info); - } else { - publicPath = RuntimeGlobals.publicPath; - runtimeRequirements.add(RuntimeGlobals.publicPath); // add __webpack_require__.p + } } - assetInfo = { - sourceFilename, - ...assetInfo - }; - module.buildInfo.filename = filename; - module.buildInfo.assetInfo = assetInfo; - if (getData) { - // Due to code generation caching module.buildInfo.XXX can't used to store such information - // It need to be stored in the code generation results instead, where it's cached too - // TODO webpack 6 For back-compat reasons we also store in on module.buildInfo - const data = getData(); - data.set("fullContentHash", fullHash); - data.set("filename", filename); - data.set("assetInfo", assetInfo); + if (Array.isArray(records.chunks.usedIds)) { + compilation.usedChunkIds = new Set(records.chunks.usedIds); } - - return new RawSource( - `${ - RuntimeGlobals.module - }.exports = ${publicPath} + ${JSON.stringify(filename)};` - ); } - } - } + ); + }); } +} +module.exports = RecordIdsPlugin; - /** - * @param {NormalModule} module fresh module - * @returns {Set} available types (do not mutate) - */ - getTypes(module) { - if ((module.buildInfo && module.buildInfo.dataUrl) || this.emit === false) { - return JS_TYPES; - } else { - return JS_AND_ASSET_TYPES; - } - } - /** - * @param {NormalModule} module the module - * @param {string=} type source type - * @returns {number} estimate size of the module - */ - getSize(module, type) { - switch (type) { - case "asset": { - const originalSource = module.originalSource(); +/***/ }), - if (!originalSource) { - return 0; - } +/***/ 43157: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - return originalSource.size(); - } - default: - if (module.buildInfo && module.buildInfo.dataUrl) { - const originalSource = module.originalSource(); +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ - if (!originalSource) { - return 0; - } - // roughly for data url - // Example: m.exports="data:image/png;base64,ag82/f+2==" - // 4/3 = base64 encoding - // 34 = ~ data url header + footer + rounding - return originalSource.size() * 1.34 + 36; - } else { - // it's only estimated so this number is probably fine - // Example: m.exports=r.p+"0123456789012345678901.ext" - return 42; - } - } + +const { contextify } = __webpack_require__(96236); + +class RequestShortener { + /** + * @param {string} dir the directory + * @param {object=} associatedObjectForCache an object to which the cache will be attached + */ + constructor(dir, associatedObjectForCache) { + this.contextify = contextify.bindContextCache( + dir, + associatedObjectForCache + ); } /** - * @param {Hash} hash hash that will be modified - * @param {UpdateHashContext} updateHashContext context for updating hash + * @param {string | undefined | null} request the request to shorten + * @returns {string | undefined | null} the shortened request */ - updateHash(hash, { module }) { - hash.update(module.buildInfo.dataUrl ? "data-url" : "resource"); + shorten(request) { + if (!request) { + return request; + } + return this.contextify(request); } } -module.exports = AssetGenerator; +module.exports = RequestShortener; /***/ }), -/***/ 42553: +/***/ 81898: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; /* MIT License http://www.opensource.org/licenses/mit-license.php - Author Yuta Hiroto @hiroppy + Author Tobias Koppers @sokra */ -const { cleverMerge } = __webpack_require__(11217); -const { compareModulesByIdentifier } = __webpack_require__(26296); -const createSchemaValidation = __webpack_require__(77695); -const memoize = __webpack_require__(84297); - -/** @typedef {import("webpack-sources").Source} Source */ -/** @typedef {import("../Chunk")} Chunk */ -/** @typedef {import("../Compiler")} Compiler */ -/** @typedef {import("../Module")} Module */ - -const getSchema = name => { - const { definitions } = __webpack_require__(1863); - return { - definitions, - oneOf: [{ $ref: `#/definitions/${name}` }] - }; -}; - -const generatorValidationOptions = { - name: "Asset Modules Plugin", - baseDataPath: "generator" -}; -const validateGeneratorOptions = { - asset: createSchemaValidation( - __webpack_require__(76961), - () => getSchema("AssetGeneratorOptions"), - generatorValidationOptions - ), - "asset/resource": createSchemaValidation( - __webpack_require__(15643), - () => getSchema("AssetResourceGeneratorOptions"), - generatorValidationOptions - ), - "asset/inline": createSchemaValidation( - __webpack_require__(40851), - () => getSchema("AssetInlineGeneratorOptions"), - generatorValidationOptions - ) -}; - -const validateParserOptions = createSchemaValidation( - __webpack_require__(85912), - () => getSchema("AssetParserOptions"), - { - name: "Asset Modules Plugin", - baseDataPath: "parser" - } -); - -const getAssetGenerator = memoize(() => __webpack_require__(18764)); -const getAssetParser = memoize(() => __webpack_require__(13055)); -const getAssetSourceParser = memoize(() => __webpack_require__(75925)); -const getAssetSourceGenerator = memoize(() => - __webpack_require__(66511) -); +const RuntimeGlobals = __webpack_require__(49404); +const ConstDependency = __webpack_require__(60864); +const { + toConstantDependency +} = __webpack_require__(28723); -const type = "asset"; -const plugin = "AssetModulesPlugin"; +/** @typedef {import("./Compiler")} Compiler */ -class AssetModulesPlugin { +module.exports = class RequireJsStuffPlugin { /** * Apply the plugin * @param {Compiler} compiler the compiler instance @@ -63738,1973 +59717,2146 @@ class AssetModulesPlugin { */ apply(compiler) { compiler.hooks.compilation.tap( - plugin, + "RequireJsStuffPlugin", (compilation, { normalModuleFactory }) => { - normalModuleFactory.hooks.createParser - .for("asset") - .tap(plugin, parserOptions => { - validateParserOptions(parserOptions); - parserOptions = cleverMerge( - compiler.options.module.parser.asset, - parserOptions - ); - - let dataUrlCondition = parserOptions.dataUrlCondition; - if (!dataUrlCondition || typeof dataUrlCondition === "object") { - dataUrlCondition = { - maxSize: 8096, - ...dataUrlCondition - }; - } - - const AssetParser = getAssetParser(); - - return new AssetParser(dataUrlCondition); - }); - normalModuleFactory.hooks.createParser - .for("asset/inline") - .tap(plugin, parserOptions => { - const AssetParser = getAssetParser(); - - return new AssetParser(true); - }); - normalModuleFactory.hooks.createParser - .for("asset/resource") - .tap(plugin, parserOptions => { - const AssetParser = getAssetParser(); - - return new AssetParser(false); - }); - normalModuleFactory.hooks.createParser - .for("asset/source") - .tap(plugin, parserOptions => { - const AssetSourceParser = getAssetSourceParser(); - - return new AssetSourceParser(); - }); - - for (const type of ["asset", "asset/inline", "asset/resource"]) { - normalModuleFactory.hooks.createGenerator - .for(type) - .tap(plugin, generatorOptions => { - validateGeneratorOptions[type](generatorOptions); - - let dataUrl = undefined; - if (type !== "asset/resource") { - dataUrl = generatorOptions.dataUrl; - if (!dataUrl || typeof dataUrl === "object") { - dataUrl = { - encoding: undefined, - mimetype: undefined, - ...dataUrl - }; - } - } - - let filename = undefined; - let publicPath = undefined; - if (type !== "asset/inline") { - filename = generatorOptions.filename; - publicPath = generatorOptions.publicPath; - } - - const AssetGenerator = getAssetGenerator(); - - return new AssetGenerator( - dataUrl, - filename, - publicPath, - generatorOptions.emit !== false - ); - }); - } - normalModuleFactory.hooks.createGenerator - .for("asset/source") - .tap(plugin, () => { - const AssetSourceGenerator = getAssetSourceGenerator(); - - return new AssetSourceGenerator(); - }); - - compilation.hooks.renderManifest.tap(plugin, (result, options) => { - const { chunkGraph } = compilation; - const { chunk, codeGenerationResults } = options; - - const modules = chunkGraph.getOrderedChunkModulesIterableBySourceType( - chunk, - "asset", - compareModulesByIdentifier - ); - if (modules) { - for (const module of modules) { - try { - const codeGenResult = codeGenerationResults.get( - module, - chunk.runtime - ); - result.push({ - render: () => codeGenResult.sources.get(type), - filename: - module.buildInfo.filename || - codeGenResult.data.get("filename"), - info: - module.buildInfo.assetInfo || - codeGenResult.data.get("assetInfo"), - auxiliary: true, - identifier: `assetModule${chunkGraph.getModuleId(module)}`, - hash: - module.buildInfo.fullContentHash || - codeGenResult.data.get("fullContentHash") - }); - } catch (e) { - e.message += `\nduring rendering of asset ${module.identifier()}`; - throw e; - } - } + compilation.dependencyTemplates.set( + ConstDependency, + new ConstDependency.Template() + ); + const handler = (parser, parserOptions) => { + if ( + parserOptions.requireJs === undefined || + !parserOptions.requireJs + ) { + return; } - return result; - }); + parser.hooks.call + .for("require.config") + .tap( + "RequireJsStuffPlugin", + toConstantDependency(parser, "undefined") + ); + parser.hooks.call + .for("requirejs.config") + .tap( + "RequireJsStuffPlugin", + toConstantDependency(parser, "undefined") + ); - compilation.hooks.prepareModuleExecution.tap( - "AssetModulesPlugin", - (options, context) => { - const { codeGenerationResult } = options; - const source = codeGenerationResult.sources.get("asset"); - if (source === undefined) return; - context.assets.set(codeGenerationResult.data.get("filename"), { - source, - info: codeGenerationResult.data.get("assetInfo") - }); - } - ); + parser.hooks.expression + .for("require.version") + .tap( + "RequireJsStuffPlugin", + toConstantDependency(parser, JSON.stringify("0.0.0")) + ); + parser.hooks.expression + .for("requirejs.onError") + .tap( + "RequireJsStuffPlugin", + toConstantDependency( + parser, + RuntimeGlobals.uncaughtErrorHandler, + [RuntimeGlobals.uncaughtErrorHandler] + ) + ); + }; + normalModuleFactory.hooks.parser + .for("javascript/auto") + .tap("RequireJsStuffPlugin", handler); + normalModuleFactory.hooks.parser + .for("javascript/dynamic") + .tap("RequireJsStuffPlugin", handler); } ); } -} - -module.exports = AssetModulesPlugin; +}; /***/ }), -/***/ 13055: +/***/ 88810: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; /* MIT License http://www.opensource.org/licenses/mit-license.php - Author Yuta Hiroto @hiroppy + Author Tobias Koppers @sokra */ -const Parser = __webpack_require__(68214); +const Factory = __webpack_require__(27480).ResolverFactory; +const { HookMap, SyncHook, SyncWaterfallHook } = __webpack_require__(34718); +const { + cachedCleverMerge, + removeOperations, + resolveByProperty +} = __webpack_require__(11217); -/** @typedef {import("../../declarations/WebpackOptions").AssetParserOptions} AssetParserOptions */ -/** @typedef {import("../Parser").ParserState} ParserState */ -/** @typedef {import("../Parser").PreparsedAst} PreparsedAst */ +/** @typedef {import("enhanced-resolve").ResolveOptions} ResolveOptions */ +/** @typedef {import("enhanced-resolve").Resolver} Resolver */ +/** @typedef {import("../declarations/WebpackOptions").ResolveOptions} WebpackResolveOptions */ +/** @typedef {import("../declarations/WebpackOptions").ResolvePluginInstance} ResolvePluginInstance */ + +/** @typedef {WebpackResolveOptions & {dependencyType?: string, resolveToContext?: boolean }} ResolveOptionsWithDependencyType */ +/** + * @typedef {Object} WithOptions + * @property {function(Partial): ResolverWithOptions} withOptions create a resolver with additional/different options + */ + +/** @typedef {Resolver & WithOptions} ResolverWithOptions */ + +// need to be hoisted on module level for caching identity +const EMPTY_RESOLVE_OPTIONS = {}; + +/** + * @param {ResolveOptionsWithDependencyType} resolveOptionsWithDepType enhanced options + * @returns {ResolveOptions} merged options + */ +const convertToResolveOptions = resolveOptionsWithDepType => { + const { dependencyType, plugins, ...remaining } = resolveOptionsWithDepType; + + // check type compat + /** @type {Partial} */ + const partialOptions = { + ...remaining, + plugins: + plugins && + /** @type {ResolvePluginInstance[]} */ ( + plugins.filter(item => item !== "...") + ) + }; + + if (!partialOptions.fileSystem) { + throw new Error( + "fileSystem is missing in resolveOptions, but it's required for enhanced-resolve" + ); + } + // These weird types validate that we checked all non-optional properties + const options = + /** @type {Partial & Pick} */ ( + partialOptions + ); + + return removeOperations( + resolveByProperty(options, "byDependency", dependencyType) + ); +}; + +/** + * @typedef {Object} ResolverCache + * @property {WeakMap} direct + * @property {Map} stringified + */ + +module.exports = class ResolverFactory { + constructor() { + this.hooks = Object.freeze({ + /** @type {HookMap>} */ + resolveOptions: new HookMap( + () => new SyncWaterfallHook(["resolveOptions"]) + ), + /** @type {HookMap>} */ + resolver: new HookMap( + () => new SyncHook(["resolver", "resolveOptions", "userResolveOptions"]) + ) + }); + /** @type {Map} */ + this.cache = new Map(); + } -class AssetParser extends Parser { /** - * @param {AssetParserOptions["dataUrlCondition"] | boolean} dataUrlCondition condition for inlining as DataUrl + * @param {string} type type of resolver + * @param {ResolveOptionsWithDependencyType=} resolveOptions options + * @returns {ResolverWithOptions} the resolver */ - constructor(dataUrlCondition) { - super(); - this.dataUrlCondition = dataUrlCondition; + get(type, resolveOptions = EMPTY_RESOLVE_OPTIONS) { + let typedCaches = this.cache.get(type); + if (!typedCaches) { + typedCaches = { + direct: new WeakMap(), + stringified: new Map() + }; + this.cache.set(type, typedCaches); + } + const cachedResolver = typedCaches.direct.get(resolveOptions); + if (cachedResolver) { + return cachedResolver; + } + const ident = JSON.stringify(resolveOptions); + const resolver = typedCaches.stringified.get(ident); + if (resolver) { + typedCaches.direct.set(resolveOptions, resolver); + return resolver; + } + const newResolver = this._create(type, resolveOptions); + typedCaches.direct.set(resolveOptions, newResolver); + typedCaches.stringified.set(ident, newResolver); + return newResolver; } /** - * @param {string | Buffer | PreparsedAst} source the source to parse - * @param {ParserState} state the parser state - * @returns {ParserState} the parser state + * @param {string} type type of resolver + * @param {ResolveOptionsWithDependencyType} resolveOptionsWithDepType options + * @returns {ResolverWithOptions} the resolver */ - parse(source, state) { - if (typeof source === "object" && !Buffer.isBuffer(source)) { - throw new Error("AssetParser doesn't accept preparsed AST"); - } - state.module.buildInfo.strict = true; - state.module.buildMeta.exportsType = "default"; + _create(type, resolveOptionsWithDepType) { + /** @type {ResolveOptionsWithDependencyType} */ + const originalResolveOptions = { ...resolveOptionsWithDepType }; - if (typeof this.dataUrlCondition === "function") { - state.module.buildInfo.dataUrl = this.dataUrlCondition(source, { - filename: state.module.matchResource || state.module.resource, - module: state.module - }); - } else if (typeof this.dataUrlCondition === "boolean") { - state.module.buildInfo.dataUrl = this.dataUrlCondition; - } else if ( - this.dataUrlCondition && - typeof this.dataUrlCondition === "object" - ) { - state.module.buildInfo.dataUrl = - Buffer.byteLength(source) <= this.dataUrlCondition.maxSize; - } else { - throw new Error("Unexpected dataUrlCondition type"); + const resolveOptions = convertToResolveOptions( + this.hooks.resolveOptions.for(type).call(resolveOptionsWithDepType) + ); + const resolver = /** @type {ResolverWithOptions} */ ( + Factory.createResolver(resolveOptions) + ); + if (!resolver) { + throw new Error("No resolver created"); } - - return state; + /** @type {WeakMap, ResolverWithOptions>} */ + const childCache = new WeakMap(); + resolver.withOptions = options => { + const cacheEntry = childCache.get(options); + if (cacheEntry !== undefined) return cacheEntry; + const mergedOptions = cachedCleverMerge(originalResolveOptions, options); + const resolver = this.get(type, mergedOptions); + childCache.set(options, resolver); + return resolver; + }; + this.hooks.resolver + .for(type) + .call(resolver, resolveOptions, originalResolveOptions); + return resolver; } -} - -module.exports = AssetParser; +}; /***/ }), -/***/ 66511: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { +/***/ 49404: +/***/ (function(__unused_webpack_module, exports) { "use strict"; /* MIT License http://www.opensource.org/licenses/mit-license.php - Author Sergey Melyukov @smelukov + Author Tobias Koppers @sokra */ -const { RawSource } = __webpack_require__(96192); -const Generator = __webpack_require__(1826); -const RuntimeGlobals = __webpack_require__(49404); +/** + * the internal require function + */ +exports.require = "__webpack_require__"; -/** @typedef {import("webpack-sources").Source} Source */ -/** @typedef {import("../Generator").GenerateContext} GenerateContext */ -/** @typedef {import("../NormalModule")} NormalModule */ +/** + * access to properties of the internal require function/object + */ +exports.requireScope = "__webpack_require__.*"; -const TYPES = new Set(["javascript"]); +/** + * the internal exports object + */ +exports.exports = "__webpack_exports__"; -class AssetSourceGenerator extends Generator { - /** - * @param {NormalModule} module module for which the code should be generated - * @param {GenerateContext} generateContext context for generate - * @returns {Source} generated code - */ - generate(module, { chunkGraph, runtimeTemplate, runtimeRequirements }) { - runtimeRequirements.add(RuntimeGlobals.module); +/** + * top-level this need to be the exports object + */ +exports.thisAsExports = "top-level-this-exports"; - const originalSource = module.originalSource(); +/** + * runtime need to return the exports of the last entry module + */ +exports.returnExportsFromRuntime = "return-exports-from-runtime"; - if (!originalSource) { - return new RawSource(""); - } +/** + * the internal module object + */ +exports.module = "module"; - const content = originalSource.source(); +/** + * the internal module object + */ +exports.moduleId = "module.id"; - let encodedSource; - if (typeof content === "string") { - encodedSource = content; - } else { - encodedSource = content.toString("utf-8"); - } - return new RawSource( - `${RuntimeGlobals.module}.exports = ${JSON.stringify(encodedSource)};` - ); - } +/** + * the internal module object + */ +exports.moduleLoaded = "module.loaded"; - /** - * @param {NormalModule} module fresh module - * @returns {Set} available types (do not mutate) - */ - getTypes(module) { - return TYPES; - } +/** + * the bundle public path + */ +exports.publicPath = "__webpack_require__.p"; - /** - * @param {NormalModule} module the module - * @param {string=} type source type - * @returns {number} estimate size of the module - */ - getSize(module, type) { - const originalSource = module.originalSource(); +/** + * the module id of the entry point + */ +exports.entryModuleId = "__webpack_require__.s"; - if (!originalSource) { - return 0; - } +/** + * the module cache + */ +exports.moduleCache = "__webpack_require__.c"; - // Example: m.exports="abcd" - return originalSource.size() + 12; - } -} +/** + * the module functions + */ +exports.moduleFactories = "__webpack_require__.m"; -module.exports = AssetSourceGenerator; +/** + * the module functions, with only write access + */ +exports.moduleFactoriesAddOnly = "__webpack_require__.m (add only)"; +/** + * the chunk ensure function + */ +exports.ensureChunk = "__webpack_require__.e"; -/***/ }), +/** + * an object with handlers to ensure a chunk + */ +exports.ensureChunkHandlers = "__webpack_require__.f"; -/***/ 75925: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { +/** + * a runtime requirement if ensureChunkHandlers should include loading of chunk needed for entries + */ +exports.ensureChunkIncludeEntries = "__webpack_require__.f (include entries)"; -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Yuta Hiroto @hiroppy -*/ +/** + * the chunk prefetch function + */ +exports.prefetchChunk = "__webpack_require__.E"; +/** + * an object with handlers to prefetch a chunk + */ +exports.prefetchChunkHandlers = "__webpack_require__.F"; +/** + * the chunk preload function + */ +exports.preloadChunk = "__webpack_require__.G"; -const Parser = __webpack_require__(68214); +/** + * an object with handlers to preload a chunk + */ +exports.preloadChunkHandlers = "__webpack_require__.H"; -/** @typedef {import("../Parser").ParserState} ParserState */ -/** @typedef {import("../Parser").PreparsedAst} PreparsedAst */ +/** + * the exported property define getters function + */ +exports.definePropertyGetters = "__webpack_require__.d"; -class AssetSourceParser extends Parser { - /** - * @param {string | Buffer | PreparsedAst} source the source to parse - * @param {ParserState} state the parser state - * @returns {ParserState} the parser state - */ - parse(source, state) { - if (typeof source === "object" && !Buffer.isBuffer(source)) { - throw new Error("AssetSourceParser doesn't accept preparsed AST"); - } - const { module } = state; - module.buildInfo.strict = true; - module.buildMeta.exportsType = "default"; +/** + * define compatibility on export + */ +exports.makeNamespaceObject = "__webpack_require__.r"; - return state; - } -} +/** + * create a fake namespace object + */ +exports.createFakeNamespaceObject = "__webpack_require__.t"; -module.exports = AssetSourceParser; +/** + * compatibility get default export + */ +exports.compatGetDefaultExport = "__webpack_require__.n"; +/** + * harmony module decorator + */ +exports.harmonyModuleDecorator = "__webpack_require__.hmd"; -/***/ }), +/** + * node.js module decorator + */ +exports.nodeModuleDecorator = "__webpack_require__.nmd"; -/***/ 20911: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { +/** + * the webpack hash + */ +exports.getFullHash = "__webpack_require__.h"; -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ +/** + * an object containing all installed WebAssembly.Instance export objects keyed by module id + */ +exports.wasmInstances = "__webpack_require__.w"; +/** + * instantiate a wasm instance from module exports object, id, hash and importsObject + */ +exports.instantiateWasm = "__webpack_require__.v"; +/** + * the uncaught error handler for the webpack runtime + */ +exports.uncaughtErrorHandler = "__webpack_require__.oe"; -const InitFragment = __webpack_require__(51739); -const RuntimeGlobals = __webpack_require__(49404); -const Template = __webpack_require__(92066); +/** + * the script nonce + */ +exports.scriptNonce = "__webpack_require__.nc"; -/** @typedef {import("webpack-sources").Source} Source */ -/** @typedef {import("../Generator").GenerateContext} GenerateContext */ +/** + * function to load a script tag. + * Arguments: (url: string, done: (event) => void), key?: string | number, chunkId?: string | number) => void + * done function is called when loading has finished or timeout occurred. + * It will attach to existing script tags with data-webpack == key or src == url. + */ +exports.loadScript = "__webpack_require__.l"; /** - * @typedef {GenerateContext} Context + * function to promote a string to a TrustedScriptURL using webpack's Trusted + * Types policy + * Arguments: (url: string) => TrustedScriptURL */ -class AwaitDependenciesInitFragment extends InitFragment { - /** - * @param {Set} promises the promises that should be awaited - */ - constructor(promises) { - super( - undefined, - InitFragment.STAGE_ASYNC_DEPENDENCIES, - 0, - "await-dependencies" - ); - this.promises = promises; - } +exports.createScriptUrl = "__webpack_require__.tu"; - merge(other) { - const promises = new Set(this.promises); - for (const p of other.promises) { - promises.add(p); - } - return new AwaitDependenciesInitFragment(promises); - } +/** + * the chunk name of the chunk with the runtime + */ +exports.chunkName = "__webpack_require__.cn"; - /** - * @param {Context} context context - * @returns {string|Source} the source code that will be included as initialization code - */ - getContent({ runtimeRequirements }) { - runtimeRequirements.add(RuntimeGlobals.module); - const promises = this.promises; - if (promises.size === 0) { - return ""; - } - if (promises.size === 1) { - for (const p of promises) { - return Template.asString([ - `var __webpack_async_dependencies__ = __webpack_handle_async_dependencies__([${p}]);`, - `${p} = (__webpack_async_dependencies__.then ? await __webpack_async_dependencies__ : __webpack_async_dependencies__)[0];`, - "" - ]); - } - } - const sepPromises = Array.from(promises).join(", "); - // TODO check if destructuring is supported - return Template.asString([ - `var __webpack_async_dependencies__ = __webpack_handle_async_dependencies__([${sepPromises}]);`, - `([${sepPromises}] = __webpack_async_dependencies__.then ? await __webpack_async_dependencies__ : __webpack_async_dependencies__);`, - "" - ]); - } -} +/** + * the runtime id of the current runtime + */ +exports.runtimeId = "__webpack_require__.j"; -module.exports = AwaitDependenciesInitFragment; +/** + * the filename of the script part of the chunk + */ +exports.getChunkScriptFilename = "__webpack_require__.u"; +/** + * the filename of the script part of the hot update chunk + */ +exports.getChunkUpdateScriptFilename = "__webpack_require__.hu"; -/***/ }), +/** + * startup signal from runtime + * This will be called when the runtime chunk has been loaded. + */ +exports.startup = "__webpack_require__.x"; -/***/ 79471: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { +/** + * @deprecated + * creating a default startup function with the entry modules + */ +exports.startupNoDefault = "__webpack_require__.x (no default handler)"; -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ +/** + * startup signal from runtime but only used to add logic after the startup + */ +exports.startupOnlyAfter = "__webpack_require__.x (only after)"; +/** + * startup signal from runtime but only used to add sync logic before the startup + */ +exports.startupOnlyBefore = "__webpack_require__.x (only before)"; +/** + * global callback functions for installing chunks + */ +exports.chunkCallback = "webpackChunk"; -const HarmonyImportDependency = __webpack_require__(19577); +/** + * method to startup an entrypoint with needed chunks. + * Signature: (moduleId: Id, chunkIds: Id[]) => any. + * Returns the exports of the module or a Promise + */ +exports.startupEntrypoint = "__webpack_require__.X"; -/** @typedef {import("../Compiler")} Compiler */ -/** @typedef {import("../Module")} Module */ +/** + * register deferred code, which will run when certain + * chunks are loaded. + * Signature: (chunkIds: Id[], fn: () => any, priority: int >= 0 = 0) => any + * Returned value will be returned directly when all chunks are already loaded + * When (priority & 1) it will wait for all other handlers with lower priority to + * be executed before itself is executed + */ +exports.onChunksLoaded = "__webpack_require__.O"; -class InferAsyncModulesPlugin { - /** - * Apply the plugin - * @param {Compiler} compiler the compiler instance - * @returns {void} - */ - apply(compiler) { - compiler.hooks.compilation.tap("InferAsyncModulesPlugin", compilation => { - const { moduleGraph } = compilation; - compilation.hooks.finishModules.tap( - "InferAsyncModulesPlugin", - modules => { - /** @type {Set} */ - const queue = new Set(); - for (const module of modules) { - if (module.buildMeta && module.buildMeta.async) { - queue.add(module); - } - } - for (const module of queue) { - moduleGraph.setAsync(module); - for (const [ - originModule, - connections - ] of moduleGraph.getIncomingConnectionsByOriginModule(module)) { - if ( - connections.some( - c => - c.dependency instanceof HarmonyImportDependency && - c.isTargetActive(undefined) - ) - ) { - queue.add(originModule); - } - } - } - } - ); - }); - } -} +/** + * method to install a chunk that was loaded somehow + * Signature: ({ id, ids, modules, runtime }) => void + */ +exports.externalInstallChunk = "__webpack_require__.C"; -module.exports = InferAsyncModulesPlugin; +/** + * interceptor for module executions + */ +exports.interceptModuleExecution = "__webpack_require__.i"; + +/** + * the global object + */ +exports.global = "__webpack_require__.g"; +/** + * an object with all share scopes + */ +exports.shareScopeMap = "__webpack_require__.S"; -/***/ }), +/** + * The sharing init sequence function (only runs once per share scope). + * Has one argument, the name of the share scope. + * Creates a share scope if not existing + */ +exports.initializeSharing = "__webpack_require__.I"; -/***/ 21743: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { +/** + * The current scope when getting a module from a remote + */ +exports.currentRemoteGetScope = "__webpack_require__.R"; -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ +/** + * the filename of the HMR manifest + */ +exports.getUpdateManifestFilename = "__webpack_require__.hmrF"; +/** + * function downloading the update manifest + */ +exports.hmrDownloadManifest = "__webpack_require__.hmrM"; +/** + * array with handler functions to download chunk updates + */ +exports.hmrDownloadUpdateHandlers = "__webpack_require__.hmrC"; -const AsyncDependencyToInitialChunkError = __webpack_require__(69073); -const { connectChunkGroupParentAndChild } = __webpack_require__(76652); -const ModuleGraphConnection = __webpack_require__(94144); -const { getEntryRuntime, mergeRuntime } = __webpack_require__(19655); +/** + * object with all hmr module data for all modules + */ +exports.hmrModuleData = "__webpack_require__.hmrD"; -/** @typedef {import("./AsyncDependenciesBlock")} AsyncDependenciesBlock */ -/** @typedef {import("./Chunk")} Chunk */ -/** @typedef {import("./ChunkGroup")} ChunkGroup */ -/** @typedef {import("./Compilation")} Compilation */ -/** @typedef {import("./DependenciesBlock")} DependenciesBlock */ -/** @typedef {import("./Dependency")} Dependency */ -/** @typedef {import("./Entrypoint")} Entrypoint */ -/** @typedef {import("./Module")} Module */ -/** @typedef {import("./ModuleGraph")} ModuleGraph */ -/** @typedef {import("./ModuleGraphConnection").ConnectionState} ConnectionState */ -/** @typedef {import("./logging/Logger").Logger} Logger */ -/** @typedef {import("./util/runtime").RuntimeSpec} RuntimeSpec */ +/** + * array with handler functions when a module should be invalidated + */ +exports.hmrInvalidateModuleHandlers = "__webpack_require__.hmrI"; /** - * @typedef {Object} QueueItem - * @property {number} action - * @property {DependenciesBlock} block - * @property {Module} module - * @property {Chunk} chunk - * @property {ChunkGroup} chunkGroup - * @property {ChunkGroupInfo} chunkGroupInfo + * the prefix for storing state of runtime modules when hmr is enabled */ +exports.hmrRuntimeStatePrefix = "__webpack_require__.hmrS"; -/** @typedef {Set & { plus: Set }} ModuleSetPlus */ +/** + * the AMD define function + */ +exports.amdDefine = "__webpack_require__.amdD"; /** - * @typedef {Object} ChunkGroupInfo - * @property {ChunkGroup} chunkGroup the chunk group - * @property {RuntimeSpec} runtime the runtimes - * @property {ModuleSetPlus} minAvailableModules current minimal set of modules available at this point - * @property {boolean} minAvailableModulesOwned true, if minAvailableModules is owned and can be modified - * @property {ModuleSetPlus[]} availableModulesToBeMerged enqueued updates to the minimal set of available modules - * @property {Set=} skippedItems modules that were skipped because module is already available in parent chunks (need to reconsider when minAvailableModules is shrinking) - * @property {Set<[Module, ConnectionState]>=} skippedModuleConnections referenced modules that where skipped because they were not active in this runtime - * @property {ModuleSetPlus} resultingAvailableModules set of modules available including modules from this chunk group - * @property {Set} children set of children chunk groups, that will be revisited when availableModules shrink - * @property {Set} availableSources set of chunk groups that are the source for minAvailableModules - * @property {Set} availableChildren set of chunk groups which depend on the this chunk group as availableSource - * @property {number} preOrderIndex next pre order index - * @property {number} postOrderIndex next post order index - * @property {boolean} chunkLoading has a chunk loading mechanism - * @property {boolean} asyncChunks create async chunks + * the AMD options */ +exports.amdOptions = "__webpack_require__.amdO"; /** - * @typedef {Object} BlockChunkGroupConnection - * @property {ChunkGroupInfo} originChunkGroupInfo origin chunk group - * @property {ChunkGroup} chunkGroup referenced chunk group + * the System polyfill object */ +exports.system = "__webpack_require__.System"; -const EMPTY_SET = /** @type {ModuleSetPlus} */ (new Set()); -EMPTY_SET.plus = EMPTY_SET; +/** + * the shorthand for Object.prototype.hasOwnProperty + * using of it decreases the compiled bundle size + */ +exports.hasOwnProperty = "__webpack_require__.o"; /** - * @param {ModuleSetPlus} a first set - * @param {ModuleSetPlus} b second set - * @returns {number} cmp + * the System.register context object */ -const bySetSize = (a, b) => { - return b.size + b.plus.size - a.size - a.plus.size; -}; +exports.systemContext = "__webpack_require__.y"; -const extractBlockModules = (module, moduleGraph, runtime, blockModulesMap) => { - let blockCache; - let modules; +/** + * the baseURI of current document + */ +exports.baseURI = "__webpack_require__.b"; - const arrays = []; +/** + * a RelativeURL class when relative URLs are used + */ +exports.relativeUrl = "__webpack_require__.U"; - const queue = [module]; - while (queue.length > 0) { - const block = queue.pop(); - const arr = []; - arrays.push(arr); - blockModulesMap.set(block, arr); - for (const b of block.blocks) { - queue.push(b); - } - } +/** + * Creates an async module. The body function must be a async function. + * "module.exports" will be decorated with an AsyncModulePromise. + * The body function will be called. + * To handle async dependencies correctly do this: "([a, b, c] = await handleDependencies([a, b, c]));". + * If "hasAwaitAfterDependencies" is truthy, "handleDependencies()" must be called at the end of the body function. + * Signature: function( + * module: Module, + * body: (handleDependencies: (deps: AsyncModulePromise[]) => Promise & () => void, + * hasAwaitAfterDependencies?: boolean + * ) => void + */ +exports.asyncModule = "__webpack_require__.a"; - for (const connection of moduleGraph.getOutgoingConnections(module)) { - const d = connection.dependency; - // We skip connections without dependency - if (!d) continue; - const m = connection.module; - // We skip connections without Module pointer - if (!m) continue; - // We skip weak connections - if (connection.weak) continue; - const state = connection.getActiveState(runtime); - // We skip inactive connections - if (state === false) continue; - const block = moduleGraph.getParentBlock(d); - let index = moduleGraph.getParentBlockIndex(d); +/***/ }), - // deprecated fallback - if (index < 0) { - index = block.dependencies.indexOf(d); - } +/***/ 61439: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - if (blockCache !== block) { - modules = blockModulesMap.get((blockCache = block)); - } +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ - const i = index << 2; - modules[i] = m; - modules[i + 1] = state; - } - for (const modules of arrays) { - if (modules.length === 0) continue; - let indexMap; - let length = 0; - outer: for (let j = 0; j < modules.length; j += 2) { - const m = modules[j]; - if (m === undefined) continue; - const state = modules[j + 1]; - if (indexMap === undefined) { - let i = 0; - for (; i < length; i += 2) { - if (modules[i] === m) { - const merged = modules[i + 1]; - if (merged === true) continue outer; - modules[i + 1] = ModuleGraphConnection.addConnectionStates( - merged, - state - ); - } - } - modules[length] = m; - length++; - modules[length] = state; - length++; - if (length > 30) { - // To avoid worse case performance, we will use an index map for - // linear cost access, which allows to maintain O(n) complexity - // while keeping allocations down to a minimum - indexMap = new Map(); - for (let i = 0; i < length; i += 2) { - indexMap.set(modules[i], i + 1); - } - } - } else { - const idx = indexMap.get(m); - if (idx !== undefined) { - const merged = modules[idx]; - if (merged === true) continue outer; - modules[idx] = ModuleGraphConnection.addConnectionStates( - merged, - state - ); - } else { - modules[length] = m; - length++; - modules[length] = state; - indexMap.set(m, length); - length++; - } - } - } - modules.length = length; - } -}; -/** - * - * @param {Logger} logger a logger - * @param {Compilation} compilation the compilation - * @param {Map} inputEntrypointsAndModules chunk groups which are processed with the modules - * @param {Map} chunkGroupInfoMap mapping from chunk group to available modules - * @param {Map} blockConnections connection for blocks - * @param {Set} blocksWithNestedBlocks flag for blocks that have nested blocks - * @param {Set} allCreatedChunkGroups filled with all chunk groups that are created here - */ -const visitModules = ( - logger, - compilation, - inputEntrypointsAndModules, - chunkGroupInfoMap, - blockConnections, - blocksWithNestedBlocks, - allCreatedChunkGroups -) => { - const { moduleGraph, chunkGraph, moduleMemCaches } = compilation; +const { RawSource } = __webpack_require__(96192); +const OriginalSource = __webpack_require__(96192).OriginalSource; +const Module = __webpack_require__(85887); - const blockModulesRuntimeMap = new Map(); +/** @typedef {import("webpack-sources").Source} Source */ +/** @typedef {import("../declarations/WebpackOptions").WebpackOptionsNormalized} WebpackOptions */ +/** @typedef {import("./Chunk")} Chunk */ +/** @typedef {import("./ChunkGraph")} ChunkGraph */ +/** @typedef {import("./Compilation")} Compilation */ +/** @typedef {import("./Dependency").UpdateHashContext} UpdateHashContext */ +/** @typedef {import("./Module").CodeGenerationContext} CodeGenerationContext */ +/** @typedef {import("./Module").CodeGenerationResult} CodeGenerationResult */ +/** @typedef {import("./Module").NeedBuildContext} NeedBuildContext */ +/** @typedef {import("./RequestShortener")} RequestShortener */ +/** @typedef {import("./ResolverFactory").ResolverWithOptions} ResolverWithOptions */ +/** @typedef {import("./WebpackError")} WebpackError */ +/** @typedef {import("./util/Hash")} Hash */ +/** @typedef {import("./util/fs").InputFileSystem} InputFileSystem */ - /** @type {RuntimeSpec | false} */ - let blockModulesMapRuntime = false; - let blockModulesMap; +const TYPES = new Set(["runtime"]); +class RuntimeModule extends Module { /** - * - * @param {DependenciesBlock} block block - * @param {RuntimeSpec} runtime runtime - * @returns {(Module | ConnectionState)[]} block modules in flatten tuples + * @param {string} name a readable name + * @param {number=} stage an optional stage */ - const getBlockModules = (block, runtime) => { - if (blockModulesMapRuntime !== runtime) { - blockModulesMap = blockModulesRuntimeMap.get(runtime); - if (blockModulesMap === undefined) { - blockModulesMap = new Map(); - blockModulesRuntimeMap.set(runtime, blockModulesMap); - } - } - let blockModules = blockModulesMap.get(block); - if (blockModules !== undefined) return blockModules; - const module = /** @type {Module} */ (block.getRootBlock()); - const memCache = moduleMemCaches && moduleMemCaches.get(module); - if (memCache !== undefined) { - const map = memCache.provide( - "bundleChunkGraph.blockModules", - runtime, - () => { - logger.time("visitModules: prepare"); - const map = new Map(); - extractBlockModules(module, moduleGraph, runtime, map); - logger.timeAggregate("visitModules: prepare"); - return map; - } - ); - for (const [block, blockModules] of map) - blockModulesMap.set(block, blockModules); - return map.get(block); - } else { - logger.time("visitModules: prepare"); - extractBlockModules(module, moduleGraph, runtime, blockModulesMap); - blockModules = blockModulesMap.get(block); - logger.timeAggregate("visitModules: prepare"); - return blockModules; - } - }; - - let statProcessedQueueItems = 0; - let statProcessedBlocks = 0; - let statConnectedChunkGroups = 0; - let statProcessedChunkGroupsForMerging = 0; - let statMergedAvailableModuleSets = 0; - let statForkedAvailableModules = 0; - let statForkedAvailableModulesCount = 0; - let statForkedAvailableModulesCountPlus = 0; - let statForkedMergedModulesCount = 0; - let statForkedMergedModulesCountPlus = 0; - let statForkedResultModulesCount = 0; - let statChunkGroupInfoUpdated = 0; - let statChildChunkGroupsReconnected = 0; + constructor(name, stage = 0) { + super("runtime"); + this.name = name; + this.stage = stage; + this.buildMeta = {}; + this.buildInfo = {}; + /** @type {Compilation} */ + this.compilation = undefined; + /** @type {Chunk} */ + this.chunk = undefined; + /** @type {ChunkGraph} */ + this.chunkGraph = undefined; + this.fullHash = false; + this.dependentHash = false; + /** @type {string} */ + this._cachedGeneratedCode = undefined; + } - let nextChunkGroupIndex = 0; - let nextFreeModulePreOrderIndex = 0; - let nextFreeModulePostOrderIndex = 0; + /** + * @param {Compilation} compilation the compilation + * @param {Chunk} chunk the chunk + * @param {ChunkGraph} chunkGraph the chunk graph + * @returns {void} + */ + attach(compilation, chunk, chunkGraph = compilation.chunkGraph) { + this.compilation = compilation; + this.chunk = chunk; + this.chunkGraph = chunkGraph; + } - /** @type {Map} */ - const blockChunkGroups = new Map(); + /** + * @returns {string} a unique identifier of the module + */ + identifier() { + return `webpack/runtime/${this.name}`; + } - /** @type {Map} */ - const namedChunkGroups = new Map(); + /** + * @param {RequestShortener} requestShortener the request shortener + * @returns {string} a user readable identifier of the module + */ + readableIdentifier(requestShortener) { + return `webpack/runtime/${this.name}`; + } - /** @type {Map} */ - const namedAsyncEntrypoints = new Map(); + /** + * @param {NeedBuildContext} context context info + * @param {function(WebpackError=, boolean=): void} callback callback function, returns true, if the module needs a rebuild + * @returns {void} + */ + needBuild(context, callback) { + return callback(null, false); + } - const ADD_AND_ENTER_ENTRY_MODULE = 0; - const ADD_AND_ENTER_MODULE = 1; - const ENTER_MODULE = 2; - const PROCESS_BLOCK = 3; - const PROCESS_ENTRY_BLOCK = 4; - const LEAVE_MODULE = 5; + /** + * @param {WebpackOptions} options webpack options + * @param {Compilation} compilation the compilation + * @param {ResolverWithOptions} resolver the resolver + * @param {InputFileSystem} fs the file system + * @param {function(WebpackError=): void} callback callback function + * @returns {void} + */ + build(options, compilation, resolver, fs, callback) { + // do nothing + // should not be called as runtime modules are added later to the compilation + callback(); + } - /** @type {QueueItem[]} */ - let queue = []; + /** + * @param {Hash} hash the hash used to track dependencies + * @param {UpdateHashContext} context context + * @returns {void} + */ + updateHash(hash, context) { + hash.update(this.name); + hash.update(`${this.stage}`); + try { + if (this.fullHash || this.dependentHash) { + // Do not use getGeneratedCode here, because i. e. compilation hash might be not + // ready at this point. We will cache it later instead. + hash.update(this.generate()); + } else { + hash.update(this.getGeneratedCode()); + } + } catch (err) { + hash.update(err.message); + } + super.updateHash(hash, context); + } - /** @type {Map>} */ - const queueConnect = new Map(); - /** @type {Set} */ - const chunkGroupsForCombining = new Set(); + /** + * @returns {Set} types available (do not mutate) + */ + getSourceTypes() { + return TYPES; + } - // Fill queue with entrypoint modules - // Create ChunkGroupInfo for entrypoints - for (const [chunkGroup, modules] of inputEntrypointsAndModules) { - const runtime = getEntryRuntime( - compilation, - chunkGroup.name, - chunkGroup.options - ); - /** @type {ChunkGroupInfo} */ - const chunkGroupInfo = { - chunkGroup, - runtime, - minAvailableModules: undefined, - minAvailableModulesOwned: false, - availableModulesToBeMerged: [], - skippedItems: undefined, - resultingAvailableModules: undefined, - children: undefined, - availableSources: undefined, - availableChildren: undefined, - preOrderIndex: 0, - postOrderIndex: 0, - chunkLoading: - chunkGroup.options.chunkLoading !== undefined - ? chunkGroup.options.chunkLoading !== false - : compilation.outputOptions.chunkLoading !== false, - asyncChunks: - chunkGroup.options.asyncChunks !== undefined - ? chunkGroup.options.asyncChunks - : compilation.outputOptions.asyncChunks !== false - }; - chunkGroup.index = nextChunkGroupIndex++; - if (chunkGroup.getNumberOfParents() > 0) { - // minAvailableModules for child entrypoints are unknown yet, set to undefined. - // This means no module is added until other sets are merged into - // this minAvailableModules (by the parent entrypoints) - const skippedItems = new Set(); - for (const module of modules) { - skippedItems.add(module); - } - chunkGroupInfo.skippedItems = skippedItems; - chunkGroupsForCombining.add(chunkGroupInfo); - } else { - // The application may start here: We start with an empty list of available modules - chunkGroupInfo.minAvailableModules = EMPTY_SET; - const chunk = chunkGroup.getEntrypointChunk(); - for (const module of modules) { - queue.push({ - action: ADD_AND_ENTER_MODULE, - block: module, - module, - chunk, - chunkGroup, - chunkGroupInfo - }); - } + /** + * @param {CodeGenerationContext} context context for code generation + * @returns {CodeGenerationResult} result + */ + codeGeneration(context) { + const sources = new Map(); + const generatedCode = this.getGeneratedCode(); + if (generatedCode) { + sources.set( + "runtime", + this.useSourceMap || this.useSimpleSourceMap + ? new OriginalSource(generatedCode, this.identifier()) + : new RawSource(generatedCode) + ); } - chunkGroupInfoMap.set(chunkGroup, chunkGroupInfo); - if (chunkGroup.name) { - namedChunkGroups.set(chunkGroup.name, chunkGroupInfo); + return { + sources, + runtimeRequirements: null + }; + } + + /** + * @param {string=} type the source type for which the size should be estimated + * @returns {number} the estimated size of the module (must be non-zero) + */ + size(type) { + try { + const source = this.getGeneratedCode(); + return source ? source.length : 0; + } catch (e) { + return 0; } } - // Fill availableSources with parent-child dependencies between entrypoints - for (const chunkGroupInfo of chunkGroupsForCombining) { - const { chunkGroup } = chunkGroupInfo; - chunkGroupInfo.availableSources = new Set(); - for (const parent of chunkGroup.parentsIterable) { - const parentChunkGroupInfo = chunkGroupInfoMap.get(parent); - chunkGroupInfo.availableSources.add(parentChunkGroupInfo); - if (parentChunkGroupInfo.availableChildren === undefined) { - parentChunkGroupInfo.availableChildren = new Set(); - } - parentChunkGroupInfo.availableChildren.add(chunkGroupInfo); + + /* istanbul ignore next */ + /** + * @abstract + * @returns {string} runtime code + */ + generate() { + const AbstractMethodError = __webpack_require__(570); + throw new AbstractMethodError(); + } + + /** + * @returns {string} runtime code + */ + getGeneratedCode() { + if (this._cachedGeneratedCode) { + return this._cachedGeneratedCode; } + return (this._cachedGeneratedCode = this.generate()); } - // pop() is used to read from the queue - // so it need to be reversed to be iterated in - // correct order - queue.reverse(); - /** @type {Set} */ - const outdatedChunkGroupInfo = new Set(); - /** @type {Set} */ - const chunkGroupsForMerging = new Set(); - /** @type {QueueItem[]} */ - let queueDelayed = []; + /** + * @returns {boolean} true, if the runtime module should get it's own scope + */ + shouldIsolate() { + return true; + } +} - /** @type {[Module, ConnectionState][]} */ - const skipConnectionBuffer = []; - /** @type {Module[]} */ - const skipBuffer = []; - /** @type {QueueItem[]} */ - const queueBuffer = []; +/** + * Runtime modules without any dependencies to other runtime modules + */ +RuntimeModule.STAGE_NORMAL = 0; - /** @type {Module} */ - let module; - /** @type {Chunk} */ - let chunk; - /** @type {ChunkGroup} */ - let chunkGroup; - /** @type {DependenciesBlock} */ - let block; - /** @type {ChunkGroupInfo} */ - let chunkGroupInfo; +/** + * Runtime modules with simple dependencies on other runtime modules + */ +RuntimeModule.STAGE_BASIC = 5; - // For each async Block in graph +/** + * Runtime modules which attach to handlers of other runtime modules + */ +RuntimeModule.STAGE_ATTACH = 10; + +/** + * Runtime modules which trigger actions on bootstrap + */ +RuntimeModule.STAGE_TRIGGER = 20; + +module.exports = RuntimeModule; + + +/***/ }), + +/***/ 86809: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ + + + +const RuntimeGlobals = __webpack_require__(49404); +const RuntimeRequirementsDependency = __webpack_require__(75941); +const JavascriptModulesPlugin = __webpack_require__(76767); +const AsyncModuleRuntimeModule = __webpack_require__(31372); +const AutoPublicPathRuntimeModule = __webpack_require__(86150); +const CompatGetDefaultExportRuntimeModule = __webpack_require__(24013); +const CompatRuntimeModule = __webpack_require__(65788); +const CreateFakeNamespaceObjectRuntimeModule = __webpack_require__(58470); +const CreateScriptUrlRuntimeModule = __webpack_require__(41690); +const DefinePropertyGettersRuntimeModule = __webpack_require__(24905); +const EnsureChunkRuntimeModule = __webpack_require__(92857); +const GetChunkFilenameRuntimeModule = __webpack_require__(53288); +const GetMainFilenameRuntimeModule = __webpack_require__(10034); +const GlobalRuntimeModule = __webpack_require__(89651); +const HasOwnPropertyRuntimeModule = __webpack_require__(39399); +const LoadScriptRuntimeModule = __webpack_require__(80647); +const MakeNamespaceObjectRuntimeModule = __webpack_require__(62962); +const OnChunksLoadedRuntimeModule = __webpack_require__(92794); +const PublicPathRuntimeModule = __webpack_require__(10569); +const RelativeUrlRuntimeModule = __webpack_require__(68642); +const RuntimeIdRuntimeModule = __webpack_require__(90984); +const SystemContextRuntimeModule = __webpack_require__(33248); +const ShareRuntimeModule = __webpack_require__(97207); +const StringXor = __webpack_require__(23877); + +/** @typedef {import("./Chunk")} Chunk */ +/** @typedef {import("./Compiler")} Compiler */ +/** @typedef {import("./Module")} Module */ + +const GLOBALS_ON_REQUIRE = [ + RuntimeGlobals.chunkName, + RuntimeGlobals.runtimeId, + RuntimeGlobals.compatGetDefaultExport, + RuntimeGlobals.createFakeNamespaceObject, + RuntimeGlobals.createScriptUrl, + RuntimeGlobals.definePropertyGetters, + RuntimeGlobals.ensureChunk, + RuntimeGlobals.entryModuleId, + RuntimeGlobals.getFullHash, + RuntimeGlobals.global, + RuntimeGlobals.makeNamespaceObject, + RuntimeGlobals.moduleCache, + RuntimeGlobals.moduleFactories, + RuntimeGlobals.moduleFactoriesAddOnly, + RuntimeGlobals.interceptModuleExecution, + RuntimeGlobals.publicPath, + RuntimeGlobals.baseURI, + RuntimeGlobals.relativeUrl, + RuntimeGlobals.scriptNonce, + RuntimeGlobals.uncaughtErrorHandler, + RuntimeGlobals.asyncModule, + RuntimeGlobals.wasmInstances, + RuntimeGlobals.instantiateWasm, + RuntimeGlobals.shareScopeMap, + RuntimeGlobals.initializeSharing, + RuntimeGlobals.loadScript, + RuntimeGlobals.systemContext, + RuntimeGlobals.onChunksLoaded +]; + +const MODULE_DEPENDENCIES = { + [RuntimeGlobals.moduleLoaded]: [RuntimeGlobals.module], + [RuntimeGlobals.moduleId]: [RuntimeGlobals.module] +}; + +const TREE_DEPENDENCIES = { + [RuntimeGlobals.definePropertyGetters]: [RuntimeGlobals.hasOwnProperty], + [RuntimeGlobals.compatGetDefaultExport]: [ + RuntimeGlobals.definePropertyGetters + ], + [RuntimeGlobals.createFakeNamespaceObject]: [ + RuntimeGlobals.definePropertyGetters, + RuntimeGlobals.makeNamespaceObject, + RuntimeGlobals.require + ], + [RuntimeGlobals.initializeSharing]: [RuntimeGlobals.shareScopeMap], + [RuntimeGlobals.shareScopeMap]: [RuntimeGlobals.hasOwnProperty] +}; + +class RuntimePlugin { /** - * @param {AsyncDependenciesBlock} b iterating over each Async DepBlock + * @param {Compiler} compiler the Compiler * @returns {void} */ - const iteratorBlock = b => { - // 1. We create a chunk group with single chunk in it for this Block - // but only once (blockChunkGroups map) - let cgi = blockChunkGroups.get(b); - /** @type {ChunkGroup} */ - let c; - /** @type {Entrypoint} */ - let entrypoint; - const entryOptions = b.groupOptions && b.groupOptions.entryOptions; - if (cgi === undefined) { - const chunkName = (b.groupOptions && b.groupOptions.name) || b.chunkName; - if (entryOptions) { - cgi = namedAsyncEntrypoints.get(chunkName); - if (!cgi) { - entrypoint = compilation.addAsyncEntrypoint( - entryOptions, - module, - b.loc, - b.request + apply(compiler) { + compiler.hooks.compilation.tap("RuntimePlugin", compilation => { + compilation.dependencyTemplates.set( + RuntimeRequirementsDependency, + new RuntimeRequirementsDependency.Template() + ); + for (const req of GLOBALS_ON_REQUIRE) { + compilation.hooks.runtimeRequirementInModule + .for(req) + .tap("RuntimePlugin", (module, set) => { + set.add(RuntimeGlobals.requireScope); + }); + compilation.hooks.runtimeRequirementInTree + .for(req) + .tap("RuntimePlugin", (module, set) => { + set.add(RuntimeGlobals.requireScope); + }); + } + for (const req of Object.keys(TREE_DEPENDENCIES)) { + const deps = TREE_DEPENDENCIES[req]; + compilation.hooks.runtimeRequirementInTree + .for(req) + .tap("RuntimePlugin", (chunk, set) => { + for (const dep of deps) set.add(dep); + }); + } + for (const req of Object.keys(MODULE_DEPENDENCIES)) { + const deps = MODULE_DEPENDENCIES[req]; + compilation.hooks.runtimeRequirementInModule + .for(req) + .tap("RuntimePlugin", (chunk, set) => { + for (const dep of deps) set.add(dep); + }); + } + compilation.hooks.runtimeRequirementInTree + .for(RuntimeGlobals.definePropertyGetters) + .tap("RuntimePlugin", chunk => { + compilation.addRuntimeModule( + chunk, + new DefinePropertyGettersRuntimeModule() ); - entrypoint.index = nextChunkGroupIndex++; - cgi = { - chunkGroup: entrypoint, - runtime: entrypoint.options.runtime || entrypoint.name, - minAvailableModules: EMPTY_SET, - minAvailableModulesOwned: false, - availableModulesToBeMerged: [], - skippedItems: undefined, - resultingAvailableModules: undefined, - children: undefined, - availableSources: undefined, - availableChildren: undefined, - preOrderIndex: 0, - postOrderIndex: 0, - chunkLoading: - entryOptions.chunkLoading !== undefined - ? entryOptions.chunkLoading !== false - : chunkGroupInfo.chunkLoading, - asyncChunks: - entryOptions.asyncChunks !== undefined - ? entryOptions.asyncChunks - : chunkGroupInfo.asyncChunks - }; - chunkGroupInfoMap.set(entrypoint, cgi); + return true; + }); + compilation.hooks.runtimeRequirementInTree + .for(RuntimeGlobals.makeNamespaceObject) + .tap("RuntimePlugin", chunk => { + compilation.addRuntimeModule( + chunk, + new MakeNamespaceObjectRuntimeModule() + ); + return true; + }); + compilation.hooks.runtimeRequirementInTree + .for(RuntimeGlobals.createFakeNamespaceObject) + .tap("RuntimePlugin", chunk => { + compilation.addRuntimeModule( + chunk, + new CreateFakeNamespaceObjectRuntimeModule() + ); + return true; + }); + compilation.hooks.runtimeRequirementInTree + .for(RuntimeGlobals.hasOwnProperty) + .tap("RuntimePlugin", chunk => { + compilation.addRuntimeModule( + chunk, + new HasOwnPropertyRuntimeModule() + ); + return true; + }); + compilation.hooks.runtimeRequirementInTree + .for(RuntimeGlobals.compatGetDefaultExport) + .tap("RuntimePlugin", chunk => { + compilation.addRuntimeModule( + chunk, + new CompatGetDefaultExportRuntimeModule() + ); + return true; + }); + compilation.hooks.runtimeRequirementInTree + .for(RuntimeGlobals.runtimeId) + .tap("RuntimePlugin", chunk => { + compilation.addRuntimeModule(chunk, new RuntimeIdRuntimeModule()); + return true; + }); + compilation.hooks.runtimeRequirementInTree + .for(RuntimeGlobals.publicPath) + .tap("RuntimePlugin", (chunk, set) => { + const { outputOptions } = compilation; + const { publicPath: globalPublicPath, scriptType } = outputOptions; + const entryOptions = chunk.getEntryOptions(); + const publicPath = + entryOptions && entryOptions.publicPath !== undefined + ? entryOptions.publicPath + : globalPublicPath; - chunkGraph.connectBlockAndChunkGroup(b, entrypoint); - if (chunkName) { - namedAsyncEntrypoints.set(chunkName, cgi); + if (publicPath === "auto") { + const module = new AutoPublicPathRuntimeModule(); + if (scriptType !== "module") set.add(RuntimeGlobals.global); + compilation.addRuntimeModule(chunk, module); + } else { + const module = new PublicPathRuntimeModule(publicPath); + + if ( + typeof publicPath !== "string" || + /\[(full)?hash\]/.test(publicPath) + ) { + module.fullHash = true; + } + + compilation.addRuntimeModule(chunk, module); } - } else { - entrypoint = /** @type {Entrypoint} */ (cgi.chunkGroup); - // TODO merge entryOptions - entrypoint.addOrigin(module, b.loc, b.request); - chunkGraph.connectBlockAndChunkGroup(b, entrypoint); - } + return true; + }); + compilation.hooks.runtimeRequirementInTree + .for(RuntimeGlobals.global) + .tap("RuntimePlugin", chunk => { + compilation.addRuntimeModule(chunk, new GlobalRuntimeModule()); + return true; + }); + compilation.hooks.runtimeRequirementInTree + .for(RuntimeGlobals.asyncModule) + .tap("RuntimePlugin", chunk => { + compilation.addRuntimeModule(chunk, new AsyncModuleRuntimeModule()); + return true; + }); + compilation.hooks.runtimeRequirementInTree + .for(RuntimeGlobals.systemContext) + .tap("RuntimePlugin", chunk => { + const { outputOptions } = compilation; + const { library: globalLibrary } = outputOptions; + const entryOptions = chunk.getEntryOptions(); + const libraryType = + entryOptions && entryOptions.library !== undefined + ? entryOptions.library.type + : globalLibrary.type; - // 2. We enqueue the DependenciesBlock for traversal - queueDelayed.push({ - action: PROCESS_ENTRY_BLOCK, - block: b, - module: module, - chunk: entrypoint.chunks[0], - chunkGroup: entrypoint, - chunkGroupInfo: cgi + if (libraryType === "system") { + compilation.addRuntimeModule( + chunk, + new SystemContextRuntimeModule() + ); + } + return true; }); - } else if (!chunkGroupInfo.asyncChunks || !chunkGroupInfo.chunkLoading) { - // Just queue the block into the current chunk group - queue.push({ - action: PROCESS_BLOCK, - block: b, - module: module, - chunk, - chunkGroup, - chunkGroupInfo + compilation.hooks.runtimeRequirementInTree + .for(RuntimeGlobals.getChunkScriptFilename) + .tap("RuntimePlugin", (chunk, set) => { + if ( + typeof compilation.outputOptions.chunkFilename === "string" && + /\[(full)?hash(:\d+)?\]/.test( + compilation.outputOptions.chunkFilename + ) + ) { + set.add(RuntimeGlobals.getFullHash); + } + compilation.addRuntimeModule( + chunk, + new GetChunkFilenameRuntimeModule( + "javascript", + "javascript", + RuntimeGlobals.getChunkScriptFilename, + chunk => + chunk.filenameTemplate || + (chunk.canBeInitial() + ? compilation.outputOptions.filename + : compilation.outputOptions.chunkFilename), + false + ) + ); + return true; + }); + compilation.hooks.runtimeRequirementInTree + .for(RuntimeGlobals.getChunkUpdateScriptFilename) + .tap("RuntimePlugin", (chunk, set) => { + if ( + /\[(full)?hash(:\d+)?\]/.test( + compilation.outputOptions.hotUpdateChunkFilename + ) + ) + set.add(RuntimeGlobals.getFullHash); + compilation.addRuntimeModule( + chunk, + new GetChunkFilenameRuntimeModule( + "javascript", + "javascript update", + RuntimeGlobals.getChunkUpdateScriptFilename, + c => compilation.outputOptions.hotUpdateChunkFilename, + true + ) + ); + return true; + }); + compilation.hooks.runtimeRequirementInTree + .for(RuntimeGlobals.getUpdateManifestFilename) + .tap("RuntimePlugin", (chunk, set) => { + if ( + /\[(full)?hash(:\d+)?\]/.test( + compilation.outputOptions.hotUpdateMainFilename + ) + ) { + set.add(RuntimeGlobals.getFullHash); + } + compilation.addRuntimeModule( + chunk, + new GetMainFilenameRuntimeModule( + "update manifest", + RuntimeGlobals.getUpdateManifestFilename, + compilation.outputOptions.hotUpdateMainFilename + ) + ); + return true; + }); + compilation.hooks.runtimeRequirementInTree + .for(RuntimeGlobals.ensureChunk) + .tap("RuntimePlugin", (chunk, set) => { + const hasAsyncChunks = chunk.hasAsyncChunks(); + if (hasAsyncChunks) { + set.add(RuntimeGlobals.ensureChunkHandlers); + } + compilation.addRuntimeModule( + chunk, + new EnsureChunkRuntimeModule(set) + ); + return true; + }); + compilation.hooks.runtimeRequirementInTree + .for(RuntimeGlobals.ensureChunkIncludeEntries) + .tap("RuntimePlugin", (chunk, set) => { + set.add(RuntimeGlobals.ensureChunkHandlers); + }); + compilation.hooks.runtimeRequirementInTree + .for(RuntimeGlobals.shareScopeMap) + .tap("RuntimePlugin", (chunk, set) => { + compilation.addRuntimeModule(chunk, new ShareRuntimeModule()); + return true; + }); + compilation.hooks.runtimeRequirementInTree + .for(RuntimeGlobals.loadScript) + .tap("RuntimePlugin", (chunk, set) => { + const withCreateScriptUrl = !!compilation.outputOptions.trustedTypes; + if (withCreateScriptUrl) { + set.add(RuntimeGlobals.createScriptUrl); + } + compilation.addRuntimeModule( + chunk, + new LoadScriptRuntimeModule(withCreateScriptUrl) + ); + return true; + }); + compilation.hooks.runtimeRequirementInTree + .for(RuntimeGlobals.createScriptUrl) + .tap("RuntimePlugin", (chunk, set) => { + compilation.addRuntimeModule( + chunk, + new CreateScriptUrlRuntimeModule() + ); + return true; }); - } else { - cgi = chunkName && namedChunkGroups.get(chunkName); - if (!cgi) { - c = compilation.addChunkInGroup( - b.groupOptions || b.chunkName, - module, - b.loc, - b.request + compilation.hooks.runtimeRequirementInTree + .for(RuntimeGlobals.relativeUrl) + .tap("RuntimePlugin", (chunk, set) => { + compilation.addRuntimeModule(chunk, new RelativeUrlRuntimeModule()); + return true; + }); + compilation.hooks.runtimeRequirementInTree + .for(RuntimeGlobals.onChunksLoaded) + .tap("RuntimePlugin", (chunk, set) => { + compilation.addRuntimeModule( + chunk, + new OnChunksLoadedRuntimeModule() ); - c.index = nextChunkGroupIndex++; - cgi = { - chunkGroup: c, - runtime: chunkGroupInfo.runtime, - minAvailableModules: undefined, - minAvailableModulesOwned: undefined, - availableModulesToBeMerged: [], - skippedItems: undefined, - resultingAvailableModules: undefined, - children: undefined, - availableSources: undefined, - availableChildren: undefined, - preOrderIndex: 0, - postOrderIndex: 0, - chunkLoading: chunkGroupInfo.chunkLoading, - asyncChunks: chunkGroupInfo.asyncChunks - }; - allCreatedChunkGroups.add(c); - chunkGroupInfoMap.set(c, cgi); - if (chunkName) { - namedChunkGroups.set(chunkName, cgi); + return true; + }); + // TODO webpack 6: remove CompatRuntimeModule + compilation.hooks.additionalTreeRuntimeRequirements.tap( + "RuntimePlugin", + (chunk, set) => { + const { mainTemplate } = compilation; + if ( + mainTemplate.hooks.bootstrap.isUsed() || + mainTemplate.hooks.localVars.isUsed() || + mainTemplate.hooks.requireEnsure.isUsed() || + mainTemplate.hooks.requireExtensions.isUsed() + ) { + compilation.addRuntimeModule(chunk, new CompatRuntimeModule()); } - } else { - c = cgi.chunkGroup; - if (c.isInitial()) { - compilation.errors.push( - new AsyncDependencyToInitialChunkError(chunkName, module, b.loc) - ); - c = chunkGroup; + } + ); + JavascriptModulesPlugin.getCompilationHooks(compilation).chunkHash.tap( + "RuntimePlugin", + (chunk, hash, { chunkGraph }) => { + const xor = new StringXor(); + for (const m of chunkGraph.getChunkRuntimeModulesIterable(chunk)) { + xor.add(chunkGraph.getModuleHash(m, chunk.runtime)); } - c.addOptions(b.groupOptions); - c.addOrigin(module, b.loc, b.request); + xor.updateHash(hash); } - blockConnections.set(b, []); - } - blockChunkGroups.set(b, cgi); - } else if (entryOptions) { - entrypoint = /** @type {Entrypoint} */ (cgi.chunkGroup); - } else { - c = cgi.chunkGroup; - } + ); + }); + } +} +module.exports = RuntimePlugin; - if (c !== undefined) { - // 2. We store the connection for the block - // to connect it later if needed - blockConnections.get(b).push({ - originChunkGroupInfo: chunkGroupInfo, - chunkGroup: c - }); - // 3. We enqueue the chunk group info creation/updating - let connectList = queueConnect.get(chunkGroupInfo); - if (connectList === undefined) { - connectList = new Set(); - queueConnect.set(chunkGroupInfo, connectList); - } - connectList.add(cgi); +/***/ }), - // TODO check if this really need to be done for each traversal - // or if it is enough when it's queued when created - // 4. We enqueue the DependenciesBlock for traversal - queueDelayed.push({ - action: PROCESS_BLOCK, - block: b, - module: module, - chunk: c.chunks[0], - chunkGroup: c, - chunkGroupInfo: cgi - }); - } else if (entrypoint !== undefined) { - chunkGroupInfo.chunkGroup.addAsyncEntrypoint(entrypoint); - } - }; +/***/ 23974: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - /** - * @param {DependenciesBlock} block the block - * @returns {void} - */ - const processBlock = block => { - statProcessedBlocks++; - // get prepared block info - const blockModules = getBlockModules(block, chunkGroupInfo.runtime); +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ - if (blockModules !== undefined) { - const { minAvailableModules } = chunkGroupInfo; - // Buffer items because order need to be reversed to get indices correct - // Traverse all referenced modules - for (let i = 0; i < blockModules.length; i += 2) { - const refModule = /** @type {Module} */ (blockModules[i]); - if (chunkGraph.isModuleInChunk(refModule, chunk)) { - // skip early if already connected - continue; - } - const activeState = /** @type {ConnectionState} */ ( - blockModules[i + 1] - ); - if (activeState !== true) { - skipConnectionBuffer.push([refModule, activeState]); - if (activeState === false) continue; - } - if ( - activeState === true && - (minAvailableModules.has(refModule) || - minAvailableModules.plus.has(refModule)) - ) { - // already in parent chunks, skip it for now - skipBuffer.push(refModule); - continue; - } - // enqueue, then add and enter to be in the correct order - // this is relevant with circular dependencies - queueBuffer.push({ - action: activeState === true ? ADD_AND_ENTER_MODULE : PROCESS_BLOCK, - block: refModule, - module: refModule, - chunk, - chunkGroup, - chunkGroupInfo - }); - } - // Add buffered items in reverse order - if (skipConnectionBuffer.length > 0) { - let { skippedModuleConnections } = chunkGroupInfo; - if (skippedModuleConnections === undefined) { - chunkGroupInfo.skippedModuleConnections = skippedModuleConnections = - new Set(); - } - for (let i = skipConnectionBuffer.length - 1; i >= 0; i--) { - skippedModuleConnections.add(skipConnectionBuffer[i]); - } - skipConnectionBuffer.length = 0; - } - if (skipBuffer.length > 0) { - let { skippedItems } = chunkGroupInfo; - if (skippedItems === undefined) { - chunkGroupInfo.skippedItems = skippedItems = new Set(); - } - for (let i = skipBuffer.length - 1; i >= 0; i--) { - skippedItems.add(skipBuffer[i]); - } - skipBuffer.length = 0; - } - if (queueBuffer.length > 0) { - for (let i = queueBuffer.length - 1; i >= 0; i--) { - queue.push(queueBuffer[i]); - } - queueBuffer.length = 0; - } - } - // Traverse all Blocks - for (const b of block.blocks) { - iteratorBlock(b); - } - if (block.blocks.length > 0 && module !== block) { - blocksWithNestedBlocks.add(block); - } - }; +const InitFragment = __webpack_require__(51739); +const RuntimeGlobals = __webpack_require__(49404); +const Template = __webpack_require__(92066); +const { equals } = __webpack_require__(21537); +const compileBooleanMatcher = __webpack_require__(356); +const propertyAccess = __webpack_require__(86709); +const { forEachRuntime, subtractRuntime } = __webpack_require__(19655); + +/** @typedef {import("../declarations/WebpackOptions").OutputNormalized} OutputOptions */ +/** @typedef {import("./AsyncDependenciesBlock")} AsyncDependenciesBlock */ +/** @typedef {import("./ChunkGraph")} ChunkGraph */ +/** @typedef {import("./Compilation")} Compilation */ +/** @typedef {import("./Dependency")} Dependency */ +/** @typedef {import("./Module")} Module */ +/** @typedef {import("./ModuleGraph")} ModuleGraph */ +/** @typedef {import("./RequestShortener")} RequestShortener */ +/** @typedef {import("./util/runtime").RuntimeSpec} RuntimeSpec */ + +/** + * @param {Module} module the module + * @param {ChunkGraph} chunkGraph the chunk graph + * @returns {string} error message + */ +const noModuleIdErrorMessage = (module, chunkGraph) => { + return `Module ${module.identifier()} has no id assigned. +This should not happen. +It's in these chunks: ${ + Array.from( + chunkGraph.getModuleChunksIterable(module), + c => c.name || c.id || c.debugId + ).join(", ") || "none" + } (If module is in no chunk this indicates a bug in some chunk/module optimization logic) +Module has these incoming connections: ${Array.from( + chunkGraph.moduleGraph.getIncomingConnections(module), + connection => + `\n - ${ + connection.originModule && connection.originModule.identifier() + } ${connection.dependency && connection.dependency.type} ${ + (connection.explanations && + Array.from(connection.explanations).join(", ")) || + "" + }` + ).join("")}`; +}; +class RuntimeTemplate { /** - * @param {DependenciesBlock} block the block - * @returns {void} + * @param {Compilation} compilation the compilation + * @param {OutputOptions} outputOptions the compilation output options + * @param {RequestShortener} requestShortener the request shortener */ - const processEntryBlock = block => { - statProcessedBlocks++; - // get prepared block info - const blockModules = getBlockModules(block, chunkGroupInfo.runtime); + constructor(compilation, outputOptions, requestShortener) { + this.compilation = compilation; + this.outputOptions = outputOptions || {}; + this.requestShortener = requestShortener; + } - if (blockModules !== undefined) { - // Traverse all referenced modules - for (let i = 0; i < blockModules.length; i += 2) { - const refModule = /** @type {Module} */ (blockModules[i]); - const activeState = /** @type {ConnectionState} */ ( - blockModules[i + 1] - ); - // enqueue, then add and enter to be in the correct order - // this is relevant with circular dependencies - queueBuffer.push({ - action: - activeState === true ? ADD_AND_ENTER_ENTRY_MODULE : PROCESS_BLOCK, - block: refModule, - module: refModule, - chunk, - chunkGroup, - chunkGroupInfo - }); - } - // Add buffered items in reverse order - if (queueBuffer.length > 0) { - for (let i = queueBuffer.length - 1; i >= 0; i--) { - queue.push(queueBuffer[i]); - } - queueBuffer.length = 0; - } - } + isIIFE() { + return this.outputOptions.iife; + } - // Traverse all Blocks - for (const b of block.blocks) { - iteratorBlock(b); - } + isModule() { + return this.outputOptions.module; + } - if (block.blocks.length > 0 && module !== block) { - blocksWithNestedBlocks.add(block); - } - }; + supportsConst() { + return this.outputOptions.environment.const; + } - const processQueue = () => { - while (queue.length) { - statProcessedQueueItems++; - const queueItem = queue.pop(); - module = queueItem.module; - block = queueItem.block; - chunk = queueItem.chunk; - chunkGroup = queueItem.chunkGroup; - chunkGroupInfo = queueItem.chunkGroupInfo; + supportsArrowFunction() { + return this.outputOptions.environment.arrowFunction; + } - switch (queueItem.action) { - case ADD_AND_ENTER_ENTRY_MODULE: - chunkGraph.connectChunkAndEntryModule( - chunk, - module, - /** @type {Entrypoint} */ (chunkGroup) - ); - // fallthrough - case ADD_AND_ENTER_MODULE: { - if (chunkGraph.isModuleInChunk(module, chunk)) { - // already connected, skip it - break; - } - // We connect Module and Chunk - chunkGraph.connectChunkAndModule(chunk, module); - } - // fallthrough - case ENTER_MODULE: { - const index = chunkGroup.getModulePreOrderIndex(module); - if (index === undefined) { - chunkGroup.setModulePreOrderIndex( - module, - chunkGroupInfo.preOrderIndex++ - ); - } + supportsForOf() { + return this.outputOptions.environment.forOf; + } - if ( - moduleGraph.setPreOrderIndexIfUnset( - module, - nextFreeModulePreOrderIndex - ) - ) { - nextFreeModulePreOrderIndex++; - } + supportsDestructuring() { + return this.outputOptions.environment.destructuring; + } - // reuse queueItem - queueItem.action = LEAVE_MODULE; - queue.push(queueItem); - } - // fallthrough - case PROCESS_BLOCK: { - processBlock(block); - break; - } - case PROCESS_ENTRY_BLOCK: { - processEntryBlock(block); - break; - } - case LEAVE_MODULE: { - const index = chunkGroup.getModulePostOrderIndex(module); - if (index === undefined) { - chunkGroup.setModulePostOrderIndex( - module, - chunkGroupInfo.postOrderIndex++ - ); - } + supportsBigIntLiteral() { + return this.outputOptions.environment.bigIntLiteral; + } - if ( - moduleGraph.setPostOrderIndexIfUnset( - module, - nextFreeModulePostOrderIndex - ) - ) { - nextFreeModulePostOrderIndex++; - } - break; - } - } + supportsDynamicImport() { + return this.outputOptions.environment.dynamicImport; + } + + supportsEcmaScriptModuleSyntax() { + return this.outputOptions.environment.module; + } + + supportTemplateLiteral() { + // TODO + return false; + } + + returningFunction(returnValue, args = "") { + return this.supportsArrowFunction() + ? `(${args}) => (${returnValue})` + : `function(${args}) { return ${returnValue}; }`; + } + + basicFunction(args, body) { + return this.supportsArrowFunction() + ? `(${args}) => {\n${Template.indent(body)}\n}` + : `function(${args}) {\n${Template.indent(body)}\n}`; + } + + expressionFunction(expression, args = "") { + return this.supportsArrowFunction() + ? `(${args}) => (${expression})` + : `function(${args}) { ${expression}; }`; + } + + emptyFunction() { + return this.supportsArrowFunction() ? "x => {}" : "function() {}"; + } + + destructureArray(items, value) { + return this.supportsDestructuring() + ? `var [${items.join(", ")}] = ${value};` + : Template.asString( + items.map((item, i) => `var ${item} = ${value}[${i}];`) + ); + } + + destructureObject(items, value) { + return this.supportsDestructuring() + ? `var {${items.join(", ")}} = ${value};` + : Template.asString( + items.map(item => `var ${item} = ${value}${propertyAccess([item])};`) + ); + } + + iife(args, body) { + return `(${this.basicFunction(args, body)})()`; + } + + forEach(variable, array, body) { + return this.supportsForOf() + ? `for(const ${variable} of ${array}) {\n${Template.indent(body)}\n}` + : `${array}.forEach(function(${variable}) {\n${Template.indent( + body + )}\n});`; + } + + /** + * Add a comment + * @param {object} options Information content of the comment + * @param {string=} options.request request string used originally + * @param {string=} options.chunkName name of the chunk referenced + * @param {string=} options.chunkReason reason information of the chunk + * @param {string=} options.message additional message + * @param {string=} options.exportName name of the export + * @returns {string} comment + */ + comment({ request, chunkName, chunkReason, message, exportName }) { + let content; + if (this.outputOptions.pathinfo) { + content = [message, request, chunkName, chunkReason] + .filter(Boolean) + .map(item => this.requestShortener.shorten(item)) + .join(" | "); + } else { + content = [message, chunkName, chunkReason] + .filter(Boolean) + .map(item => this.requestShortener.shorten(item)) + .join(" | "); } - }; + if (!content) return ""; + if (this.outputOptions.pathinfo) { + return Template.toComment(content) + " "; + } else { + return Template.toNormalComment(content) + " "; + } + } + + /** + * @param {object} options generation options + * @param {string=} options.request request string used originally + * @returns {string} generated error block + */ + throwMissingModuleErrorBlock({ request }) { + const err = `Cannot find module '${request}'`; + return `var e = new Error(${JSON.stringify( + err + )}); e.code = 'MODULE_NOT_FOUND'; throw e;`; + } + + /** + * @param {object} options generation options + * @param {string=} options.request request string used originally + * @returns {string} generated error function + */ + throwMissingModuleErrorFunction({ request }) { + return `function webpackMissingModule() { ${this.throwMissingModuleErrorBlock( + { request } + )} }`; + } - const calculateResultingAvailableModules = chunkGroupInfo => { - if (chunkGroupInfo.resultingAvailableModules) - return chunkGroupInfo.resultingAvailableModules; + /** + * @param {object} options generation options + * @param {string=} options.request request string used originally + * @returns {string} generated error IIFE + */ + missingModule({ request }) { + return `Object(${this.throwMissingModuleErrorFunction({ request })}())`; + } - const minAvailableModules = chunkGroupInfo.minAvailableModules; + /** + * @param {object} options generation options + * @param {string=} options.request request string used originally + * @returns {string} generated error statement + */ + missingModuleStatement({ request }) { + return `${this.missingModule({ request })};\n`; + } - // Create a new Set of available modules at this point - // We want to be as lazy as possible. There are multiple ways doing this: - // Note that resultingAvailableModules is stored as "(a) + (b)" as it's a ModuleSetPlus - // - resultingAvailableModules = (modules of chunk) + (minAvailableModules + minAvailableModules.plus) - // - resultingAvailableModules = (minAvailableModules + modules of chunk) + (minAvailableModules.plus) - // We choose one depending on the size of minAvailableModules vs minAvailableModules.plus + /** + * @param {object} options generation options + * @param {string=} options.request request string used originally + * @returns {string} generated error code + */ + missingModulePromise({ request }) { + return `Promise.resolve().then(${this.throwMissingModuleErrorFunction({ + request + })})`; + } - let resultingAvailableModules; - if (minAvailableModules.size > minAvailableModules.plus.size) { - // resultingAvailableModules = (modules of chunk) + (minAvailableModules + minAvailableModules.plus) - resultingAvailableModules = - /** @type {Set & {plus: Set}} */ (new Set()); - for (const module of minAvailableModules.plus) - minAvailableModules.add(module); - minAvailableModules.plus = EMPTY_SET; - resultingAvailableModules.plus = minAvailableModules; - chunkGroupInfo.minAvailableModulesOwned = false; - } else { - // resultingAvailableModules = (minAvailableModules + modules of chunk) + (minAvailableModules.plus) - resultingAvailableModules = - /** @type {Set & {plus: Set}} */ ( - new Set(minAvailableModules) - ); - resultingAvailableModules.plus = minAvailableModules.plus; + /** + * @param {Object} options options object + * @param {ChunkGraph} options.chunkGraph the chunk graph + * @param {Module} options.module the module + * @param {string} options.request the request that should be printed as comment + * @param {string=} options.idExpr expression to use as id expression + * @param {"expression" | "promise" | "statements"} options.type which kind of code should be returned + * @returns {string} the code + */ + weakError({ module, chunkGraph, request, idExpr, type }) { + const moduleId = chunkGraph.getModuleId(module); + const errorMessage = + moduleId === null + ? JSON.stringify("Module is not available (weak dependency)") + : idExpr + ? `"Module '" + ${idExpr} + "' is not available (weak dependency)"` + : JSON.stringify( + `Module '${moduleId}' is not available (weak dependency)` + ); + const comment = request ? Template.toNormalComment(request) + " " : ""; + const errorStatements = + `var e = new Error(${errorMessage}); ` + + comment + + "e.code = 'MODULE_NOT_FOUND'; throw e;"; + switch (type) { + case "statements": + return errorStatements; + case "promise": + return `Promise.resolve().then(${this.basicFunction( + "", + errorStatements + )})`; + case "expression": + return this.iife("", errorStatements); } + } - // add the modules from the chunk group to the set - for (const chunk of chunkGroupInfo.chunkGroup.chunks) { - for (const m of chunkGraph.getChunkModulesIterable(chunk)) { - resultingAvailableModules.add(m); + /** + * @param {Object} options options object + * @param {Module} options.module the module + * @param {ChunkGraph} options.chunkGraph the chunk graph + * @param {string} options.request the request that should be printed as comment + * @param {boolean=} options.weak if the dependency is weak (will create a nice error message) + * @returns {string} the expression + */ + moduleId({ module, chunkGraph, request, weak }) { + if (!module) { + return this.missingModule({ + request + }); + } + const moduleId = chunkGraph.getModuleId(module); + if (moduleId === null) { + if (weak) { + return "null /* weak dependency, without id */"; } + throw new Error( + `RuntimeTemplate.moduleId(): ${noModuleIdErrorMessage( + module, + chunkGraph + )}` + ); } - return (chunkGroupInfo.resultingAvailableModules = - resultingAvailableModules); - }; + return `${this.comment({ request })}${JSON.stringify(moduleId)}`; + } - const processConnectQueue = () => { - // Figure out new parents for chunk groups - // to get new available modules for these children - for (const [chunkGroupInfo, targets] of queueConnect) { - // 1. Add new targets to the list of children - if (chunkGroupInfo.children === undefined) { - chunkGroupInfo.children = targets; - } else { - for (const target of targets) { - chunkGroupInfo.children.add(target); - } + /** + * @param {Object} options options object + * @param {Module} options.module the module + * @param {ChunkGraph} options.chunkGraph the chunk graph + * @param {string} options.request the request that should be printed as comment + * @param {boolean=} options.weak if the dependency is weak (will create a nice error message) + * @param {Set} options.runtimeRequirements if set, will be filled with runtime requirements + * @returns {string} the expression + */ + moduleRaw({ module, chunkGraph, request, weak, runtimeRequirements }) { + if (!module) { + return this.missingModule({ + request + }); + } + const moduleId = chunkGraph.getModuleId(module); + if (moduleId === null) { + if (weak) { + // only weak referenced modules don't get an id + // we can always emit an error emitting code here + return this.weakError({ + module, + chunkGraph, + request, + type: "expression" + }); } + throw new Error( + `RuntimeTemplate.moduleId(): ${noModuleIdErrorMessage( + module, + chunkGraph + )}` + ); + } + runtimeRequirements.add(RuntimeGlobals.require); + return `__webpack_require__(${this.moduleId({ + module, + chunkGraph, + request, + weak + })})`; + } - // 2. Calculate resulting available modules - const resultingAvailableModules = - calculateResultingAvailableModules(chunkGroupInfo); - - const runtime = chunkGroupInfo.runtime; + /** + * @param {Object} options options object + * @param {Module} options.module the module + * @param {ChunkGraph} options.chunkGraph the chunk graph + * @param {string} options.request the request that should be printed as comment + * @param {boolean=} options.weak if the dependency is weak (will create a nice error message) + * @param {Set} options.runtimeRequirements if set, will be filled with runtime requirements + * @returns {string} the expression + */ + moduleExports({ module, chunkGraph, request, weak, runtimeRequirements }) { + return this.moduleRaw({ + module, + chunkGraph, + request, + weak, + runtimeRequirements + }); + } - // 3. Update chunk group info - for (const target of targets) { - target.availableModulesToBeMerged.push(resultingAvailableModules); - chunkGroupsForMerging.add(target); - const oldRuntime = target.runtime; - const newRuntime = mergeRuntime(oldRuntime, runtime); - if (oldRuntime !== newRuntime) { - target.runtime = newRuntime; - outdatedChunkGroupInfo.add(target); - } + /** + * @param {Object} options options object + * @param {Module} options.module the module + * @param {ChunkGraph} options.chunkGraph the chunk graph + * @param {string} options.request the request that should be printed as comment + * @param {boolean=} options.strict if the current module is in strict esm mode + * @param {boolean=} options.weak if the dependency is weak (will create a nice error message) + * @param {Set} options.runtimeRequirements if set, will be filled with runtime requirements + * @returns {string} the expression + */ + moduleNamespace({ + module, + chunkGraph, + request, + strict, + weak, + runtimeRequirements + }) { + if (!module) { + return this.missingModule({ + request + }); + } + if (chunkGraph.getModuleId(module) === null) { + if (weak) { + // only weak referenced modules don't get an id + // we can always emit an error emitting code here + return this.weakError({ + module, + chunkGraph, + request, + type: "expression" + }); } - - statConnectedChunkGroups += targets.size; + throw new Error( + `RuntimeTemplate.moduleNamespace(): ${noModuleIdErrorMessage( + module, + chunkGraph + )}` + ); } - queueConnect.clear(); - }; - - const processChunkGroupsForMerging = () => { - statProcessedChunkGroupsForMerging += chunkGroupsForMerging.size; - - // Execute the merge - for (const info of chunkGroupsForMerging) { - const availableModulesToBeMerged = info.availableModulesToBeMerged; - let cachedMinAvailableModules = info.minAvailableModules; - - statMergedAvailableModuleSets += availableModulesToBeMerged.length; + const moduleId = this.moduleId({ + module, + chunkGraph, + request, + weak + }); + const exportsType = module.getExportsType(chunkGraph.moduleGraph, strict); + switch (exportsType) { + case "namespace": + return this.moduleRaw({ + module, + chunkGraph, + request, + weak, + runtimeRequirements + }); + case "default-with-named": + runtimeRequirements.add(RuntimeGlobals.createFakeNamespaceObject); + return `${RuntimeGlobals.createFakeNamespaceObject}(${moduleId}, 3)`; + case "default-only": + runtimeRequirements.add(RuntimeGlobals.createFakeNamespaceObject); + return `${RuntimeGlobals.createFakeNamespaceObject}(${moduleId}, 1)`; + case "dynamic": + runtimeRequirements.add(RuntimeGlobals.createFakeNamespaceObject); + return `${RuntimeGlobals.createFakeNamespaceObject}(${moduleId}, 7)`; + } + } - // 1. Get minimal available modules - // It doesn't make sense to traverse a chunk again with more available modules. - // This step calculates the minimal available modules and skips traversal when - // the list didn't shrink. - if (availableModulesToBeMerged.length > 1) { - availableModulesToBeMerged.sort(bySetSize); - } - let changed = false; - merge: for (const availableModules of availableModulesToBeMerged) { - if (cachedMinAvailableModules === undefined) { - cachedMinAvailableModules = availableModules; - info.minAvailableModules = cachedMinAvailableModules; - info.minAvailableModulesOwned = false; - changed = true; - } else { - if (info.minAvailableModulesOwned) { - // We own it and can modify it - if (cachedMinAvailableModules.plus === availableModules.plus) { - for (const m of cachedMinAvailableModules) { - if (!availableModules.has(m)) { - cachedMinAvailableModules.delete(m); - changed = true; - } - } - } else { - for (const m of cachedMinAvailableModules) { - if (!availableModules.has(m) && !availableModules.plus.has(m)) { - cachedMinAvailableModules.delete(m); - changed = true; - } - } - for (const m of cachedMinAvailableModules.plus) { - if (!availableModules.has(m) && !availableModules.plus.has(m)) { - // We can't remove modules from the plus part - // so we need to merge plus into the normal part to allow modifying it - const iterator = - cachedMinAvailableModules.plus[Symbol.iterator](); - // fast forward add all modules until m - /** @type {IteratorResult} */ - let it; - while (!(it = iterator.next()).done) { - const module = it.value; - if (module === m) break; - cachedMinAvailableModules.add(module); - } - // check the remaining modules before adding - while (!(it = iterator.next()).done) { - const module = it.value; - if ( - availableModules.has(module) || - availableModules.plus.has(m) - ) { - cachedMinAvailableModules.add(module); - } - } - cachedMinAvailableModules.plus = EMPTY_SET; - changed = true; - continue merge; - } - } - } - } else if (cachedMinAvailableModules.plus === availableModules.plus) { - // Common and fast case when the plus part is shared - // We only need to care about the normal part - if (availableModules.size < cachedMinAvailableModules.size) { - // the new availableModules is smaller so it's faster to - // fork from the new availableModules - statForkedAvailableModules++; - statForkedAvailableModulesCount += availableModules.size; - statForkedMergedModulesCount += cachedMinAvailableModules.size; - // construct a new Set as intersection of cachedMinAvailableModules and availableModules - const newSet = /** @type {ModuleSetPlus} */ (new Set()); - newSet.plus = availableModules.plus; - for (const m of availableModules) { - if (cachedMinAvailableModules.has(m)) { - newSet.add(m); - } - } - statForkedResultModulesCount += newSet.size; - cachedMinAvailableModules = newSet; - info.minAvailableModulesOwned = true; - info.minAvailableModules = newSet; - changed = true; - continue merge; - } - for (const m of cachedMinAvailableModules) { - if (!availableModules.has(m)) { - // cachedMinAvailableModules need to be modified - // but we don't own it - statForkedAvailableModules++; - statForkedAvailableModulesCount += - cachedMinAvailableModules.size; - statForkedMergedModulesCount += availableModules.size; - // construct a new Set as intersection of cachedMinAvailableModules and availableModules - // as the plus part is equal we can just take over this one - const newSet = /** @type {ModuleSetPlus} */ (new Set()); - newSet.plus = availableModules.plus; - const iterator = cachedMinAvailableModules[Symbol.iterator](); - // fast forward add all modules until m - /** @type {IteratorResult} */ - let it; - while (!(it = iterator.next()).done) { - const module = it.value; - if (module === m) break; - newSet.add(module); - } - // check the remaining modules before adding - while (!(it = iterator.next()).done) { - const module = it.value; - if (availableModules.has(module)) { - newSet.add(module); - } - } - statForkedResultModulesCount += newSet.size; - cachedMinAvailableModules = newSet; - info.minAvailableModulesOwned = true; - info.minAvailableModules = newSet; - changed = true; - continue merge; - } - } - } else { - for (const m of cachedMinAvailableModules) { - if (!availableModules.has(m) && !availableModules.plus.has(m)) { - // cachedMinAvailableModules need to be modified - // but we don't own it - statForkedAvailableModules++; - statForkedAvailableModulesCount += - cachedMinAvailableModules.size; - statForkedAvailableModulesCountPlus += - cachedMinAvailableModules.plus.size; - statForkedMergedModulesCount += availableModules.size; - statForkedMergedModulesCountPlus += availableModules.plus.size; - // construct a new Set as intersection of cachedMinAvailableModules and availableModules - const newSet = /** @type {ModuleSetPlus} */ (new Set()); - newSet.plus = EMPTY_SET; - const iterator = cachedMinAvailableModules[Symbol.iterator](); - // fast forward add all modules until m - /** @type {IteratorResult} */ - let it; - while (!(it = iterator.next()).done) { - const module = it.value; - if (module === m) break; - newSet.add(module); - } - // check the remaining modules before adding - while (!(it = iterator.next()).done) { - const module = it.value; - if ( - availableModules.has(module) || - availableModules.plus.has(module) - ) { - newSet.add(module); - } - } - // also check all modules in cachedMinAvailableModules.plus - for (const module of cachedMinAvailableModules.plus) { - if ( - availableModules.has(module) || - availableModules.plus.has(module) - ) { - newSet.add(module); - } - } - statForkedResultModulesCount += newSet.size; - cachedMinAvailableModules = newSet; - info.minAvailableModulesOwned = true; - info.minAvailableModules = newSet; - changed = true; - continue merge; - } - } - for (const m of cachedMinAvailableModules.plus) { - if (!availableModules.has(m) && !availableModules.plus.has(m)) { - // cachedMinAvailableModules need to be modified - // but we don't own it - statForkedAvailableModules++; - statForkedAvailableModulesCount += - cachedMinAvailableModules.size; - statForkedAvailableModulesCountPlus += - cachedMinAvailableModules.plus.size; - statForkedMergedModulesCount += availableModules.size; - statForkedMergedModulesCountPlus += availableModules.plus.size; - // construct a new Set as intersection of cachedMinAvailableModules and availableModules - // we already know that all modules directly from cachedMinAvailableModules are in availableModules too - const newSet = /** @type {ModuleSetPlus} */ ( - new Set(cachedMinAvailableModules) - ); - newSet.plus = EMPTY_SET; - const iterator = - cachedMinAvailableModules.plus[Symbol.iterator](); - // fast forward add all modules until m - /** @type {IteratorResult} */ - let it; - while (!(it = iterator.next()).done) { - const module = it.value; - if (module === m) break; - newSet.add(module); - } - // check the remaining modules before adding - while (!(it = iterator.next()).done) { - const module = it.value; - if ( - availableModules.has(module) || - availableModules.plus.has(module) - ) { - newSet.add(module); - } - } - statForkedResultModulesCount += newSet.size; - cachedMinAvailableModules = newSet; - info.minAvailableModulesOwned = true; - info.minAvailableModules = newSet; - changed = true; - continue merge; - } - } - } - } - } - availableModulesToBeMerged.length = 0; - if (changed) { - info.resultingAvailableModules = undefined; - outdatedChunkGroupInfo.add(info); + /** + * @param {Object} options options object + * @param {ChunkGraph} options.chunkGraph the chunk graph + * @param {AsyncDependenciesBlock=} options.block the current dependencies block + * @param {Module} options.module the module + * @param {string} options.request the request that should be printed as comment + * @param {string} options.message a message for the comment + * @param {boolean=} options.strict if the current module is in strict esm mode + * @param {boolean=} options.weak if the dependency is weak (will create a nice error message) + * @param {Set} options.runtimeRequirements if set, will be filled with runtime requirements + * @returns {string} the promise expression + */ + moduleNamespacePromise({ + chunkGraph, + block, + module, + request, + message, + strict, + weak, + runtimeRequirements + }) { + if (!module) { + return this.missingModulePromise({ + request + }); + } + const moduleId = chunkGraph.getModuleId(module); + if (moduleId === null) { + if (weak) { + // only weak referenced modules don't get an id + // we can always emit an error emitting code here + return this.weakError({ + module, + chunkGraph, + request, + type: "promise" + }); } + throw new Error( + `RuntimeTemplate.moduleNamespacePromise(): ${noModuleIdErrorMessage( + module, + chunkGraph + )}` + ); } - chunkGroupsForMerging.clear(); - }; + const promise = this.blockPromise({ + chunkGraph, + block, + message, + runtimeRequirements + }); - const processChunkGroupsForCombining = () => { - for (const info of chunkGroupsForCombining) { - for (const source of info.availableSources) { - if (!source.minAvailableModules) { - chunkGroupsForCombining.delete(info); - break; - } + let appending; + let idExpr = JSON.stringify(chunkGraph.getModuleId(module)); + const comment = this.comment({ + request + }); + let header = ""; + if (weak) { + if (idExpr.length > 8) { + // 'var x="nnnnnn";x,"+x+",x' vs '"nnnnnn",nnnnnn,"nnnnnn"' + header += `var id = ${idExpr}; `; + idExpr = "id"; } + runtimeRequirements.add(RuntimeGlobals.moduleFactories); + header += `if(!${ + RuntimeGlobals.moduleFactories + }[${idExpr}]) { ${this.weakError({ + module, + chunkGraph, + request, + idExpr, + type: "statements" + })} } `; } - for (const info of chunkGroupsForCombining) { - const availableModules = /** @type {ModuleSetPlus} */ (new Set()); - availableModules.plus = EMPTY_SET; - const mergeSet = set => { - if (set.size > availableModules.plus.size) { - for (const item of availableModules.plus) availableModules.add(item); - availableModules.plus = set; + const moduleIdExpr = this.moduleId({ + module, + chunkGraph, + request, + weak + }); + const exportsType = module.getExportsType(chunkGraph.moduleGraph, strict); + let fakeType = 16; + switch (exportsType) { + case "namespace": + if (header) { + const rawModule = this.moduleRaw({ + module, + chunkGraph, + request, + weak, + runtimeRequirements + }); + appending = `.then(${this.basicFunction( + "", + `${header}return ${rawModule};` + )})`; } else { - for (const item of set) availableModules.add(item); + runtimeRequirements.add(RuntimeGlobals.require); + appending = `.then(__webpack_require__.bind(__webpack_require__, ${comment}${idExpr}))`; } - }; - // combine minAvailableModules from all resultingAvailableModules - for (const source of info.availableSources) { - const resultingAvailableModules = - calculateResultingAvailableModules(source); - mergeSet(resultingAvailableModules); - mergeSet(resultingAvailableModules.plus); - } - info.minAvailableModules = availableModules; - info.minAvailableModulesOwned = false; - info.resultingAvailableModules = undefined; - outdatedChunkGroupInfo.add(info); - } - chunkGroupsForCombining.clear(); - }; - - const processOutdatedChunkGroupInfo = () => { - statChunkGroupInfoUpdated += outdatedChunkGroupInfo.size; - // Revisit skipped elements - for (const info of outdatedChunkGroupInfo) { - // 1. Reconsider skipped items - if (info.skippedItems !== undefined) { - const { minAvailableModules } = info; - for (const module of info.skippedItems) { - if ( - !minAvailableModules.has(module) && - !minAvailableModules.plus.has(module) - ) { - queue.push({ - action: ADD_AND_ENTER_MODULE, - block: module, + break; + case "dynamic": + fakeType |= 4; + /* fall through */ + case "default-with-named": + fakeType |= 2; + /* fall through */ + case "default-only": + runtimeRequirements.add(RuntimeGlobals.createFakeNamespaceObject); + if (chunkGraph.moduleGraph.isAsync(module)) { + if (header) { + const rawModule = this.moduleRaw({ module, - chunk: info.chunkGroup.chunks[0], - chunkGroup: info.chunkGroup, - chunkGroupInfo: info + chunkGraph, + request, + weak, + runtimeRequirements }); - info.skippedItems.delete(module); - } - } - } - - // 2. Reconsider skipped connections - if (info.skippedModuleConnections !== undefined) { - const { minAvailableModules } = info; - for (const entry of info.skippedModuleConnections) { - const [module, activeState] = entry; - if (activeState === false) continue; - if (activeState === true) { - info.skippedModuleConnections.delete(entry); - } - if ( - activeState === true && - (minAvailableModules.has(module) || - minAvailableModules.plus.has(module)) - ) { - info.skippedItems.add(module); - continue; + appending = `.then(${this.basicFunction( + "", + `${header}return ${rawModule};` + )})`; + } else { + runtimeRequirements.add(RuntimeGlobals.require); + appending = `.then(__webpack_require__.bind(__webpack_require__, ${comment}${idExpr}))`; } - queue.push({ - action: activeState === true ? ADD_AND_ENTER_MODULE : PROCESS_BLOCK, - block: module, - module, - chunk: info.chunkGroup.chunks[0], - chunkGroup: info.chunkGroup, - chunkGroupInfo: info - }); - } - } - - // 2. Reconsider children chunk groups - if (info.children !== undefined) { - statChildChunkGroupsReconnected += info.children.size; - for (const cgi of info.children) { - let connectList = queueConnect.get(info); - if (connectList === undefined) { - connectList = new Set(); - queueConnect.set(info, connectList); + appending += `.then(${this.returningFunction( + `${RuntimeGlobals.createFakeNamespaceObject}(m, ${fakeType})`, + "m" + )})`; + } else { + fakeType |= 1; + if (header) { + const returnExpression = `${RuntimeGlobals.createFakeNamespaceObject}(${moduleIdExpr}, ${fakeType})`; + appending = `.then(${this.basicFunction( + "", + `${header}return ${returnExpression};` + )})`; + } else { + appending = `.then(${RuntimeGlobals.createFakeNamespaceObject}.bind(__webpack_require__, ${comment}${idExpr}, ${fakeType}))`; } - connectList.add(cgi); } - } - - // 3. Reconsider chunk groups for combining - if (info.availableChildren !== undefined) { - for (const cgi of info.availableChildren) { - chunkGroupsForCombining.add(cgi); - } - } + break; } - outdatedChunkGroupInfo.clear(); - }; - - // Iterative traversal of the Module graph - // Recursive would be simpler to write but could result in Stack Overflows - while (queue.length || queueConnect.size) { - logger.time("visitModules: visiting"); - processQueue(); - logger.timeAggregateEnd("visitModules: prepare"); - logger.timeEnd("visitModules: visiting"); - if (chunkGroupsForCombining.size > 0) { - logger.time("visitModules: combine available modules"); - processChunkGroupsForCombining(); - logger.timeEnd("visitModules: combine available modules"); - } + return `${promise || "Promise.resolve()"}${appending}`; + } - if (queueConnect.size > 0) { - logger.time("visitModules: calculating available modules"); - processConnectQueue(); - logger.timeEnd("visitModules: calculating available modules"); + /** + * @param {Object} options options object + * @param {ChunkGraph} options.chunkGraph the chunk graph + * @param {RuntimeSpec=} options.runtime runtime for which this code will be generated + * @param {RuntimeSpec | boolean=} options.runtimeCondition only execute the statement in some runtimes + * @param {Set} options.runtimeRequirements if set, will be filled with runtime requirements + * @returns {string} expression + */ + runtimeConditionExpression({ + chunkGraph, + runtimeCondition, + runtime, + runtimeRequirements + }) { + if (runtimeCondition === undefined) return "true"; + if (typeof runtimeCondition === "boolean") return `${runtimeCondition}`; + /** @type {Set} */ + const positiveRuntimeIds = new Set(); + forEachRuntime(runtimeCondition, runtime => + positiveRuntimeIds.add(`${chunkGraph.getRuntimeId(runtime)}`) + ); + /** @type {Set} */ + const negativeRuntimeIds = new Set(); + forEachRuntime(subtractRuntime(runtime, runtimeCondition), runtime => + negativeRuntimeIds.add(`${chunkGraph.getRuntimeId(runtime)}`) + ); + runtimeRequirements.add(RuntimeGlobals.runtimeId); + return compileBooleanMatcher.fromLists( + Array.from(positiveRuntimeIds), + Array.from(negativeRuntimeIds) + )(RuntimeGlobals.runtimeId); + } - if (chunkGroupsForMerging.size > 0) { - logger.time("visitModules: merging available modules"); - processChunkGroupsForMerging(); - logger.timeEnd("visitModules: merging available modules"); + /** + * + * @param {Object} options options object + * @param {boolean=} options.update whether a new variable should be created or the existing one updated + * @param {Module} options.module the module + * @param {ChunkGraph} options.chunkGraph the chunk graph + * @param {string} options.request the request that should be printed as comment + * @param {string} options.importVar name of the import variable + * @param {Module} options.originModule module in which the statement is emitted + * @param {boolean=} options.weak true, if this is a weak dependency + * @param {Set} options.runtimeRequirements if set, will be filled with runtime requirements + * @returns {[string, string]} the import statement and the compat statement + */ + importStatement({ + update, + module, + chunkGraph, + request, + importVar, + originModule, + weak, + runtimeRequirements + }) { + if (!module) { + return [ + this.missingModuleStatement({ + request + }), + "" + ]; + } + if (chunkGraph.getModuleId(module) === null) { + if (weak) { + // only weak referenced modules don't get an id + // we can always emit an error emitting code here + return [ + this.weakError({ + module, + chunkGraph, + request, + type: "statements" + }), + "" + ]; } + throw new Error( + `RuntimeTemplate.importStatement(): ${noModuleIdErrorMessage( + module, + chunkGraph + )}` + ); } + const moduleId = this.moduleId({ + module, + chunkGraph, + request, + weak + }); + const optDeclaration = update ? "" : "var "; - if (outdatedChunkGroupInfo.size > 0) { - logger.time("visitModules: check modules for revisit"); - processOutdatedChunkGroupInfo(); - logger.timeEnd("visitModules: check modules for revisit"); - } + const exportsType = module.getExportsType( + chunkGraph.moduleGraph, + originModule.buildMeta.strictHarmonyModule + ); + runtimeRequirements.add(RuntimeGlobals.require); + const importContent = `/* harmony import */ ${optDeclaration}${importVar} = __webpack_require__(${moduleId});\n`; - // Run queueDelayed when all items of the queue are processed - // This is important to get the global indexing correct - // Async blocks should be processed after all sync blocks are processed - if (queue.length === 0) { - const tempQueue = queue; - queue = queueDelayed.reverse(); - queueDelayed = tempQueue; + if (exportsType === "dynamic") { + runtimeRequirements.add(RuntimeGlobals.compatGetDefaultExport); + return [ + importContent, + `/* harmony import */ ${optDeclaration}${importVar}_default = /*#__PURE__*/${RuntimeGlobals.compatGetDefaultExport}(${importVar});\n` + ]; } + return [importContent, ""]; } - logger.log( - `${statProcessedQueueItems} queue items processed (${statProcessedBlocks} blocks)` - ); - logger.log(`${statConnectedChunkGroups} chunk groups connected`); - logger.log( - `${statProcessedChunkGroupsForMerging} chunk groups processed for merging (${statMergedAvailableModuleSets} module sets, ${statForkedAvailableModules} forked, ${statForkedAvailableModulesCount} + ${statForkedAvailableModulesCountPlus} modules forked, ${statForkedMergedModulesCount} + ${statForkedMergedModulesCountPlus} modules merged into fork, ${statForkedResultModulesCount} resulting modules)` - ); - logger.log( - `${statChunkGroupInfoUpdated} chunk group info updated (${statChildChunkGroupsReconnected} already connected chunk groups reconnected)` - ); -}; - -/** - * - * @param {Compilation} compilation the compilation - * @param {Set} blocksWithNestedBlocks flag for blocks that have nested blocks - * @param {Map} blockConnections connection for blocks - * @param {Map} chunkGroupInfoMap mapping from chunk group to available modules - */ -const connectChunkGroups = ( - compilation, - blocksWithNestedBlocks, - blockConnections, - chunkGroupInfoMap -) => { - const { chunkGraph } = compilation; - /** - * Helper function to check if all modules of a chunk are available - * - * @param {ChunkGroup} chunkGroup the chunkGroup to scan - * @param {ModuleSetPlus} availableModules the comparator set - * @returns {boolean} return true if all modules of a chunk are available + * @param {Object} options options + * @param {ModuleGraph} options.moduleGraph the module graph + * @param {Module} options.module the module + * @param {string} options.request the request + * @param {string | string[]} options.exportName the export name + * @param {Module} options.originModule the origin module + * @param {boolean|undefined} options.asiSafe true, if location is safe for ASI, a bracket can be emitted + * @param {boolean} options.isCall true, if expression will be called + * @param {boolean} options.callContext when false, call context will not be preserved + * @param {boolean} options.defaultInterop when true and accessing the default exports, interop code will be generated + * @param {string} options.importVar the identifier name of the import variable + * @param {InitFragment[]} options.initFragments init fragments will be added here + * @param {RuntimeSpec} options.runtime runtime for which this code will be generated + * @param {Set} options.runtimeRequirements if set, will be filled with runtime requirements + * @returns {string} expression */ - const areModulesAvailable = (chunkGroup, availableModules) => { - for (const chunk of chunkGroup.chunks) { - for (const module of chunkGraph.getChunkModulesIterable(chunk)) { - if (!availableModules.has(module) && !availableModules.plus.has(module)) - return false; - } + exportFromImport({ + moduleGraph, + module, + request, + exportName, + originModule, + asiSafe, + isCall, + callContext, + defaultInterop, + importVar, + initFragments, + runtime, + runtimeRequirements + }) { + if (!module) { + return this.missingModule({ + request + }); } - return true; - }; - - // For each edge in the basic chunk graph - for (const [block, connections] of blockConnections) { - // 1. Check if connection is needed - // When none of the dependencies need to be connected - // we can skip all of them - // It's not possible to filter each item so it doesn't create inconsistent - // connections and modules can only create one version - // TODO maybe decide this per runtime - if ( - // TODO is this needed? - !blocksWithNestedBlocks.has(block) && - connections.every(({ chunkGroup, originChunkGroupInfo }) => - areModulesAvailable( - chunkGroup, - originChunkGroupInfo.resultingAvailableModules - ) - ) - ) { - continue; + if (!Array.isArray(exportName)) { + exportName = exportName ? [exportName] : []; } + const exportsType = module.getExportsType( + moduleGraph, + originModule.buildMeta.strictHarmonyModule + ); - // 2. Foreach edge - for (let i = 0; i < connections.length; i++) { - const { chunkGroup, originChunkGroupInfo } = connections[i]; - - // 3. Connect block with chunk - chunkGraph.connectBlockAndChunkGroup(block, chunkGroup); - - // 4. Connect chunk with parent - connectChunkGroupParentAndChild( - originChunkGroupInfo.chunkGroup, - chunkGroup - ); + if (defaultInterop) { + if (exportName.length > 0 && exportName[0] === "default") { + switch (exportsType) { + case "dynamic": + if (isCall) { + return `${importVar}_default()${propertyAccess(exportName, 1)}`; + } else { + return asiSafe + ? `(${importVar}_default()${propertyAccess(exportName, 1)})` + : asiSafe === false + ? `;(${importVar}_default()${propertyAccess(exportName, 1)})` + : `${importVar}_default.a${propertyAccess(exportName, 1)}`; + } + case "default-only": + case "default-with-named": + exportName = exportName.slice(1); + break; + } + } else if (exportName.length > 0) { + if (exportsType === "default-only") { + return ( + "/* non-default import from non-esm module */undefined" + + propertyAccess(exportName, 1) + ); + } else if ( + exportsType !== "namespace" && + exportName[0] === "__esModule" + ) { + return "/* __esModule */true"; + } + } else if ( + exportsType === "default-only" || + exportsType === "default-with-named" + ) { + runtimeRequirements.add(RuntimeGlobals.createFakeNamespaceObject); + initFragments.push( + new InitFragment( + `var ${importVar}_namespace_cache;\n`, + InitFragment.STAGE_CONSTANTS, + -1, + `${importVar}_namespace_cache` + ) + ); + return `/*#__PURE__*/ ${ + asiSafe ? "" : asiSafe === false ? ";" : "Object" + }(${importVar}_namespace_cache || (${importVar}_namespace_cache = ${ + RuntimeGlobals.createFakeNamespaceObject + }(${importVar}${exportsType === "default-only" ? "" : ", 2"})))`; + } } - } -}; - -/** - * Remove all unconnected chunk groups - * @param {Compilation} compilation the compilation - * @param {Iterable} allCreatedChunkGroups all chunk groups that where created before - */ -const cleanupUnconnectedGroups = (compilation, allCreatedChunkGroups) => { - const { chunkGraph } = compilation; - for (const chunkGroup of allCreatedChunkGroups) { - if (chunkGroup.getNumberOfParents() === 0) { - for (const chunk of chunkGroup.chunks) { - compilation.chunks.delete(chunk); - chunkGraph.disconnectChunk(chunk); + if (exportName.length > 0) { + const exportsInfo = moduleGraph.getExportsInfo(module); + const used = exportsInfo.getUsedName(exportName, runtime); + if (!used) { + const comment = Template.toNormalComment( + `unused export ${propertyAccess(exportName)}` + ); + return `${comment} undefined`; } - chunkGraph.disconnectChunkGroup(chunkGroup); - chunkGroup.remove(); + const comment = equals(used, exportName) + ? "" + : Template.toNormalComment(propertyAccess(exportName)) + " "; + const access = `${importVar}${comment}${propertyAccess(used)}`; + if (isCall && callContext === false) { + return asiSafe + ? `(0,${access})` + : asiSafe === false + ? `;(0,${access})` + : `/*#__PURE__*/Object(${access})`; + } + return access; + } else { + return importVar; } } -}; - -/** - * This method creates the Chunk graph from the Module graph - * @param {Compilation} compilation the compilation - * @param {Map} inputEntrypointsAndModules chunk groups which are processed with the modules - * @returns {void} - */ -const buildChunkGraph = (compilation, inputEntrypointsAndModules) => { - const logger = compilation.getLogger("webpack.buildChunkGraph"); - - // SHARED STATE - - /** @type {Map} */ - const blockConnections = new Map(); - - /** @type {Set} */ - const allCreatedChunkGroups = new Set(); - - /** @type {Map} */ - const chunkGroupInfoMap = new Map(); - - /** @type {Set} */ - const blocksWithNestedBlocks = new Set(); - - // PART ONE - - logger.time("visitModules"); - visitModules( - logger, - compilation, - inputEntrypointsAndModules, - chunkGroupInfoMap, - blockConnections, - blocksWithNestedBlocks, - allCreatedChunkGroups - ); - logger.timeEnd("visitModules"); - - // PART TWO - - logger.time("connectChunkGroups"); - connectChunkGroups( - compilation, - blocksWithNestedBlocks, - blockConnections, - chunkGroupInfoMap - ); - logger.timeEnd("connectChunkGroups"); - - for (const [chunkGroup, chunkGroupInfo] of chunkGroupInfoMap) { - for (const chunk of chunkGroup.chunks) - chunk.runtime = mergeRuntime(chunk.runtime, chunkGroupInfo.runtime); - } - - // Cleanup work - - logger.time("cleanup"); - cleanupUnconnectedGroups(compilation, allCreatedChunkGroups); - logger.timeEnd("cleanup"); -}; - -module.exports = buildChunkGraph; - - -/***/ }), - -/***/ 30743: -/***/ (function(module) { - -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ - - -/** @typedef {import("../Compiler")} Compiler */ - -class AddBuildDependenciesPlugin { /** - * @param {Iterable} buildDependencies list of build dependencies + * @param {Object} options options + * @param {AsyncDependenciesBlock} options.block the async block + * @param {string} options.message the message + * @param {ChunkGraph} options.chunkGraph the chunk graph + * @param {Set} options.runtimeRequirements if set, will be filled with runtime requirements + * @returns {string} expression */ - constructor(buildDependencies) { - this.buildDependencies = new Set(buildDependencies); + blockPromise({ block, message, chunkGraph, runtimeRequirements }) { + if (!block) { + const comment = this.comment({ + message + }); + return `Promise.resolve(${comment.trim()})`; + } + const chunkGroup = chunkGraph.getBlockChunkGroup(block); + if (!chunkGroup || chunkGroup.chunks.length === 0) { + const comment = this.comment({ + message + }); + return `Promise.resolve(${comment.trim()})`; + } + const chunks = chunkGroup.chunks.filter( + chunk => !chunk.hasRuntime() && chunk.id !== null + ); + const comment = this.comment({ + message, + chunkName: block.chunkName + }); + if (chunks.length === 1) { + const chunkId = JSON.stringify(chunks[0].id); + runtimeRequirements.add(RuntimeGlobals.ensureChunk); + return `${RuntimeGlobals.ensureChunk}(${comment}${chunkId})`; + } else if (chunks.length > 0) { + runtimeRequirements.add(RuntimeGlobals.ensureChunk); + const requireChunkId = chunk => + `${RuntimeGlobals.ensureChunk}(${JSON.stringify(chunk.id)})`; + return `Promise.all(${comment.trim()}[${chunks + .map(requireChunkId) + .join(", ")}])`; + } else { + return `Promise.resolve(${comment.trim()})`; + } } /** - * Apply the plugin - * @param {Compiler} compiler the compiler instance - * @returns {void} + * @param {Object} options options + * @param {AsyncDependenciesBlock} options.block the async block + * @param {ChunkGraph} options.chunkGraph the chunk graph + * @param {Set} options.runtimeRequirements if set, will be filled with runtime requirements + * @param {string=} options.request request string used originally + * @returns {string} expression */ - apply(compiler) { - compiler.hooks.compilation.tap( - "AddBuildDependenciesPlugin", - compilation => { - compilation.buildDependencies.addAll(this.buildDependencies); - } + asyncModuleFactory({ block, chunkGraph, runtimeRequirements, request }) { + const dep = block.dependencies[0]; + const module = chunkGraph.moduleGraph.getModule(dep); + const ensureChunk = this.blockPromise({ + block, + message: "", + chunkGraph, + runtimeRequirements + }); + const factory = this.returningFunction( + this.moduleRaw({ + module, + chunkGraph, + request, + runtimeRequirements + }) + ); + return this.returningFunction( + ensureChunk.startsWith("Promise.resolve(") + ? `${factory}` + : `${ensureChunk}.then(${this.returningFunction(factory)})` ); } -} - -module.exports = AddBuildDependenciesPlugin; - -/***/ }), - -/***/ 19724: -/***/ (function(module) { - -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ - - - -/** @typedef {import("../Compiler")} Compiler */ - -class AddManagedPathsPlugin { /** - * @param {Iterable} managedPaths list of managed paths - * @param {Iterable} immutablePaths list of immutable paths + * @param {Object} options options + * @param {Dependency} options.dependency the dependency + * @param {ChunkGraph} options.chunkGraph the chunk graph + * @param {Set} options.runtimeRequirements if set, will be filled with runtime requirements + * @param {string=} options.request request string used originally + * @returns {string} expression */ - constructor(managedPaths, immutablePaths) { - this.managedPaths = new Set(managedPaths); - this.immutablePaths = new Set(immutablePaths); + syncModuleFactory({ dependency, chunkGraph, runtimeRequirements, request }) { + const module = chunkGraph.moduleGraph.getModule(dependency); + const factory = this.returningFunction( + this.moduleRaw({ + module, + chunkGraph, + request, + runtimeRequirements + }) + ); + return this.returningFunction(factory); } /** - * Apply the plugin - * @param {Compiler} compiler the compiler instance - * @returns {void} + * @param {Object} options options + * @param {string} options.exportsArgument the name of the exports object + * @param {Set} options.runtimeRequirements if set, will be filled with runtime requirements + * @returns {string} statement */ - apply(compiler) { - for (const managedPath of this.managedPaths) { - compiler.managedPaths.add(managedPath); - } - for (const immutablePath of this.immutablePaths) { - compiler.immutablePaths.add(immutablePath); - } + defineEsModuleFlagStatement({ exportsArgument, runtimeRequirements }) { + runtimeRequirements.add(RuntimeGlobals.makeNamespaceObject); + runtimeRequirements.add(RuntimeGlobals.exports); + return `${RuntimeGlobals.makeNamespaceObject}(${exportsArgument});\n`; } } -module.exports = AddManagedPathsPlugin; +module.exports = RuntimeTemplate; /***/ }), -/***/ 26277: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { +/***/ 31374: +/***/ (function(module) { "use strict"; /* @@ -65714,296 +61866,76 @@ module.exports = AddManagedPathsPlugin; -const Cache = __webpack_require__(99453); -const ProgressPlugin = __webpack_require__(41306); - -/** @typedef {import("../Compiler")} Compiler */ - -const BUILD_DEPENDENCIES_KEY = Symbol(); - -class IdleFileCachePlugin { - /** - * @param {TODO} strategy cache strategy - * @param {number} idleTimeout timeout - * @param {number} idleTimeoutForInitialStore initial timeout - * @param {number} idleTimeoutAfterLargeChanges timeout after changes - */ - constructor( - strategy, - idleTimeout, - idleTimeoutForInitialStore, - idleTimeoutAfterLargeChanges - ) { - this.strategy = strategy; - this.idleTimeout = idleTimeout; - this.idleTimeoutForInitialStore = idleTimeoutForInitialStore; - this.idleTimeoutAfterLargeChanges = idleTimeoutAfterLargeChanges; +class SelfModuleFactory { + constructor(moduleGraph) { + this.moduleGraph = moduleGraph; } - /** - * Apply the plugin - * @param {Compiler} compiler the compiler instance - * @returns {void} - */ - apply(compiler) { - let strategy = this.strategy; - const idleTimeout = this.idleTimeout; - const idleTimeoutForInitialStore = Math.min( - idleTimeout, - this.idleTimeoutForInitialStore - ); - const idleTimeoutAfterLargeChanges = this.idleTimeoutAfterLargeChanges; - const resolvedPromise = Promise.resolve(); - - let timeSpendInBuild = 0; - let timeSpendInStore = 0; - let avgTimeSpendInStore = 0; - - /** @type {Map Promise>} */ - const pendingIdleTasks = new Map(); - - compiler.cache.hooks.store.tap( - { name: "IdleFileCachePlugin", stage: Cache.STAGE_DISK }, - (identifier, etag, data) => { - pendingIdleTasks.set(identifier, () => - strategy.store(identifier, etag, data) - ); - } - ); + create(data, callback) { + const module = this.moduleGraph.getParentModule(data.dependencies[0]); + callback(null, { + module + }); + } +} - compiler.cache.hooks.get.tapPromise( - { name: "IdleFileCachePlugin", stage: Cache.STAGE_DISK }, - (identifier, etag, gotHandlers) => { - const restore = () => - strategy.restore(identifier, etag).then(cacheEntry => { - if (cacheEntry === undefined) { - gotHandlers.push((result, callback) => { - if (result !== undefined) { - pendingIdleTasks.set(identifier, () => - strategy.store(identifier, etag, result) - ); - } - callback(); - }); - } else { - return cacheEntry; - } - }); - const pendingTask = pendingIdleTasks.get(identifier); - if (pendingTask !== undefined) { - pendingIdleTasks.delete(identifier); - return pendingTask().then(restore); - } - return restore(); - } - ); +module.exports = SelfModuleFactory; - compiler.cache.hooks.storeBuildDependencies.tap( - { name: "IdleFileCachePlugin", stage: Cache.STAGE_DISK }, - dependencies => { - pendingIdleTasks.set(BUILD_DEPENDENCIES_KEY, () => - strategy.storeBuildDependencies(dependencies) - ); - } - ); - compiler.cache.hooks.shutdown.tapPromise( - { name: "IdleFileCachePlugin", stage: Cache.STAGE_DISK }, - () => { - if (idleTimer) { - clearTimeout(idleTimer); - idleTimer = undefined; - } - isIdle = false; - const reportProgress = ProgressPlugin.getReporter(compiler); - const jobs = Array.from(pendingIdleTasks.values()); - if (reportProgress) reportProgress(0, "process pending cache items"); - const promises = jobs.map(fn => fn()); - pendingIdleTasks.clear(); - promises.push(currentIdlePromise); - const promise = Promise.all(promises); - currentIdlePromise = promise.then(() => strategy.afterAllStored()); - if (reportProgress) { - currentIdlePromise = currentIdlePromise.then(() => { - reportProgress(1, `stored`); - }); - } - return currentIdlePromise.then(() => { - // Reset strategy - if (strategy.clear) strategy.clear(); - }); - } - ); +/***/ }), + +/***/ 16551: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Sean Larkin @thelarkinn +*/ - /** @type {Promise} */ - let currentIdlePromise = resolvedPromise; - let isIdle = false; - let isInitialStore = true; - const processIdleTasks = () => { - if (isIdle) { - const startTime = Date.now(); - if (pendingIdleTasks.size > 0) { - const promises = [currentIdlePromise]; - const maxTime = startTime + 100; - let maxCount = 100; - for (const [filename, factory] of pendingIdleTasks) { - pendingIdleTasks.delete(filename); - promises.push(factory()); - if (maxCount-- <= 0 || Date.now() > maxTime) break; - } - currentIdlePromise = Promise.all(promises); - currentIdlePromise.then(() => { - timeSpendInStore += Date.now() - startTime; - // Allow to exit the process between - idleTimer = setTimeout(processIdleTasks, 0); - idleTimer.unref(); - }); - return; - } - currentIdlePromise = currentIdlePromise - .then(async () => { - await strategy.afterAllStored(); - timeSpendInStore += Date.now() - startTime; - avgTimeSpendInStore = - Math.max(avgTimeSpendInStore, timeSpendInStore) * 0.9 + - timeSpendInStore * 0.1; - timeSpendInStore = 0; - timeSpendInBuild = 0; - }) - .catch(err => { - const logger = compiler.getInfrastructureLogger( - "IdleFileCachePlugin" - ); - logger.warn(`Background tasks during idle failed: ${err.message}`); - logger.debug(err.stack); - }); - isInitialStore = false; - } - }; - let idleTimer = undefined; - compiler.cache.hooks.beginIdle.tap( - { name: "IdleFileCachePlugin", stage: Cache.STAGE_DISK }, - () => { - const isLargeChange = timeSpendInBuild > avgTimeSpendInStore * 2; - if (isInitialStore && idleTimeoutForInitialStore < idleTimeout) { - compiler - .getInfrastructureLogger("IdleFileCachePlugin") - .log( - `Initial cache was generated and cache will be persisted in ${ - idleTimeoutForInitialStore / 1000 - }s.` - ); - } else if ( - isLargeChange && - idleTimeoutAfterLargeChanges < idleTimeout - ) { - compiler - .getInfrastructureLogger("IdleFileCachePlugin") - .log( - `Spend ${Math.round(timeSpendInBuild) / 1000}s in build and ${ - Math.round(avgTimeSpendInStore) / 1000 - }s in average in cache store. This is considered as large change and cache will be persisted in ${ - idleTimeoutAfterLargeChanges / 1000 - }s.` - ); - } - idleTimer = setTimeout(() => { - idleTimer = undefined; - isIdle = true; - resolvedPromise.then(processIdleTasks); - }, Math.min(isInitialStore ? idleTimeoutForInitialStore : Infinity, isLargeChange ? idleTimeoutAfterLargeChanges : Infinity, idleTimeout)); - idleTimer.unref(); - } - ); - compiler.cache.hooks.endIdle.tap( - { name: "IdleFileCachePlugin", stage: Cache.STAGE_DISK }, - () => { - if (idleTimer) { - clearTimeout(idleTimer); - idleTimer = undefined; - } - isIdle = false; - } - ); - compiler.hooks.done.tap("IdleFileCachePlugin", stats => { - // 10% build overhead is ignored, as it's not cacheable - timeSpendInBuild *= 0.9; - timeSpendInBuild += stats.endTime - stats.startTime; - }); - } -} -module.exports = IdleFileCachePlugin; + +module.exports = __webpack_require__(82430); /***/ }), -/***/ 4045: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { +/***/ 15979: +/***/ (function(__unused_webpack_module, exports) { "use strict"; /* MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra + Author Sean Larkin @thelarkinn */ -const Cache = __webpack_require__(99453); - -/** @typedef {import("webpack-sources").Source} Source */ -/** @typedef {import("../Cache").Etag} Etag */ -/** @typedef {import("../Compiler")} Compiler */ -/** @typedef {import("../Module")} Module */ +/** + * @param {number} size the size in bytes + * @returns {string} the formatted size + */ +exports.formatSize = size => { + if (typeof size !== "number" || Number.isNaN(size) === true) { + return "unknown size"; + } -class MemoryCachePlugin { - /** - * Apply the plugin - * @param {Compiler} compiler the compiler instance - * @returns {void} - */ - apply(compiler) { - /** @type {Map} */ - const cache = new Map(); - compiler.cache.hooks.store.tap( - { name: "MemoryCachePlugin", stage: Cache.STAGE_MEMORY }, - (identifier, etag, data) => { - cache.set(identifier, { etag, data }); - } - ); - compiler.cache.hooks.get.tap( - { name: "MemoryCachePlugin", stage: Cache.STAGE_MEMORY }, - (identifier, etag, gotHandlers) => { - const cacheEntry = cache.get(identifier); - if (cacheEntry === null) { - return null; - } else if (cacheEntry !== undefined) { - return cacheEntry.etag === etag ? cacheEntry.data : null; - } - gotHandlers.push((result, callback) => { - if (result === undefined) { - cache.set(identifier, null); - } else { - cache.set(identifier, { etag, data: result }); - } - return callback(); - }); - } - ); - compiler.cache.hooks.shutdown.tap( - { name: "MemoryCachePlugin", stage: Cache.STAGE_MEMORY }, - () => { - cache.clear(); - } - ); + if (size <= 0) { + return "0 bytes"; } -} -module.exports = MemoryCachePlugin; + + const abbreviations = ["bytes", "KiB", "MiB", "GiB"]; + const index = Math.floor(Math.log(size) / Math.log(1024)); + + return `${+(size / Math.pow(1024, index)).toPrecision(3)} ${ + abbreviations[index] + }`; +}; /***/ }), -/***/ 34854: +/***/ 37661: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; @@ -66014,133 +61946,61 @@ module.exports = MemoryCachePlugin; -const Cache = __webpack_require__(99453); +const JavascriptModulesPlugin = __webpack_require__(76767); -/** @typedef {import("webpack-sources").Source} Source */ -/** @typedef {import("../Cache").Etag} Etag */ -/** @typedef {import("../Compiler")} Compiler */ -/** @typedef {import("../Module")} Module */ +/** @typedef {import("./Compilation")} Compilation */ -class MemoryWithGcCachePlugin { - constructor({ maxGenerations }) { - this._maxGenerations = maxGenerations; +class SourceMapDevToolModuleOptionsPlugin { + constructor(options) { + this.options = options; } + /** - * Apply the plugin - * @param {Compiler} compiler the compiler instance + * @param {Compilation} compilation the compiler instance * @returns {void} */ - apply(compiler) { - const maxGenerations = this._maxGenerations; - /** @type {Map} */ - const cache = new Map(); - /** @type {Map} */ - const oldCache = new Map(); - let generation = 0; - let cachePosition = 0; - const logger = compiler.getInfrastructureLogger("MemoryWithGcCachePlugin"); - compiler.hooks.afterDone.tap("MemoryWithGcCachePlugin", () => { - generation++; - let clearedEntries = 0; - let lastClearedIdentifier; - for (const [identifier, entry] of oldCache) { - if (entry.until > generation) break; - - oldCache.delete(identifier); - if (cache.get(identifier) === undefined) { - cache.delete(identifier); - clearedEntries++; - lastClearedIdentifier = identifier; - } - } - if (clearedEntries > 0 || oldCache.size > 0) { - logger.log( - `${cache.size - oldCache.size} active entries, ${ - oldCache.size - } recently unused cached entries${ - clearedEntries > 0 - ? `, ${clearedEntries} old unused cache entries removed e. g. ${lastClearedIdentifier}` - : "" - }` - ); - } - let i = (cache.size / maxGenerations) | 0; - let j = cachePosition >= cache.size ? 0 : cachePosition; - cachePosition = j + i; - for (const [identifier, entry] of cache) { - if (j !== 0) { - j--; - continue; + apply(compilation) { + const options = this.options; + if (options.module !== false) { + compilation.hooks.buildModule.tap( + "SourceMapDevToolModuleOptionsPlugin", + module => { + module.useSourceMap = true; } - if (entry !== undefined) { - // We don't delete the cache entry, but set it to undefined instead - // This reserves the location in the data table and avoids rehashing - // when constantly adding and removing entries. - // It will be deleted when removed from oldCache. - cache.set(identifier, undefined); - oldCache.delete(identifier); - oldCache.set(identifier, { - entry, - until: generation + maxGenerations - }); - if (i-- === 0) break; + ); + compilation.hooks.runtimeModule.tap( + "SourceMapDevToolModuleOptionsPlugin", + module => { + module.useSourceMap = true; } - } - }); - compiler.cache.hooks.store.tap( - { name: "MemoryWithGcCachePlugin", stage: Cache.STAGE_MEMORY }, - (identifier, etag, data) => { - cache.set(identifier, { etag, data }); - } - ); - compiler.cache.hooks.get.tap( - { name: "MemoryWithGcCachePlugin", stage: Cache.STAGE_MEMORY }, - (identifier, etag, gotHandlers) => { - const cacheEntry = cache.get(identifier); - if (cacheEntry === null) { - return null; - } else if (cacheEntry !== undefined) { - return cacheEntry.etag === etag ? cacheEntry.data : null; + ); + } else { + compilation.hooks.buildModule.tap( + "SourceMapDevToolModuleOptionsPlugin", + module => { + module.useSimpleSourceMap = true; } - const oldCacheEntry = oldCache.get(identifier); - if (oldCacheEntry !== undefined) { - const cacheEntry = oldCacheEntry.entry; - if (cacheEntry === null) { - oldCache.delete(identifier); - cache.set(identifier, cacheEntry); - return null; - } else { - if (cacheEntry.etag !== etag) return null; - oldCache.delete(identifier); - cache.set(identifier, cacheEntry); - return cacheEntry.data; - } + ); + compilation.hooks.runtimeModule.tap( + "SourceMapDevToolModuleOptionsPlugin", + module => { + module.useSimpleSourceMap = true; } - gotHandlers.push((result, callback) => { - if (result === undefined) { - cache.set(identifier, null); - } else { - cache.set(identifier, { etag, data: result }); - } - return callback(); - }); - } - ); - compiler.cache.hooks.shutdown.tap( - { name: "MemoryWithGcCachePlugin", stage: Cache.STAGE_MEMORY }, - () => { - cache.clear(); - oldCache.clear(); - } + ); + } + JavascriptModulesPlugin.getCompilationHooks(compilation).useSourceMap.tap( + "SourceMapDevToolModuleOptionsPlugin", + () => true ); } } -module.exports = MemoryWithGcCachePlugin; + +module.exports = SourceMapDevToolModuleOptionsPlugin; /***/ }), -/***/ 46810: +/***/ 79917: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; @@ -66151,1821 +62011,1453 @@ module.exports = MemoryWithGcCachePlugin; -const FileSystemInfo = __webpack_require__(13679); +const asyncLib = __webpack_require__(36386); +const { ConcatSource, RawSource } = __webpack_require__(96192); +const Compilation = __webpack_require__(59622); +const ModuleFilenameHelpers = __webpack_require__(80295); const ProgressPlugin = __webpack_require__(41306); -const { formatSize } = __webpack_require__(15979); -const SerializerMiddleware = __webpack_require__(37063); -const LazySet = __webpack_require__(59534); -const makeSerializable = __webpack_require__(26522); -const memoize = __webpack_require__(84297); -const { - createFileSerializer, - NOT_SERIALIZABLE -} = __webpack_require__(99551); - -/** @typedef {import("../../declarations/WebpackOptions").SnapshotOptions} SnapshotOptions */ -/** @typedef {import("../Cache").Etag} Etag */ -/** @typedef {import("../Compiler")} Compiler */ -/** @typedef {import("../FileSystemInfo").Snapshot} Snapshot */ -/** @typedef {import("../logging/Logger").Logger} Logger */ -/** @typedef {import("../util/fs").IntermediateFileSystem} IntermediateFileSystem */ - -class PackContainer { - /** - * @param {Object} data stored data - * @param {string} version version identifier - * @param {Snapshot} buildSnapshot snapshot of all build dependencies - * @param {Set} buildDependencies list of all unresolved build dependencies captured - * @param {Map} resolveResults result of the resolved build dependencies - * @param {Snapshot} resolveBuildDependenciesSnapshot snapshot of the dependencies of the build dependencies resolving - */ - constructor( - data, - version, - buildSnapshot, - buildDependencies, - resolveResults, - resolveBuildDependenciesSnapshot - ) { - this.data = data; - this.version = version; - this.buildSnapshot = buildSnapshot; - this.buildDependencies = buildDependencies; - this.resolveResults = resolveResults; - this.resolveBuildDependenciesSnapshot = resolveBuildDependenciesSnapshot; - } +const SourceMapDevToolModuleOptionsPlugin = __webpack_require__(37661); +const createSchemaValidation = __webpack_require__(77695); +const createHash = __webpack_require__(24123); +const { relative, dirname } = __webpack_require__(93204); +const { makePathsAbsolute } = __webpack_require__(96236); - serialize({ write, writeLazy }) { - write(this.version); - write(this.buildSnapshot); - write(this.buildDependencies); - write(this.resolveResults); - write(this.resolveBuildDependenciesSnapshot); - writeLazy(this.data); - } +/** @typedef {import("webpack-sources").MapOptions} MapOptions */ +/** @typedef {import("webpack-sources").Source} Source */ +/** @typedef {import("../declarations/plugins/SourceMapDevToolPlugin").SourceMapDevToolPluginOptions} SourceMapDevToolPluginOptions */ +/** @typedef {import("./Cache").Etag} Etag */ +/** @typedef {import("./CacheFacade").ItemCacheFacade} ItemCacheFacade */ +/** @typedef {import("./Chunk")} Chunk */ +/** @typedef {import("./Compilation").AssetInfo} AssetInfo */ +/** @typedef {import("./Compiler")} Compiler */ +/** @typedef {import("./Module")} Module */ +/** @typedef {import("./NormalModule").SourceMap} SourceMap */ +/** @typedef {import("./util/Hash")} Hash */ - deserialize({ read }) { - this.version = read(); - this.buildSnapshot = read(); - this.buildDependencies = read(); - this.resolveResults = read(); - this.resolveBuildDependenciesSnapshot = read(); - this.data = read(); +const validate = createSchemaValidation( + __webpack_require__(27084), + () => __webpack_require__(95228), + { + name: "SourceMap DevTool Plugin", + baseDataPath: "options" } -} - -makeSerializable( - PackContainer, - "webpack/lib/cache/PackFileCacheStrategy", - "PackContainer" ); +/** + * @typedef {object} SourceMapTask + * @property {Source} asset + * @property {AssetInfo} assetInfo + * @property {(string | Module)[]} modules + * @property {string} source + * @property {string} file + * @property {SourceMap} sourceMap + * @property {ItemCacheFacade} cacheItem cache item + */ -const MIN_CONTENT_SIZE = 1024 * 1024; // 1 MB -const CONTENT_COUNT_TO_MERGE = 10; -const MIN_ITEMS_IN_FRESH_PACK = 100; -const MAX_ITEMS_IN_FRESH_PACK = 50000; -const MAX_TIME_IN_FRESH_PACK = 1 * 60 * 1000; // 1 min +/** + * Escapes regular expression metacharacters + * @param {string} str String to quote + * @returns {string} Escaped string + */ +const quoteMeta = str => { + return str.replace(/[-[\]\\/{}()*+?.^$|]/g, "\\$&"); +}; -class PackItemInfo { +/** + * Creating {@link SourceMapTask} for given file + * @param {string} file current compiled file + * @param {Source} asset the asset + * @param {AssetInfo} assetInfo the asset info + * @param {MapOptions} options source map options + * @param {Compilation} compilation compilation instance + * @param {ItemCacheFacade} cacheItem cache item + * @returns {SourceMapTask | undefined} created task instance or `undefined` + */ +const getTaskForFile = ( + file, + asset, + assetInfo, + options, + compilation, + cacheItem +) => { + let source; + /** @type {SourceMap} */ + let sourceMap; /** - * @param {string} identifier identifier of item - * @param {string | null} etag etag of item - * @param {any} value fresh value of item + * Check if asset can build source map */ - constructor(identifier, etag, value) { - this.identifier = identifier; - this.etag = etag; - this.location = -1; - this.lastAccess = Date.now(); - this.freshValue = value; - } -} - -class Pack { - constructor(logger, maxAge) { - /** @type {Map} */ - this.itemInfo = new Map(); - /** @type {string[]} */ - this.requests = []; - this.requestsTimeout = undefined; - /** @type {Map} */ - this.freshContent = new Map(); - /** @type {(undefined | PackContent)[]} */ - this.content = []; - this.invalid = false; - this.logger = logger; - this.maxAge = maxAge; - } - - _addRequest(identifier) { - this.requests.push(identifier); - if (this.requestsTimeout === undefined) { - this.requestsTimeout = setTimeout(() => { - this.requests.push(undefined); - this.requestsTimeout = undefined; - }, MAX_TIME_IN_FRESH_PACK); - if (this.requestsTimeout.unref) this.requestsTimeout.unref(); - } - } - - stopCapturingRequests() { - if (this.requestsTimeout !== undefined) { - clearTimeout(this.requestsTimeout); - this.requestsTimeout = undefined; - } + if (asset.sourceAndMap) { + const sourceAndMap = asset.sourceAndMap(options); + sourceMap = /** @type {SourceMap} */ (sourceAndMap.map); + source = sourceAndMap.source; + } else { + sourceMap = /** @type {SourceMap} */ (asset.map(options)); + source = asset.source(); } + if (!sourceMap || typeof source !== "string") return; + const context = compilation.options.context; + const root = compilation.compiler.root; + const cachedAbsolutify = makePathsAbsolute.bindContextCache(context, root); + const modules = sourceMap.sources.map(source => { + if (!source.startsWith("webpack://")) return source; + source = cachedAbsolutify(source.slice(10)); + const module = compilation.findModule(source); + return module || source; + }); - /** - * @param {string} identifier unique name for the resource - * @param {string | null} etag etag of the resource - * @returns {any} cached content - */ - get(identifier, etag) { - const info = this.itemInfo.get(identifier); - this._addRequest(identifier); - if (info === undefined) { - return undefined; - } - if (info.etag !== etag) return null; - info.lastAccess = Date.now(); - const loc = info.location; - if (loc === -1) { - return info.freshValue; - } else { - if (!this.content[loc]) { - return undefined; - } - return this.content[loc].get(identifier); - } - } + return { + file, + asset, + source, + assetInfo, + sourceMap, + modules, + cacheItem + }; +}; +class SourceMapDevToolPlugin { /** - * @param {string} identifier unique name for the resource - * @param {string | null} etag etag of the resource - * @param {any} data cached content - * @returns {void} + * @param {SourceMapDevToolPluginOptions} [options] options object + * @throws {Error} throws error, if got more than 1 arguments */ - set(identifier, etag, data) { - if (!this.invalid) { - this.invalid = true; - this.logger.log(`Pack got invalid because of write to: ${identifier}`); - } - const info = this.itemInfo.get(identifier); - if (info === undefined) { - const newInfo = new PackItemInfo(identifier, etag, data); - this.itemInfo.set(identifier, newInfo); - this._addRequest(identifier); - this.freshContent.set(identifier, newInfo); - } else { - const loc = info.location; - if (loc >= 0) { - this._addRequest(identifier); - this.freshContent.set(identifier, info); - const content = this.content[loc]; - content.delete(identifier); - if (content.items.size === 0) { - this.content[loc] = undefined; - this.logger.debug("Pack %d got empty and is removed", loc); - } - } - info.freshValue = data; - info.lastAccess = Date.now(); - info.etag = etag; - info.location = -1; - } - } + constructor(options = {}) { + validate(options); - getContentStats() { - let count = 0; - let size = 0; - for (const content of this.content) { - if (content !== undefined) { - count++; - const s = content.getSize(); - if (s > 0) { - size += s; - } - } - } - return { count, size }; + /** @type {string | false} */ + this.sourceMapFilename = options.filename; + /** @type {string | false} */ + this.sourceMappingURLComment = + options.append === false + ? false + : options.append || "\n//# source" + "MappingURL=[url]"; + /** @type {string | Function} */ + this.moduleFilenameTemplate = + options.moduleFilenameTemplate || "webpack://[namespace]/[resourcePath]"; + /** @type {string | Function} */ + this.fallbackModuleFilenameTemplate = + options.fallbackModuleFilenameTemplate || + "webpack://[namespace]/[resourcePath]?[hash]"; + /** @type {string} */ + this.namespace = options.namespace || ""; + /** @type {SourceMapDevToolPluginOptions} */ + this.options = options; } /** - * @returns {number} new location of data entries + * Apply the plugin + * @param {Compiler} compiler compiler instance + * @returns {void} */ - _findLocation() { - let i; - for (i = 0; i < this.content.length && this.content[i] !== undefined; i++); - return i; - } + apply(compiler) { + const outputFs = compiler.outputFileSystem; + const sourceMapFilename = this.sourceMapFilename; + const sourceMappingURLComment = this.sourceMappingURLComment; + const moduleFilenameTemplate = this.moduleFilenameTemplate; + const namespace = this.namespace; + const fallbackModuleFilenameTemplate = this.fallbackModuleFilenameTemplate; + const requestShortener = compiler.requestShortener; + const options = this.options; + options.test = options.test || /\.((c|m)?js|css)($|\?)/i; - _gcAndUpdateLocation(items, usedItems, newLoc) { - let count = 0; - let lastGC; - const now = Date.now(); - for (const identifier of items) { - const info = this.itemInfo.get(identifier); - if (now - info.lastAccess > this.maxAge) { - this.itemInfo.delete(identifier); - items.delete(identifier); - usedItems.delete(identifier); - count++; - lastGC = identifier; - } else { - info.location = newLoc; - } - } - if (count > 0) { - this.logger.log( - "Garbage Collected %d old items at pack %d (%d items remaining) e. g. %s", - count, - newLoc, - items.size, - lastGC - ); - } - } + const matchObject = ModuleFilenameHelpers.matchObject.bind( + undefined, + options + ); - _persistFreshContent() { - const itemsCount = this.freshContent.size; - if (itemsCount > 0) { - const packCount = Math.ceil(itemsCount / MAX_ITEMS_IN_FRESH_PACK); - const itemsPerPack = Math.ceil(itemsCount / packCount); - const packs = []; - let i = 0; - let ignoreNextTimeTick = false; - const createNextPack = () => { - const loc = this._findLocation(); - this.content[loc] = null; // reserve - const pack = { - /** @type {Set} */ - items: new Set(), - /** @type {Map} */ - map: new Map(), - loc - }; - packs.push(pack); - return pack; - }; - let pack = createNextPack(); - if (this.requestsTimeout !== undefined) - clearTimeout(this.requestsTimeout); - for (const identifier of this.requests) { - if (identifier === undefined) { - if (ignoreNextTimeTick) { - ignoreNextTimeTick = false; - } else if (pack.items.size >= MIN_ITEMS_IN_FRESH_PACK) { - i = 0; - pack = createNextPack(); + compiler.hooks.compilation.tap("SourceMapDevToolPlugin", compilation => { + new SourceMapDevToolModuleOptionsPlugin(options).apply(compilation); + + compilation.hooks.processAssets.tapAsync( + { + name: "SourceMapDevToolPlugin", + stage: Compilation.PROCESS_ASSETS_STAGE_DEV_TOOLING, + additionalAssets: true + }, + (assets, callback) => { + const chunkGraph = compilation.chunkGraph; + const cache = compilation.getCache("SourceMapDevToolPlugin"); + /** @type {Map} */ + const moduleToSourceNameMapping = new Map(); + /** + * @type {Function} + * @returns {void} + */ + const reportProgress = + ProgressPlugin.getReporter(compilation.compiler) || (() => {}); + + /** @type {Map} */ + const fileToChunk = new Map(); + for (const chunk of compilation.chunks) { + for (const file of chunk.files) { + fileToChunk.set(file, chunk); + } + for (const file of chunk.auxiliaryFiles) { + fileToChunk.set(file, chunk); + } } - continue; - } - const info = this.freshContent.get(identifier); - if (info === undefined) continue; - pack.items.add(identifier); - pack.map.set(identifier, info.freshValue); - info.location = pack.loc; - info.freshValue = undefined; - this.freshContent.delete(identifier); - if (++i > itemsPerPack) { - i = 0; - pack = createNextPack(); - ignoreNextTimeTick = true; - } - } - this.requests.length = 0; - for (const pack of packs) { - this.content[pack.loc] = new PackContent( - pack.items, - new Set(pack.items), - new PackContentItems(pack.map) - ); - } - this.logger.log( - `${itemsCount} fresh items in cache put into pack ${ - packs.length > 1 - ? packs - .map(pack => `${pack.loc} (${pack.items.size} items)`) - .join(", ") - : packs[0].loc - }` - ); - } - } - /** - * Merges small content files to a single content file - */ - _optimizeSmallContent() { - // 1. Find all small content files - // Treat unused content files separately to avoid - // a merge-split cycle - /** @type {number[]} */ - const smallUsedContents = []; - /** @type {number} */ - let smallUsedContentSize = 0; - /** @type {number[]} */ - const smallUnusedContents = []; - /** @type {number} */ - let smallUnusedContentSize = 0; - for (let i = 0; i < this.content.length; i++) { - const content = this.content[i]; - if (content === undefined) continue; - if (content.outdated) continue; - const size = content.getSize(); - if (size < 0 || size > MIN_CONTENT_SIZE) continue; - if (content.used.size > 0) { - smallUsedContents.push(i); - smallUsedContentSize += size; - } else { - smallUnusedContents.push(i); - smallUnusedContentSize += size; - } - } + /** @type {string[]} */ + const files = []; + for (const file of Object.keys(assets)) { + if (matchObject(file)) { + files.push(file); + } + } - // 2. Check if minimum number is reached - let mergedIndices; - if ( - smallUsedContents.length >= CONTENT_COUNT_TO_MERGE || - smallUsedContentSize > MIN_CONTENT_SIZE - ) { - mergedIndices = smallUsedContents; - } else if ( - smallUnusedContents.length >= CONTENT_COUNT_TO_MERGE || - smallUnusedContentSize > MIN_CONTENT_SIZE - ) { - mergedIndices = smallUnusedContents; - } else return; + reportProgress(0.0); + /** @type {SourceMapTask[]} */ + const tasks = []; + let fileIndex = 0; - const mergedContent = []; + asyncLib.each( + files, + (file, callback) => { + const asset = compilation.getAsset(file); + if (asset.info.related && asset.info.related.sourceMap) { + fileIndex++; + return callback(); + } + const cacheItem = cache.getItemCache( + file, + cache.mergeEtags( + cache.getLazyHashedEtag(asset.source), + namespace + ) + ); - // 3. Remove old content entries - for (const i of mergedIndices) { - mergedContent.push(this.content[i]); - this.content[i] = undefined; - } + cacheItem.get((err, cacheEntry) => { + if (err) { + return callback(err); + } + /** + * If presented in cache, reassigns assets. Cache assets already have source maps. + */ + if (cacheEntry) { + const { assets, assetsInfo } = cacheEntry; + for (const cachedFile of Object.keys(assets)) { + if (cachedFile === file) { + compilation.updateAsset( + cachedFile, + assets[cachedFile], + assetsInfo[cachedFile] + ); + } else { + compilation.emitAsset( + cachedFile, + assets[cachedFile], + assetsInfo[cachedFile] + ); + } + /** + * Add file to chunk, if not presented there + */ + if (cachedFile !== file) { + const chunk = fileToChunk.get(file); + if (chunk !== undefined) + chunk.auxiliaryFiles.add(cachedFile); + } + } - // 4. Determine merged items - /** @type {Set} */ - const mergedItems = new Set(); - /** @type {Set} */ - const mergedUsedItems = new Set(); - /** @type {(function(Map): Promise)[]} */ - const addToMergedMap = []; - for (const content of mergedContent) { - for (const identifier of content.items) { - mergedItems.add(identifier); - } - for (const identifier of content.used) { - mergedUsedItems.add(identifier); - } - addToMergedMap.push(async map => { - // unpack existing content - // after that values are accessible in .content - await content.unpack( - "it should be merged with other small pack contents" - ); - for (const [identifier, value] of content.content) { - map.set(identifier, value); - } - }); - } + reportProgress( + (0.5 * ++fileIndex) / files.length, + file, + "restored cached SourceMap" + ); - // 5. GC and update location of merged items - const newLoc = this._findLocation(); - this._gcAndUpdateLocation(mergedItems, mergedUsedItems, newLoc); + return callback(); + } - // 6. If not empty, store content somewhere - if (mergedItems.size > 0) { - this.content[newLoc] = new PackContent( - mergedItems, - mergedUsedItems, - memoize(async () => { - /** @type {Map} */ - const map = new Map(); - await Promise.all(addToMergedMap.map(fn => fn(map))); - return new PackContentItems(map); - }) - ); - this.logger.log( - "Merged %d small files with %d cache items into pack %d", - mergedContent.length, - mergedItems.size, - newLoc - ); - } - } + reportProgress( + (0.5 * fileIndex) / files.length, + file, + "generate SourceMap" + ); - /** - * Split large content files with used and unused items - * into two parts to separate used from unused items - */ - _optimizeUnusedContent() { - // 1. Find a large content file with used and unused items - for (let i = 0; i < this.content.length; i++) { - const content = this.content[i]; - if (content === undefined) continue; - const size = content.getSize(); - if (size < MIN_CONTENT_SIZE) continue; - const used = content.used.size; - const total = content.items.size; - if (used > 0 && used < total) { - // 2. Remove this content - this.content[i] = undefined; + /** @type {SourceMapTask | undefined} */ + const task = getTaskForFile( + file, + asset.source, + asset.info, + { + module: options.module, + columns: options.columns + }, + compilation, + cacheItem + ); - // 3. Determine items for the used content file - const usedItems = new Set(content.used); - const newLoc = this._findLocation(); - this._gcAndUpdateLocation(usedItems, usedItems, newLoc); + if (task) { + const modules = task.modules; - // 4. Create content file for used items - if (usedItems.size > 0) { - this.content[newLoc] = new PackContent( - usedItems, - new Set(usedItems), - async () => { - await content.unpack( - "it should be splitted into used and unused items" - ); - const map = new Map(); - for (const identifier of usedItems) { - map.set(identifier, content.content.get(identifier)); + for (let idx = 0; idx < modules.length; idx++) { + const module = modules[idx]; + if (!moduleToSourceNameMapping.get(module)) { + moduleToSourceNameMapping.set( + module, + ModuleFilenameHelpers.createFilename( + module, + { + moduleFilenameTemplate: moduleFilenameTemplate, + namespace: namespace + }, + { + requestShortener, + chunkGraph, + hashFunction: compilation.outputOptions.hashFunction + } + ) + ); + } + } + + tasks.push(task); + } + + reportProgress( + (0.5 * ++fileIndex) / files.length, + file, + "generated SourceMap" + ); + + callback(); + }); + }, + err => { + if (err) { + return callback(err); } - return new PackContentItems(map); - } - ); - } - // 5. Determine items for the unused content file - const unusedItems = new Set(content.items); - const usedOfUnusedItems = new Set(); - for (const identifier of usedItems) { - unusedItems.delete(identifier); - } - const newUnusedLoc = this._findLocation(); - this._gcAndUpdateLocation(unusedItems, usedOfUnusedItems, newUnusedLoc); + reportProgress(0.5, "resolve sources"); + /** @type {Set} */ + const usedNamesSet = new Set(moduleToSourceNameMapping.values()); + /** @type {Set} */ + const conflictDetectionSet = new Set(); - // 6. Create content file for unused items - if (unusedItems.size > 0) { - this.content[newUnusedLoc] = new PackContent( - unusedItems, - usedOfUnusedItems, - async () => { - await content.unpack( - "it should be splitted into used and unused items" - ); - const map = new Map(); - for (const identifier of unusedItems) { - map.set(identifier, content.content.get(identifier)); + /** + * all modules in defined order (longest identifier first) + * @type {Array} + */ + const allModules = Array.from( + moduleToSourceNameMapping.keys() + ).sort((a, b) => { + const ai = typeof a === "string" ? a : a.identifier(); + const bi = typeof b === "string" ? b : b.identifier(); + return ai.length - bi.length; + }); + + // find modules with conflicting source names + for (let idx = 0; idx < allModules.length; idx++) { + const module = allModules[idx]; + let sourceName = moduleToSourceNameMapping.get(module); + let hasName = conflictDetectionSet.has(sourceName); + if (!hasName) { + conflictDetectionSet.add(sourceName); + continue; + } + + // try the fallback name first + sourceName = ModuleFilenameHelpers.createFilename( + module, + { + moduleFilenameTemplate: fallbackModuleFilenameTemplate, + namespace: namespace + }, + { + requestShortener, + chunkGraph, + hashFunction: compilation.outputOptions.hashFunction + } + ); + hasName = usedNamesSet.has(sourceName); + if (!hasName) { + moduleToSourceNameMapping.set(module, sourceName); + usedNamesSet.add(sourceName); + continue; + } + + // otherwise just append stars until we have a valid name + while (hasName) { + sourceName += "*"; + hasName = usedNamesSet.has(sourceName); + } + moduleToSourceNameMapping.set(module, sourceName); + usedNamesSet.add(sourceName); } - return new PackContentItems(map); - } - ); - } - this.logger.log( - "Split pack %d into pack %d with %d used items and pack %d with %d unused items", - i, - newLoc, - usedItems.size, - newUnusedLoc, - unusedItems.size - ); + let taskIndex = 0; + + asyncLib.each( + tasks, + (task, callback) => { + const assets = Object.create(null); + const assetsInfo = Object.create(null); + const file = task.file; + const chunk = fileToChunk.get(file); + const sourceMap = task.sourceMap; + const source = task.source; + const modules = task.modules; - // optimizing only one of them is good enough and - // reduces the amount of serialization needed - return; - } - } - } + reportProgress( + 0.5 + (0.5 * taskIndex) / tasks.length, + file, + "attach SourceMap" + ); - /** - * Find the content with the oldest item and run GC on that. - * Only runs for one content to avoid large invalidation. - */ - _gcOldestContent() { - /** @type {PackItemInfo} */ - let oldest = undefined; - for (const info of this.itemInfo.values()) { - if (oldest === undefined || info.lastAccess < oldest.lastAccess) { - oldest = info; - } - } - if (Date.now() - oldest.lastAccess > this.maxAge) { - const loc = oldest.location; - if (loc < 0) return; - const content = this.content[loc]; - const items = new Set(content.items); - const usedItems = new Set(content.used); - this._gcAndUpdateLocation(items, usedItems, loc); + const moduleFilenames = modules.map(m => + moduleToSourceNameMapping.get(m) + ); + sourceMap.sources = moduleFilenames; + if (options.noSources) { + sourceMap.sourcesContent = undefined; + } + sourceMap.sourceRoot = options.sourceRoot || ""; + sourceMap.file = file; + const usesContentHash = + sourceMapFilename && + /\[contenthash(:\w+)?\]/.test(sourceMapFilename); - this.content[loc] = - items.size > 0 - ? new PackContent(items, usedItems, async () => { - await content.unpack( - "it contains old items that should be garbage collected" - ); - const map = new Map(); - for (const identifier of items) { - map.set(identifier, content.content.get(identifier)); - } - return new PackContentItems(map); - }) - : undefined; - } - } + // If SourceMap and asset uses contenthash, avoid a circular dependency by hiding hash in `file` + if (usesContentHash && task.assetInfo.contenthash) { + const contenthash = task.assetInfo.contenthash; + let pattern; + if (Array.isArray(contenthash)) { + pattern = contenthash.map(quoteMeta).join("|"); + } else { + pattern = quoteMeta(contenthash); + } + sourceMap.file = sourceMap.file.replace( + new RegExp(pattern, "g"), + m => "x".repeat(m.length) + ); + } - serialize({ write, writeSeparate }) { - this._persistFreshContent(); - this._optimizeSmallContent(); - this._optimizeUnusedContent(); - this._gcOldestContent(); - for (const identifier of this.itemInfo.keys()) { - write(identifier); - } - write(null); // null as marker of the end of keys - for (const info of this.itemInfo.values()) { - write(info.etag); - } - for (const info of this.itemInfo.values()) { - write(info.lastAccess); - } - for (let i = 0; i < this.content.length; i++) { - const content = this.content[i]; - if (content !== undefined) { - write(content.items); - content.writeLazy(lazy => writeSeparate(lazy, { name: `${i}` })); - } else { - write(undefined); // undefined marks an empty content slot - } - } - write(null); // null as marker of the end of items - } + /** @type {string | false} */ + let currentSourceMappingURLComment = sourceMappingURLComment; + if ( + currentSourceMappingURLComment !== false && + /\.css($|\?)/i.test(file) + ) { + currentSourceMappingURLComment = + currentSourceMappingURLComment.replace( + /^\n\/\/(.*)$/, + "\n/*$1*/" + ); + } + const sourceMapString = JSON.stringify(sourceMap); + if (sourceMapFilename) { + let filename = file; + const sourceMapContentHash = + usesContentHash && + /** @type {string} */ ( + createHash(compilation.outputOptions.hashFunction) + .update(sourceMapString) + .digest("hex") + ); + const pathParams = { + chunk, + filename: options.fileContext + ? relative( + outputFs, + `/${options.fileContext}`, + `/${filename}` + ) + : filename, + contentHash: sourceMapContentHash + }; + const { path: sourceMapFile, info: sourceMapInfo } = + compilation.getPathWithInfo( + sourceMapFilename, + pathParams + ); + const sourceMapUrl = options.publicPath + ? options.publicPath + sourceMapFile + : relative( + outputFs, + dirname(outputFs, `/${file}`), + `/${sourceMapFile}` + ); + /** @type {Source} */ + let asset = new RawSource(source); + if (currentSourceMappingURLComment !== false) { + // Add source map url to compilation asset, if currentSourceMappingURLComment is set + asset = new ConcatSource( + asset, + compilation.getPath( + currentSourceMappingURLComment, + Object.assign({ url: sourceMapUrl }, pathParams) + ) + ); + } + const assetInfo = { + related: { sourceMap: sourceMapFile } + }; + assets[file] = asset; + assetsInfo[file] = assetInfo; + compilation.updateAsset(file, asset, assetInfo); + // Add source map file to compilation assets and chunk files + const sourceMapAsset = new RawSource(sourceMapString); + const sourceMapAssetInfo = { + ...sourceMapInfo, + development: true + }; + assets[sourceMapFile] = sourceMapAsset; + assetsInfo[sourceMapFile] = sourceMapAssetInfo; + compilation.emitAsset( + sourceMapFile, + sourceMapAsset, + sourceMapAssetInfo + ); + if (chunk !== undefined) + chunk.auxiliaryFiles.add(sourceMapFile); + } else { + if (currentSourceMappingURLComment === false) { + throw new Error( + "SourceMapDevToolPlugin: append can't be false when no filename is provided" + ); + } + /** + * Add source map as data url to asset + */ + const asset = new ConcatSource( + new RawSource(source), + currentSourceMappingURLComment + .replace(/\[map\]/g, () => sourceMapString) + .replace( + /\[url\]/g, + () => + `data:application/json;charset=utf-8;base64,${Buffer.from( + sourceMapString, + "utf-8" + ).toString("base64")}` + ) + ); + assets[file] = asset; + assetsInfo[file] = undefined; + compilation.updateAsset(file, asset); + } - deserialize({ read, logger }) { - this.logger = logger; - { - const items = []; - let item = read(); - while (item !== null) { - items.push(item); - item = read(); - } - this.itemInfo.clear(); - const infoItems = items.map(identifier => { - const info = new PackItemInfo(identifier, undefined, undefined); - this.itemInfo.set(identifier, info); - return info; - }); - for (const info of infoItems) { - info.etag = read(); - } - for (const info of infoItems) { - info.lastAccess = read(); - } - } - this.content.length = 0; - let items = read(); - while (items !== null) { - if (items === undefined) { - this.content.push(items); - } else { - const idx = this.content.length; - const lazy = read(); - this.content.push( - new PackContent( - items, - new Set(), - lazy, - logger, - `${this.content.length}` - ) - ); - for (const identifier of items) { - this.itemInfo.get(identifier).location = idx; + task.cacheItem.store({ assets, assetsInfo }, err => { + reportProgress( + 0.5 + (0.5 * ++taskIndex) / tasks.length, + task.file, + "attached SourceMap" + ); + + if (err) { + return callback(err); + } + callback(); + }); + }, + err => { + reportProgress(1.0); + callback(err); + } + ); + } + ); } - } - items = read(); - } + ); + }); } } -makeSerializable(Pack, "webpack/lib/cache/PackFileCacheStrategy", "Pack"); +module.exports = SourceMapDevToolPlugin; -class PackContentItems { - /** - * @param {Map} map items - */ - constructor(map) { - this.map = map; - } - serialize({ write, snapshot, rollback, logger, profile }) { - if (profile) { - write(false); - for (const [key, value] of this.map) { - const s = snapshot(); - try { - write(key); - const start = process.hrtime(); - write(value); - const durationHr = process.hrtime(start); - const duration = durationHr[0] * 1000 + durationHr[1] / 1e6; - if (duration > 1) { - if (duration > 500) - logger.error(`Serialization of '${key}': ${duration} ms`); - else if (duration > 50) - logger.warn(`Serialization of '${key}': ${duration} ms`); - else if (duration > 10) - logger.info(`Serialization of '${key}': ${duration} ms`); - else if (duration > 5) - logger.log(`Serialization of '${key}': ${duration} ms`); - else logger.debug(`Serialization of '${key}': ${duration} ms`); - } - } catch (e) { - rollback(s); - if (e === NOT_SERIALIZABLE) continue; - logger.warn( - `Skipped not serializable cache item '${key}': ${e.message}` - ); - logger.debug(e.stack); - } - } - write(null); - return; - } - // Try to serialize all at once - const s = snapshot(); - try { - write(true); - write(this.map); - } catch (e) { - rollback(s); +/***/ }), - // Try to serialize each item on it's own - write(false); - for (const [key, value] of this.map) { - const s = snapshot(); - try { - write(key); - write(value); - } catch (e) { - rollback(s); - if (e === NOT_SERIALIZABLE) continue; - logger.warn( - `Skipped not serializable cache item '${key}': ${e.message}` - ); - logger.debug(e.stack); - } - } - write(null); - } - } +/***/ 87797: +/***/ (function(module) { - deserialize({ read, logger, profile }) { - if (read()) { - this.map = read(); - } else if (profile) { - const map = new Map(); - let key = read(); - while (key !== null) { - const start = process.hrtime(); - const value = read(); - const durationHr = process.hrtime(start); - const duration = durationHr[0] * 1000 + durationHr[1] / 1e6; - if (duration > 1) { - if (duration > 100) - logger.error(`Deserialization of '${key}': ${duration} ms`); - else if (duration > 20) - logger.warn(`Deserialization of '${key}': ${duration} ms`); - else if (duration > 5) - logger.info(`Deserialization of '${key}': ${duration} ms`); - else if (duration > 2) - logger.log(`Deserialization of '${key}': ${duration} ms`); - else logger.debug(`Deserialization of '${key}': ${duration} ms`); - } - map.set(key, value); - key = read(); - } - this.map = map; - } else { - const map = new Map(); - let key = read(); - while (key !== null) { - map.set(key, read()); - key = read(); - } - this.map = map; - } - } -} +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ -makeSerializable( - PackContentItems, - "webpack/lib/cache/PackFileCacheStrategy", - "PackContentItems" -); -class PackContent { - /* - This class can be in these states: - | this.lazy | this.content | this.outdated | state - A1 | undefined | Map | false | fresh content - A2 | undefined | Map | true | (will not happen) - B1 | lazy () => {} | undefined | false | not deserialized - B2 | lazy () => {} | undefined | true | not deserialized, but some items has been removed - C1 | lazy* () => {} | Map | false | deserialized - C2 | lazy* () => {} | Map | true | deserialized, and some items has been removed - this.used is a subset of this.items. - this.items is a subset of this.content.keys() resp. this.lazy().map.keys() - When this.outdated === false, this.items === this.content.keys() resp. this.lazy().map.keys() - When this.outdated === true, this.items should be used to recreated this.lazy/this.content. - When this.lazy and this.content is set, they contain the same data. - this.get must only be called with a valid item from this.items. - In state C this.lazy is unMemoized - */ +/** @typedef {import("../declarations/WebpackOptions").StatsOptions} StatsOptions */ +/** @typedef {import("./Compilation")} Compilation */ +/** @typedef {import("./stats/DefaultStatsFactoryPlugin").StatsCompilation} StatsCompilation */ +class Stats { /** - * @param {Set} items keys - * @param {Set} usedItems used keys - * @param {PackContentItems | function(): Promise} dataOrFn sync or async content - * @param {Logger=} logger logger for logging - * @param {string=} lazyName name of dataOrFn for logging + * @param {Compilation} compilation webpack compilation */ - constructor(items, usedItems, dataOrFn, logger, lazyName) { - this.items = items; - /** @type {function(): Promise | PackContentItems} */ - this.lazy = typeof dataOrFn === "function" ? dataOrFn : undefined; - /** @type {Map} */ - this.content = typeof dataOrFn === "function" ? undefined : dataOrFn.map; - this.outdated = false; - this.used = usedItems; - this.logger = logger; - this.lazyName = lazyName; + constructor(compilation) { + this.compilation = compilation; } - get(identifier) { - this.used.add(identifier); - if (this.content) { - return this.content.get(identifier); - } - - // We are in state B - const { lazyName } = this; - let timeMessage; - if (lazyName) { - // only log once - this.lazyName = undefined; - timeMessage = `restore cache content ${lazyName} (${formatSize( - this.getSize() - )})`; - this.logger.log( - `starting to restore cache content ${lazyName} (${formatSize( - this.getSize() - )}) because of request to: ${identifier}` - ); - this.logger.time(timeMessage); - } - const value = this.lazy(); - if ("then" in value) { - return value.then(data => { - const map = data.map; - if (timeMessage) { - this.logger.timeEnd(timeMessage); - } - // Move to state C - this.content = map; - this.lazy = SerializerMiddleware.unMemoizeLazy(this.lazy); - return map.get(identifier); - }); - } else { - const map = value.map; - if (timeMessage) { - this.logger.timeEnd(timeMessage); - } - // Move to state C - this.content = map; - this.lazy = SerializerMiddleware.unMemoizeLazy(this.lazy); - return map.get(identifier); - } + get hash() { + return this.compilation.hash; } - /** - * @param {string} reason explanation why unpack is necessary - * @returns {void | Promise} maybe a promise if lazy - */ - unpack(reason) { - if (this.content) return; - - // Move from state B to C - if (this.lazy) { - const { lazyName } = this; - let timeMessage; - if (lazyName) { - // only log once - this.lazyName = undefined; - timeMessage = `unpack cache content ${lazyName} (${formatSize( - this.getSize() - )})`; - this.logger.log( - `starting to unpack cache content ${lazyName} (${formatSize( - this.getSize() - )}) because ${reason}` - ); - this.logger.time(timeMessage); - } - const value = this.lazy(); - if ("then" in value) { - return value.then(data => { - if (timeMessage) { - this.logger.timeEnd(timeMessage); - } - this.content = data.map; - }); - } else { - if (timeMessage) { - this.logger.timeEnd(timeMessage); - } - this.content = value.map; - } - } + get startTime() { + return this.compilation.startTime; + } + + get endTime() { + return this.compilation.endTime; } /** - * @returns {number} size of the content or -1 if not known + * @returns {boolean} true if the compilation had a warning */ - getSize() { - if (!this.lazy) return -1; - const options = /** @type {any} */ (this.lazy).options; - if (!options) return -1; - const size = options.size; - if (typeof size !== "number") return -1; - return size; + hasWarnings() { + return ( + this.compilation.warnings.length > 0 || + this.compilation.children.some(child => child.getStats().hasWarnings()) + ); } - delete(identifier) { - this.items.delete(identifier); - this.used.delete(identifier); - this.outdated = true; + /** + * @returns {boolean} true if the compilation encountered an error + */ + hasErrors() { + return ( + this.compilation.errors.length > 0 || + this.compilation.children.some(child => child.getStats().hasErrors()) + ); } /** - * @template T - * @param {function(any): function(): Promise | PackContentItems} write write function - * @returns {void} + * @param {(string|StatsOptions)=} options stats options + * @returns {StatsCompilation} json output */ - writeLazy(write) { - if (!this.outdated && this.lazy) { - // State B1 or C1 - // this.lazy is still the valid deserialized version - write(this.lazy); - return; - } - if (!this.outdated && this.content) { - // State A1 - const map = new Map(this.content); - // Move to state C1 - this.lazy = SerializerMiddleware.unMemoizeLazy( - write(() => new PackContentItems(map)) - ); - return; - } - if (this.content) { - // State A2 or C2 - /** @type {Map} */ - const map = new Map(); - for (const item of this.items) { - map.set(item, this.content.get(item)); - } - // Move to state C1 - this.outdated = false; - this.content = map; - this.lazy = SerializerMiddleware.unMemoizeLazy( - write(() => new PackContentItems(map)) - ); - return; - } - // State B2 - const { lazyName } = this; - let timeMessage; - if (lazyName) { - // only log once - this.lazyName = undefined; - timeMessage = `unpack cache content ${lazyName} (${formatSize( - this.getSize() - )})`; - this.logger.log( - `starting to unpack cache content ${lazyName} (${formatSize( - this.getSize() - )}) because it's outdated and need to be serialized` - ); - this.logger.time(timeMessage); - } - const value = this.lazy(); - this.outdated = false; - if ("then" in value) { - // Move to state B1 - this.lazy = write(() => - value.then(data => { - if (timeMessage) { - this.logger.timeEnd(timeMessage); - } - const oldMap = data.map; - /** @type {Map} */ - const map = new Map(); - for (const item of this.items) { - map.set(item, oldMap.get(item)); - } - // Move to state C1 (or maybe C2) - this.content = map; - this.lazy = SerializerMiddleware.unMemoizeLazy(this.lazy); + toJson(options) { + options = this.compilation.createStatsOptions(options, { + forToString: false + }); - return new PackContentItems(map); - }) - ); - } else { - // Move to state C1 - if (timeMessage) { - this.logger.timeEnd(timeMessage); - } - const oldMap = value.map; - /** @type {Map} */ - const map = new Map(); - for (const item of this.items) { - map.set(item, oldMap.get(item)); - } - this.content = map; - this.lazy = write(() => new PackContentItems(map)); - } + const statsFactory = this.compilation.createStatsFactory(options); + + return statsFactory.create("compilation", this.compilation, { + compilation: this.compilation + }); + } + + toString(options) { + options = this.compilation.createStatsOptions(options, { + forToString: true + }); + + const statsFactory = this.compilation.createStatsFactory(options); + const statsPrinter = this.compilation.createStatsPrinter(options); + + const data = statsFactory.create("compilation", this.compilation, { + compilation: this.compilation + }); + const result = statsPrinter.print("compilation", data); + return result === undefined ? "" : result; } } -const allowCollectingMemory = buf => { - const wasted = buf.buffer.byteLength - buf.byteLength; - if (wasted > 8192 && (wasted > 1048576 || wasted > buf.byteLength)) { - return Buffer.from(buf); +module.exports = Stats; + + +/***/ }), + +/***/ 92066: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ + + + +const { ConcatSource, PrefixSource } = __webpack_require__(96192); + +/** @typedef {import("webpack-sources").Source} Source */ +/** @typedef {import("../declarations/WebpackOptions").Output} OutputOptions */ +/** @typedef {import("./Chunk")} Chunk */ +/** @typedef {import("./ChunkGraph")} ChunkGraph */ +/** @typedef {import("./CodeGenerationResults")} CodeGenerationResults */ +/** @typedef {import("./Compilation").AssetInfo} AssetInfo */ +/** @typedef {import("./Compilation").PathData} PathData */ +/** @typedef {import("./DependencyTemplates")} DependencyTemplates */ +/** @typedef {import("./Module")} Module */ +/** @typedef {import("./ModuleGraph")} ModuleGraph */ +/** @typedef {import("./ModuleTemplate")} ModuleTemplate */ +/** @typedef {import("./RuntimeModule")} RuntimeModule */ +/** @typedef {import("./RuntimeTemplate")} RuntimeTemplate */ +/** @typedef {import("./javascript/JavascriptModulesPlugin").ChunkRenderContext} ChunkRenderContext */ +/** @typedef {import("./javascript/JavascriptModulesPlugin").RenderContext} RenderContext */ + +const START_LOWERCASE_ALPHABET_CODE = "a".charCodeAt(0); +const START_UPPERCASE_ALPHABET_CODE = "A".charCodeAt(0); +const DELTA_A_TO_Z = "z".charCodeAt(0) - START_LOWERCASE_ALPHABET_CODE + 1; +const NUMBER_OF_IDENTIFIER_START_CHARS = DELTA_A_TO_Z * 2 + 2; // a-z A-Z _ $ +const NUMBER_OF_IDENTIFIER_CONTINUATION_CHARS = + NUMBER_OF_IDENTIFIER_START_CHARS + 10; // a-z A-Z _ $ 0-9 +const FUNCTION_CONTENT_REGEX = /^function\s?\(\)\s?\{\r?\n?|\r?\n?\}$/g; +const INDENT_MULTILINE_REGEX = /^\t/gm; +const LINE_SEPARATOR_REGEX = /\r?\n/g; +const IDENTIFIER_NAME_REPLACE_REGEX = /^([^a-zA-Z$_])/; +const IDENTIFIER_ALPHA_NUMERIC_NAME_REPLACE_REGEX = /[^a-zA-Z0-9$]+/g; +const COMMENT_END_REGEX = /\*\//g; +const PATH_NAME_NORMALIZE_REPLACE_REGEX = /[^a-zA-Z0-9_!§$()=\-^°]+/g; +const MATCH_PADDED_HYPHENS_REPLACE_REGEX = /^-|-$/g; + +/** + * @typedef {Object} RenderManifestOptions + * @property {Chunk} chunk the chunk used to render + * @property {string} hash + * @property {string} fullHash + * @property {OutputOptions} outputOptions + * @property {CodeGenerationResults} codeGenerationResults + * @property {{javascript: ModuleTemplate}} moduleTemplates + * @property {DependencyTemplates} dependencyTemplates + * @property {RuntimeTemplate} runtimeTemplate + * @property {ModuleGraph} moduleGraph + * @property {ChunkGraph} chunkGraph + */ + +/** @typedef {RenderManifestEntryTemplated | RenderManifestEntryStatic} RenderManifestEntry */ + +/** + * @typedef {Object} RenderManifestEntryTemplated + * @property {function(): Source} render + * @property {string | function(PathData, AssetInfo=): string} filenameTemplate + * @property {PathData=} pathOptions + * @property {AssetInfo=} info + * @property {string} identifier + * @property {string=} hash + * @property {boolean=} auxiliary + */ + +/** + * @typedef {Object} RenderManifestEntryStatic + * @property {function(): Source} render + * @property {string} filename + * @property {AssetInfo} info + * @property {string} identifier + * @property {string=} hash + * @property {boolean=} auxiliary + */ + +/** + * @typedef {Object} HasId + * @property {number | string} id + */ + +/** + * @typedef {function(Module, number): boolean} ModuleFilterPredicate + */ + +class Template { + /** + * + * @param {Function} fn a runtime function (.runtime.js) "template" + * @returns {string} the updated and normalized function string + */ + static getFunctionContent(fn) { + return fn + .toString() + .replace(FUNCTION_CONTENT_REGEX, "") + .replace(INDENT_MULTILINE_REGEX, "") + .replace(LINE_SEPARATOR_REGEX, "\n"); } - return buf; -}; -class PackFileCacheStrategy { /** - * @param {Object} options options - * @param {Compiler} options.compiler the compiler - * @param {IntermediateFileSystem} options.fs the filesystem - * @param {string} options.context the context directory - * @param {string} options.cacheLocation the location of the cache data - * @param {string} options.version version identifier - * @param {Logger} options.logger a logger - * @param {SnapshotOptions} options.snapshot options regarding snapshotting - * @param {number} options.maxAge max age of cache items - * @param {boolean} options.profile track and log detailed timing information for individual cache items - * @param {boolean} options.allowCollectingMemory allow to collect unused memory created during deserialization - * @param {false | "gzip" | "brotli"} options.compression compression used + * @param {string} str the string converted to identifier + * @returns {string} created identifier */ - constructor({ - compiler, - fs, - context, - cacheLocation, - version, - logger, - snapshot, - maxAge, - profile, - allowCollectingMemory, - compression - }) { - this.fileSerializer = createFileSerializer( - fs, - compiler.options.output.hashFunction - ); - this.fileSystemInfo = new FileSystemInfo(fs, { - managedPaths: snapshot.managedPaths, - immutablePaths: snapshot.immutablePaths, - logger: logger.getChildLogger("webpack.FileSystemInfo"), - hashFunction: compiler.options.output.hashFunction - }); - this.compiler = compiler; - this.context = context; - this.cacheLocation = cacheLocation; - this.version = version; - this.logger = logger; - this.maxAge = maxAge; - this.profile = profile; - this.allowCollectingMemory = allowCollectingMemory; - this.compression = compression; - this._extension = - compression === "brotli" - ? ".pack.br" - : compression === "gzip" - ? ".pack.gz" - : ".pack"; - this.snapshot = snapshot; - /** @type {Set} */ - this.buildDependencies = new Set(); - /** @type {LazySet} */ - this.newBuildDependencies = new LazySet(); - /** @type {Snapshot} */ - this.resolveBuildDependenciesSnapshot = undefined; - /** @type {Map} */ - this.resolveResults = undefined; - /** @type {Snapshot} */ - this.buildSnapshot = undefined; - /** @type {Promise} */ - this.packPromise = this._openPack(); - this.storePromise = Promise.resolve(); + static toIdentifier(str) { + if (typeof str !== "string") return ""; + return str + .replace(IDENTIFIER_NAME_REPLACE_REGEX, "_$1") + .replace(IDENTIFIER_ALPHA_NUMERIC_NAME_REPLACE_REGEX, "_"); + } + /** + * + * @param {string} str string to be converted to commented in bundle code + * @returns {string} returns a commented version of string + */ + static toComment(str) { + if (!str) return ""; + return `/*! ${str.replace(COMMENT_END_REGEX, "* /")} */`; } - _getPack() { - if (this.packPromise === undefined) { - this.packPromise = this.storePromise.then(() => this._openPack()); - } - return this.packPromise; + /** + * + * @param {string} str string to be converted to "normal comment" + * @returns {string} returns a commented version of string + */ + static toNormalComment(str) { + if (!str) return ""; + return `/* ${str.replace(COMMENT_END_REGEX, "* /")} */`; } /** - * @returns {Promise} the pack + * @param {string} str string path to be normalized + * @returns {string} normalized bundle-safe path */ - _openPack() { - const { logger, profile, cacheLocation, version } = this; - /** @type {Snapshot} */ - let buildSnapshot; - /** @type {Set} */ - let buildDependencies; - /** @type {Set} */ - let newBuildDependencies; - /** @type {Snapshot} */ - let resolveBuildDependenciesSnapshot; - /** @type {Map} */ - let resolveResults; - logger.time("restore cache container"); - return this.fileSerializer - .deserialize(null, { - filename: `${cacheLocation}/index${this._extension}`, - extension: `${this._extension}`, - logger, - profile, - retainedBuffer: this.allowCollectingMemory - ? allowCollectingMemory - : undefined - }) - .catch(err => { - if (err.code !== "ENOENT") { - logger.warn( - `Restoring pack failed from ${cacheLocation}${this._extension}: ${err}` - ); - logger.debug(err.stack); - } else { - logger.debug( - `No pack exists at ${cacheLocation}${this._extension}: ${err}` - ); - } - return undefined; - }) - .then(packContainer => { - logger.timeEnd("restore cache container"); - if (!packContainer) return undefined; - if (!(packContainer instanceof PackContainer)) { - logger.warn( - `Restored pack from ${cacheLocation}${this._extension}, but contained content is unexpected.`, - packContainer - ); - return undefined; - } - if (packContainer.version !== version) { - logger.log( - `Restored pack from ${cacheLocation}${this._extension}, but version doesn't match.` - ); - return undefined; - } - logger.time("check build dependencies"); - return Promise.all([ - new Promise((resolve, reject) => { - this.fileSystemInfo.checkSnapshotValid( - packContainer.buildSnapshot, - (err, valid) => { - if (err) { - logger.log( - `Restored pack from ${cacheLocation}${this._extension}, but checking snapshot of build dependencies errored: ${err}.` - ); - logger.debug(err.stack); - return resolve(false); - } - if (!valid) { - logger.log( - `Restored pack from ${cacheLocation}${this._extension}, but build dependencies have changed.` - ); - return resolve(false); - } - buildSnapshot = packContainer.buildSnapshot; - return resolve(true); - } - ); - }), - new Promise((resolve, reject) => { - this.fileSystemInfo.checkSnapshotValid( - packContainer.resolveBuildDependenciesSnapshot, - (err, valid) => { - if (err) { - logger.log( - `Restored pack from ${cacheLocation}${this._extension}, but checking snapshot of resolving of build dependencies errored: ${err}.` - ); - logger.debug(err.stack); - return resolve(false); - } - if (valid) { - resolveBuildDependenciesSnapshot = - packContainer.resolveBuildDependenciesSnapshot; - buildDependencies = packContainer.buildDependencies; - resolveResults = packContainer.resolveResults; - return resolve(true); - } - logger.log( - "resolving of build dependencies is invalid, will re-resolve build dependencies" - ); - this.fileSystemInfo.checkResolveResultsValid( - packContainer.resolveResults, - (err, valid) => { - if (err) { - logger.log( - `Restored pack from ${cacheLocation}${this._extension}, but resolving of build dependencies errored: ${err}.` - ); - logger.debug(err.stack); - return resolve(false); - } - if (valid) { - newBuildDependencies = packContainer.buildDependencies; - resolveResults = packContainer.resolveResults; - return resolve(true); - } - logger.log( - `Restored pack from ${cacheLocation}${this._extension}, but build dependencies resolve to different locations.` - ); - return resolve(false); - } - ); - } - ); - }) - ]) - .catch(err => { - logger.timeEnd("check build dependencies"); - throw err; - }) - .then(([buildSnapshotValid, resolveValid]) => { - logger.timeEnd("check build dependencies"); - if (buildSnapshotValid && resolveValid) { - logger.time("restore cache content metadata"); - const d = packContainer.data(); - logger.timeEnd("restore cache content metadata"); - return d; - } - return undefined; - }); - }) - .then(pack => { - if (pack) { - pack.maxAge = this.maxAge; - this.buildSnapshot = buildSnapshot; - if (buildDependencies) this.buildDependencies = buildDependencies; - if (newBuildDependencies) - this.newBuildDependencies.addAll(newBuildDependencies); - this.resolveResults = resolveResults; - this.resolveBuildDependenciesSnapshot = - resolveBuildDependenciesSnapshot; - return pack; - } - return new Pack(logger, this.maxAge); - }) - .catch(err => { - this.logger.warn( - `Restoring pack from ${cacheLocation}${this._extension} failed: ${err}` - ); - this.logger.debug(err.stack); - return new Pack(logger, this.maxAge); - }); + static toPath(str) { + if (typeof str !== "string") return ""; + return str + .replace(PATH_NAME_NORMALIZE_REPLACE_REGEX, "-") + .replace(MATCH_PADDED_HYPHENS_REPLACE_REGEX, ""); } + // map number to a single character a-z, A-Z or multiple characters if number is too big /** - * @param {string} identifier unique name for the resource - * @param {Etag | null} etag etag of the resource - * @param {any} data cached content - * @returns {Promise} promise + * @param {number} n number to convert to ident + * @returns {string} returns single character ident */ - store(identifier, etag, data) { - return this._getPack().then(pack => { - pack.set(identifier, etag === null ? null : etag.toString(), data); - }); + static numberToIdentifier(n) { + if (n >= NUMBER_OF_IDENTIFIER_START_CHARS) { + // use multiple letters + return ( + Template.numberToIdentifier(n % NUMBER_OF_IDENTIFIER_START_CHARS) + + Template.numberToIdentifierContinuation( + Math.floor(n / NUMBER_OF_IDENTIFIER_START_CHARS) + ) + ); + } + + // lower case + if (n < DELTA_A_TO_Z) { + return String.fromCharCode(START_LOWERCASE_ALPHABET_CODE + n); + } + n -= DELTA_A_TO_Z; + + // upper case + if (n < DELTA_A_TO_Z) { + return String.fromCharCode(START_UPPERCASE_ALPHABET_CODE + n); + } + + if (n === DELTA_A_TO_Z) return "_"; + return "$"; } /** - * @param {string} identifier unique name for the resource - * @param {Etag | null} etag etag of the resource - * @returns {Promise} promise to the cached content + * @param {number} n number to convert to ident + * @returns {string} returns single character ident */ - restore(identifier, etag) { - return this._getPack() - .then(pack => - pack.get(identifier, etag === null ? null : etag.toString()) - ) - .catch(err => { - if (err && err.code !== "ENOENT") { - this.logger.warn( - `Restoring failed for ${identifier} from pack: ${err}` - ); - this.logger.debug(err.stack); - } - }); + static numberToIdentifierContinuation(n) { + if (n >= NUMBER_OF_IDENTIFIER_CONTINUATION_CHARS) { + // use multiple letters + return ( + Template.numberToIdentifierContinuation( + n % NUMBER_OF_IDENTIFIER_CONTINUATION_CHARS + ) + + Template.numberToIdentifierContinuation( + Math.floor(n / NUMBER_OF_IDENTIFIER_CONTINUATION_CHARS) + ) + ); + } + + // lower case + if (n < DELTA_A_TO_Z) { + return String.fromCharCode(START_LOWERCASE_ALPHABET_CODE + n); + } + n -= DELTA_A_TO_Z; + + // upper case + if (n < DELTA_A_TO_Z) { + return String.fromCharCode(START_UPPERCASE_ALPHABET_CODE + n); + } + n -= DELTA_A_TO_Z; + + // numbers + if (n < 10) { + return `${n}`; + } + + if (n === 10) return "_"; + return "$"; } - storeBuildDependencies(dependencies) { - this.newBuildDependencies.addAll(dependencies); + /** + * + * @param {string | string[]} s string to convert to identity + * @returns {string} converted identity + */ + static indent(s) { + if (Array.isArray(s)) { + return s.map(Template.indent).join("\n"); + } else { + const str = s.trimRight(); + if (!str) return ""; + const ind = str[0] === "\n" ? "" : "\t"; + return ind + str.replace(/\n([^\n])/g, "\n\t$1"); + } } - afterAllStored() { - const packPromise = this.packPromise; - if (packPromise === undefined) return Promise.resolve(); - const reportProgress = ProgressPlugin.getReporter(this.compiler); - return (this.storePromise = packPromise - .then(pack => { - pack.stopCapturingRequests(); - if (!pack.invalid) return; - this.packPromise = undefined; - this.logger.log(`Storing pack...`); - let promise; - const newBuildDependencies = new Set(); - for (const dep of this.newBuildDependencies) { - if (!this.buildDependencies.has(dep)) { - newBuildDependencies.add(dep); - } - } - if (newBuildDependencies.size > 0 || !this.buildSnapshot) { - if (reportProgress) reportProgress(0.5, "resolve build dependencies"); - this.logger.debug( - `Capturing build dependencies... (${Array.from( - newBuildDependencies - ).join(", ")})` - ); - promise = new Promise((resolve, reject) => { - this.logger.time("resolve build dependencies"); - this.fileSystemInfo.resolveBuildDependencies( - this.context, - newBuildDependencies, - (err, result) => { - this.logger.timeEnd("resolve build dependencies"); - if (err) return reject(err); + /** + * + * @param {string|string[]} s string to create prefix for + * @param {string} prefix prefix to compose + * @returns {string} returns new prefix string + */ + static prefix(s, prefix) { + const str = Template.asString(s).trim(); + if (!str) return ""; + const ind = str[0] === "\n" ? "" : prefix; + return ind + str.replace(/\n([^\n])/g, "\n" + prefix + "$1"); + } - this.logger.time("snapshot build dependencies"); - const { - files, - directories, - missing, - resolveResults, - resolveDependencies - } = result; - if (this.resolveResults) { - for (const [key, value] of resolveResults) { - this.resolveResults.set(key, value); - } - } else { - this.resolveResults = resolveResults; - } - if (reportProgress) { - reportProgress( - 0.6, - "snapshot build dependencies", - "resolving" - ); - } - this.fileSystemInfo.createSnapshot( - undefined, - resolveDependencies.files, - resolveDependencies.directories, - resolveDependencies.missing, - this.snapshot.resolveBuildDependencies, - (err, snapshot) => { - if (err) { - this.logger.timeEnd("snapshot build dependencies"); - return reject(err); - } - if (!snapshot) { - this.logger.timeEnd("snapshot build dependencies"); - return reject( - new Error("Unable to snapshot resolve dependencies") - ); - } - if (this.resolveBuildDependenciesSnapshot) { - this.resolveBuildDependenciesSnapshot = - this.fileSystemInfo.mergeSnapshots( - this.resolveBuildDependenciesSnapshot, - snapshot - ); - } else { - this.resolveBuildDependenciesSnapshot = snapshot; - } - if (reportProgress) { - reportProgress( - 0.7, - "snapshot build dependencies", - "modules" - ); - } - this.fileSystemInfo.createSnapshot( - undefined, - files, - directories, - missing, - this.snapshot.buildDependencies, - (err, snapshot) => { - this.logger.timeEnd("snapshot build dependencies"); - if (err) return reject(err); - if (!snapshot) { - return reject( - new Error("Unable to snapshot build dependencies") - ); - } - this.logger.debug("Captured build dependencies"); + /** + * + * @param {string|string[]} str string or string collection + * @returns {string} returns a single string from array + */ + static asString(str) { + if (Array.isArray(str)) { + return str.join("\n"); + } + return str; + } - if (this.buildSnapshot) { - this.buildSnapshot = - this.fileSystemInfo.mergeSnapshots( - this.buildSnapshot, - snapshot - ); - } else { - this.buildSnapshot = snapshot; - } + /** + * @typedef {Object} WithId + * @property {string|number} id + */ - resolve(); - } - ); - } - ); - } - ); - }); - } else { - promise = Promise.resolve(); + /** + * @param {WithId[]} modules a collection of modules to get array bounds for + * @returns {[number, number] | false} returns the upper and lower array bounds + * or false if not every module has a number based id + */ + static getModulesArrayBounds(modules) { + let maxId = -Infinity; + let minId = Infinity; + for (const module of modules) { + const moduleId = module.id; + if (typeof moduleId !== "number") return false; + if (maxId < moduleId) maxId = moduleId; + if (minId > moduleId) minId = moduleId; + } + if (minId < 16 + ("" + minId).length) { + // add minId x ',' instead of 'Array(minId).concat(…)' + minId = 0; + } + // start with -1 because the first module needs no comma + let objectOverhead = -1; + for (const module of modules) { + // module id + colon + comma + objectOverhead += `${module.id}`.length + 2; + } + // number of commas, or when starting non-zero the length of Array(minId).concat() + const arrayOverhead = minId === 0 ? maxId : 16 + `${minId}`.length + maxId; + return arrayOverhead < objectOverhead ? [minId, maxId] : false; + } + + /** + * @param {ChunkRenderContext} renderContext render context + * @param {Module[]} modules modules to render (should be ordered by identifier) + * @param {function(Module): Source} renderModule function to render a module + * @param {string=} prefix applying prefix strings + * @returns {Source} rendered chunk modules in a Source object + */ + static renderChunkModules(renderContext, modules, renderModule, prefix = "") { + const { chunkGraph } = renderContext; + var source = new ConcatSource(); + if (modules.length === 0) { + return null; + } + /** @type {{id: string|number, source: Source|string}[]} */ + const allModules = modules.map(module => { + return { + id: chunkGraph.getModuleId(module), + source: renderModule(module) || "false" + }; + }); + const bounds = Template.getModulesArrayBounds(allModules); + if (bounds) { + // Render a spare array + const minId = bounds[0]; + const maxId = bounds[1]; + if (minId !== 0) { + source.add(`Array(${minId}).concat(`); + } + source.add("[\n"); + /** @type {Map} */ + const modules = new Map(); + for (const module of allModules) { + modules.set(module.id, module); + } + for (let idx = minId; idx <= maxId; idx++) { + const module = modules.get(idx); + if (idx !== minId) { + source.add(",\n"); } - return promise.then(() => { - if (reportProgress) reportProgress(0.8, "serialize pack"); - this.logger.time(`store pack`); - const updatedBuildDependencies = new Set(this.buildDependencies); - for (const dep of newBuildDependencies) { - updatedBuildDependencies.add(dep); - } - const content = new PackContainer( - pack, - this.version, - this.buildSnapshot, - updatedBuildDependencies, - this.resolveResults, - this.resolveBuildDependenciesSnapshot - ); - return this.fileSerializer - .serialize(content, { - filename: `${this.cacheLocation}/index${this._extension}`, - extension: `${this._extension}`, - logger: this.logger, - profile: this.profile - }) - .then(() => { - for (const dep of newBuildDependencies) { - this.buildDependencies.add(dep); - } - this.newBuildDependencies.clear(); - this.logger.timeEnd(`store pack`); - const stats = pack.getContentStats(); - this.logger.log( - "Stored pack (%d items, %d files, %d MiB)", - pack.itemInfo.size, - stats.count, - Math.round(stats.size / 1024 / 1024) - ); - }) - .catch(err => { - this.logger.timeEnd(`store pack`); - this.logger.warn(`Caching failed for pack: ${err}`); - this.logger.debug(err.stack); - }); + source.add(`/* ${idx} */`); + if (module) { + source.add("\n"); + source.add(module.source); + } + } + source.add("\n" + prefix + "]"); + if (minId !== 0) { + source.add(")"); + } + } else { + // Render an object + source.add("{\n"); + for (let i = 0; i < allModules.length; i++) { + const module = allModules[i]; + if (i !== 0) { + source.add(",\n"); + } + source.add(`\n/***/ ${JSON.stringify(module.id)}:\n`); + source.add(module.source); + } + source.add(`\n\n${prefix}}`); + } + return source; + } + + /** + * @param {RuntimeModule[]} runtimeModules array of runtime modules in order + * @param {RenderContext & { codeGenerationResults?: CodeGenerationResults }} renderContext render context + * @returns {Source} rendered runtime modules in a Source object + */ + static renderRuntimeModules(runtimeModules, renderContext) { + const source = new ConcatSource(); + for (const module of runtimeModules) { + const codeGenerationResults = renderContext.codeGenerationResults; + let runtimeSource; + if (codeGenerationResults) { + runtimeSource = codeGenerationResults.getSource( + module, + renderContext.chunk.runtime, + "runtime" + ); + } else { + const codeGenResult = module.codeGeneration({ + chunkGraph: renderContext.chunkGraph, + dependencyTemplates: renderContext.dependencyTemplates, + moduleGraph: renderContext.moduleGraph, + runtimeTemplate: renderContext.runtimeTemplate, + runtime: renderContext.chunk.runtime }); - }) - .catch(err => { - this.logger.warn(`Caching failed for pack: ${err}`); - this.logger.debug(err.stack); - })); + if (!codeGenResult) continue; + runtimeSource = codeGenResult.sources.get("runtime"); + } + if (runtimeSource) { + source.add(Template.toNormalComment(module.identifier()) + "\n"); + if (!module.shouldIsolate()) { + source.add(runtimeSource); + source.add("\n\n"); + } else if (renderContext.runtimeTemplate.supportsArrowFunction()) { + source.add("(() => {\n"); + source.add(new PrefixSource("\t", runtimeSource)); + source.add("\n})();\n\n"); + } else { + source.add("!function() {\n"); + source.add(new PrefixSource("\t", runtimeSource)); + source.add("\n}();\n\n"); + } + } + } + return source; } - clear() { - this.fileSystemInfo.clear(); - this.buildDependencies.clear(); - this.newBuildDependencies.clear(); - this.resolveBuildDependenciesSnapshot = undefined; - this.resolveResults = undefined; - this.buildSnapshot = undefined; - this.packPromise = undefined; + /** + * @param {RuntimeModule[]} runtimeModules array of runtime modules in order + * @param {RenderContext} renderContext render context + * @returns {Source} rendered chunk runtime modules in a Source object + */ + static renderChunkRuntimeModules(runtimeModules, renderContext) { + return new PrefixSource( + "/******/ ", + new ConcatSource( + "function(__webpack_require__) { // webpackRuntimeModules\n", + this.renderRuntimeModules(runtimeModules, renderContext), + "}\n" + ) + ); } } -module.exports = PackFileCacheStrategy; +module.exports = Template; +module.exports.NUMBER_OF_IDENTIFIER_START_CHARS = + NUMBER_OF_IDENTIFIER_START_CHARS; +module.exports.NUMBER_OF_IDENTIFIER_CONTINUATION_CHARS = + NUMBER_OF_IDENTIFIER_CONTINUATION_CHARS; + + +/***/ }), + +/***/ 54642: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Jason Anderson @diurnalist +*/ + + + +const { basename, extname } = __webpack_require__(85622); +const util = __webpack_require__(31669); +const Chunk = __webpack_require__(65574); +const Module = __webpack_require__(85887); +const { parseResource } = __webpack_require__(96236); + +/** @typedef {import("./Compilation").AssetInfo} AssetInfo */ +/** @typedef {import("./Compilation").PathData} PathData */ +/** @typedef {import("./Compiler")} Compiler */ + +const REGEXP = /\[\\*([\w:]+)\\*\]/gi; + +const prepareId = id => { + if (typeof id !== "string") return id; + + if (/^"\s\+*.*\+\s*"$/.test(id)) { + const match = /^"\s\+*\s*(.*)\s*\+\s*"$/.exec(id); + + return `" + (${match[1]} + "").replace(/(^[.-]|[^a-zA-Z0-9_-])+/g, "_") + "`; + } + + return id.replace(/(^[.-]|[^a-zA-Z0-9_-])+/g, "_"); +}; + +const hashLength = (replacer, handler, assetInfo, hashName) => { + const fn = (match, arg, input) => { + let result; + const length = arg && parseInt(arg, 10); + + if (length && handler) { + result = handler(length); + } else { + const hash = replacer(match, arg, input); + + result = length ? hash.slice(0, length) : hash; + } + if (assetInfo) { + assetInfo.immutable = true; + if (Array.isArray(assetInfo[hashName])) { + assetInfo[hashName] = [...assetInfo[hashName], result]; + } else if (assetInfo[hashName]) { + assetInfo[hashName] = [assetInfo[hashName], result]; + } else { + assetInfo[hashName] = result; + } + } + return result; + }; + + return fn; +}; +const replacer = (value, allowEmpty) => { + const fn = (match, arg, input) => { + if (typeof value === "function") { + value = value(); + } + if (value === null || value === undefined) { + if (!allowEmpty) { + throw new Error( + `Path variable ${match} not implemented in this context: ${input}` + ); + } -/***/ }), + return ""; + } else { + return `${value}`; + } + }; -/***/ 11740: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + return fn; +}; -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ +const deprecationCache = new Map(); +const deprecatedFunction = (() => () => {})(); +const deprecated = (fn, message, code) => { + let d = deprecationCache.get(message); + if (d === undefined) { + d = util.deprecate(deprecatedFunction, message, code); + deprecationCache.set(message, d); + } + return (...args) => { + d(); + return fn(...args); + }; +}; +/** + * @param {string | function(PathData, AssetInfo=): string} path the raw path + * @param {PathData} data context data + * @param {AssetInfo} assetInfo extra info about the asset (will be written to) + * @returns {string} the interpolated path + */ +const replacePathVariables = (path, data, assetInfo) => { + const chunkGraph = data.chunkGraph; + /** @type {Map} */ + const replacements = new Map(); -const LazySet = __webpack_require__(59534); -const makeSerializable = __webpack_require__(26522); + // Filename context + // + // Placeholders + // + // for /some/path/file.js?query#fragment: + // [file] - /some/path/file.js + // [query] - ?query + // [fragment] - #fragment + // [base] - file.js + // [path] - /some/path/ + // [name] - file + // [ext] - .js + if (typeof data.filename === "string") { + const { path: file, query, fragment } = parseResource(data.filename); -/** @typedef {import("enhanced-resolve/lib/Resolver")} Resolver */ -/** @typedef {import("../CacheFacade").ItemCacheFacade} ItemCacheFacade */ -/** @typedef {import("../Compiler")} Compiler */ -/** @typedef {import("../FileSystemInfo")} FileSystemInfo */ -/** @typedef {import("../FileSystemInfo").Snapshot} Snapshot */ + const ext = extname(file); + const base = basename(file); + const name = base.slice(0, base.length - ext.length); + const path = file.slice(0, file.length - base.length); -class CacheEntry { - constructor(result, snapshot) { - this.result = result; - this.snapshot = snapshot; + replacements.set("file", replacer(file)); + replacements.set("query", replacer(query, true)); + replacements.set("fragment", replacer(fragment, true)); + replacements.set("path", replacer(path, true)); + replacements.set("base", replacer(base)); + replacements.set("name", replacer(name)); + replacements.set("ext", replacer(ext, true)); + // Legacy + replacements.set( + "filebase", + deprecated( + replacer(base), + "[filebase] is now [base]", + "DEP_WEBPACK_TEMPLATE_PATH_PLUGIN_REPLACE_PATH_VARIABLES_FILENAME" + ) + ); } - serialize({ write }) { - write(this.result); - write(this.snapshot); + // Compilation context + // + // Placeholders + // + // [fullhash] - data.hash (3a4b5c6e7f) + // + // Legacy Placeholders + // + // [hash] - data.hash (3a4b5c6e7f) + if (data.hash) { + const hashReplacer = hashLength( + replacer(data.hash), + data.hashWithLength, + assetInfo, + "fullhash" + ); + + replacements.set("fullhash", hashReplacer); + + // Legacy + replacements.set( + "hash", + deprecated( + hashReplacer, + "[hash] is now [fullhash] (also consider using [chunkhash] or [contenthash], see documentation for details)", + "DEP_WEBPACK_TEMPLATE_PATH_PLUGIN_REPLACE_PATH_VARIABLES_HASH" + ) + ); } - deserialize({ read }) { - this.result = read(); - this.snapshot = read(); + // Chunk Context + // + // Placeholders + // + // [id] - chunk.id (0.js) + // [name] - chunk.name (app.js) + // [chunkhash] - chunk.hash (7823t4t4.js) + // [contenthash] - chunk.contentHash[type] (3256u3zg.js) + if (data.chunk) { + const chunk = data.chunk; + + const contentHashType = data.contentHashType; + + const idReplacer = replacer(chunk.id); + const nameReplacer = replacer(chunk.name || chunk.id); + const chunkhashReplacer = hashLength( + replacer(chunk instanceof Chunk ? chunk.renderedHash : chunk.hash), + "hashWithLength" in chunk ? chunk.hashWithLength : undefined, + assetInfo, + "chunkhash" + ); + const contenthashReplacer = hashLength( + replacer( + data.contentHash || + (contentHashType && + chunk.contentHash && + chunk.contentHash[contentHashType]) + ), + data.contentHashWithLength || + ("contentHashWithLength" in chunk && chunk.contentHashWithLength + ? chunk.contentHashWithLength[contentHashType] + : undefined), + assetInfo, + "contenthash" + ); + + replacements.set("id", idReplacer); + replacements.set("name", nameReplacer); + replacements.set("chunkhash", chunkhashReplacer); + replacements.set("contenthash", contenthashReplacer); } -} -makeSerializable(CacheEntry, "webpack/lib/cache/ResolverCachePlugin"); + // Module Context + // + // Placeholders + // + // [id] - module.id (2.png) + // [hash] - module.hash (6237543873.png) + // + // Legacy Placeholders + // + // [moduleid] - module.id (2.png) + // [modulehash] - module.hash (6237543873.png) + if (data.module) { + const module = data.module; -/** - * @template T - * @param {Set | LazySet} set set to add items to - * @param {Set | LazySet} otherSet set to add items from - * @returns {void} - */ -const addAllToSet = (set, otherSet) => { - if (set instanceof LazySet) { - set.addAll(otherSet); - } else { - for (const item of otherSet) { - set.add(item); - } + const idReplacer = replacer(() => + prepareId( + module instanceof Module ? chunkGraph.getModuleId(module) : module.id + ) + ); + const moduleHashReplacer = hashLength( + replacer(() => + module instanceof Module + ? chunkGraph.getRenderedModuleHash(module, data.runtime) + : module.hash + ), + "hashWithLength" in module ? module.hashWithLength : undefined, + assetInfo, + "modulehash" + ); + const contentHashReplacer = hashLength( + replacer(data.contentHash), + undefined, + assetInfo, + "contenthash" + ); + + replacements.set("id", idReplacer); + replacements.set("modulehash", moduleHashReplacer); + replacements.set("contenthash", contentHashReplacer); + replacements.set( + "hash", + data.contentHash ? contentHashReplacer : moduleHashReplacer + ); + // Legacy + replacements.set( + "moduleid", + deprecated( + idReplacer, + "[moduleid] is now [id]", + "DEP_WEBPACK_TEMPLATE_PATH_PLUGIN_REPLACE_PATH_VARIABLES_MODULE_ID" + ) + ); } -}; -/** - * @param {Object} object an object - * @param {boolean} excludeContext if true, context is not included in string - * @returns {string} stringified version - */ -const objectToString = (object, excludeContext) => { - let str = ""; - for (const key in object) { - if (excludeContext && key === "context") continue; - const value = object[key]; - if (typeof value === "object" && value !== null) { - str += `|${key}=[${objectToString(value, false)}|]`; - } else { - str += `|${key}=|${value}`; - } + // Other things + if (data.url) { + replacements.set("url", replacer(data.url)); + } + if (typeof data.runtime === "string") { + replacements.set( + "runtime", + replacer(() => prepareId(data.runtime)) + ); + } else { + replacements.set("runtime", replacer("_")); } - return str; -}; -class ResolverCachePlugin { - /** - * Apply the plugin - * @param {Compiler} compiler the compiler instance - * @returns {void} - */ - apply(compiler) { - const cache = compiler.getCache("ResolverCachePlugin"); - /** @type {FileSystemInfo} */ - let fileSystemInfo; - let snapshotOptions; - let realResolves = 0; - let cachedResolves = 0; - let cacheInvalidResolves = 0; - let concurrentResolves = 0; - compiler.hooks.thisCompilation.tap("ResolverCachePlugin", compilation => { - snapshotOptions = compilation.options.snapshot.resolve; - fileSystemInfo = compilation.fileSystemInfo; - compilation.hooks.finishModules.tap("ResolverCachePlugin", () => { - if (realResolves + cachedResolves > 0) { - const logger = compilation.getLogger("webpack.ResolverCachePlugin"); - logger.log( - `${Math.round( - (100 * realResolves) / (realResolves + cachedResolves) - )}% really resolved (${realResolves} real resolves with ${cacheInvalidResolves} cached but invalid, ${cachedResolves} cached valid, ${concurrentResolves} concurrent)` - ); - realResolves = 0; - cachedResolves = 0; - cacheInvalidResolves = 0; - concurrentResolves = 0; - } - }); - }); - /** - * @param {ItemCacheFacade} itemCache cache - * @param {Resolver} resolver the resolver - * @param {Object} resolveContext context for resolving meta info - * @param {Object} request the request info object - * @param {function(Error=, Object=): void} callback callback function - * @returns {void} - */ - const doRealResolve = ( - itemCache, - resolver, - resolveContext, - request, - callback - ) => { - realResolves++; - const newRequest = { - _ResolverCachePluginCacheMiss: true, - ...request - }; - const newResolveContext = { - ...resolveContext, - stack: new Set(), - missingDependencies: new LazySet(), - fileDependencies: new LazySet(), - contextDependencies: new LazySet() - }; - const propagate = key => { - if (resolveContext[key]) { - addAllToSet(resolveContext[key], newResolveContext[key]); - } - }; - const resolveTime = Date.now(); - resolver.doResolve( - resolver.hooks.resolve, - newRequest, - "Cache miss", - newResolveContext, - (err, result) => { - propagate("fileDependencies"); - propagate("contextDependencies"); - propagate("missingDependencies"); - if (err) return callback(err); - const fileDependencies = newResolveContext.fileDependencies; - const contextDependencies = newResolveContext.contextDependencies; - const missingDependencies = newResolveContext.missingDependencies; - fileSystemInfo.createSnapshot( - resolveTime, - fileDependencies, - contextDependencies, - missingDependencies, - snapshotOptions, - (err, snapshot) => { - if (err) return callback(err); - if (!snapshot) { - if (result) return callback(null, result); - return callback(); - } - itemCache.store(new CacheEntry(result, snapshot), storeErr => { - if (storeErr) return callback(storeErr); - if (result) return callback(null, result); - callback(); - }); - } - ); - } - ); - }; - compiler.resolverFactory.hooks.resolver.intercept({ - factory(type, hook) { - /** @type {Map} */ - const activeRequests = new Map(); - hook.tap( - "ResolverCachePlugin", - /** - * @param {Resolver} resolver the resolver - * @param {Object} options resolve options - * @param {Object} userOptions resolve options passed by the user - * @returns {void} - */ - (resolver, options, userOptions) => { - if (options.cache !== true) return; - const optionsIdent = objectToString(userOptions, false); - const cacheWithContext = - options.cacheWithContext !== undefined - ? options.cacheWithContext - : false; - resolver.hooks.resolve.tapAsync( - { - name: "ResolverCachePlugin", - stage: -100 - }, - (request, resolveContext, callback) => { - if (request._ResolverCachePluginCacheMiss || !fileSystemInfo) { - return callback(); - } - const identifier = `${type}${optionsIdent}${objectToString( - request, - !cacheWithContext - )}`; - const activeRequest = activeRequests.get(identifier); - if (activeRequest) { - activeRequest.push(callback); - return; - } - const itemCache = cache.getItemCache(identifier, null); - let callbacks; - const done = (err, result) => { - if (callbacks === undefined) { - callback(err, result); - callbacks = false; - } else { - for (const callback of callbacks) { - callback(err, result); - } - activeRequests.delete(identifier); - callbacks = false; - } - }; - /** - * @param {Error=} err error if any - * @param {CacheEntry=} cacheEntry cache entry - * @returns {void} - */ - const processCacheResult = (err, cacheEntry) => { - if (err) return done(err); + if (typeof path === "function") { + path = path(data, assetInfo); + } - if (cacheEntry) { - const { snapshot, result } = cacheEntry; - fileSystemInfo.checkSnapshotValid( - snapshot, - (err, valid) => { - if (err || !valid) { - cacheInvalidResolves++; - return doRealResolve( - itemCache, - resolver, - resolveContext, - request, - done - ); - } - cachedResolves++; - if (resolveContext.missingDependencies) { - addAllToSet( - resolveContext.missingDependencies, - snapshot.getMissingIterable() - ); - } - if (resolveContext.fileDependencies) { - addAllToSet( - resolveContext.fileDependencies, - snapshot.getFileIterable() - ); - } - if (resolveContext.contextDependencies) { - addAllToSet( - resolveContext.contextDependencies, - snapshot.getContextIterable() - ); - } - done(null, result); - } - ); - } else { - doRealResolve( - itemCache, - resolver, - resolveContext, - request, - done - ); - } - }; - itemCache.get(processCacheResult); - if (callbacks === undefined) { - callbacks = [callback]; - activeRequests.set(identifier, callbacks); - } - } - ); - } - ); - return hook; + path = path.replace(REGEXP, (match, content) => { + if (content.length + 2 === match.length) { + const contentMatch = /^(\w+)(?::(\w+))?$/.exec(content); + if (!contentMatch) return match; + const [, kind, arg] = contentMatch; + const replacer = replacements.get(kind); + if (replacer !== undefined) { + return replacer(match, arg, path); } + } else if (match.startsWith("[\\") && match.endsWith("\\]")) { + return `[${match.slice(2, -2)}]`; + } + return match; + }); + + return path; +}; + +const plugin = "TemplatedPathPlugin"; + +class TemplatedPathPlugin { + /** + * Apply the plugin + * @param {Compiler} compiler the compiler instance + * @returns {void} + */ + apply(compiler) { + compiler.hooks.compilation.tap(plugin, compilation => { + compilation.hooks.assetPath.tap(plugin, replacePathVariables); }); } } -module.exports = ResolverCachePlugin; +module.exports = TemplatedPathPlugin; /***/ }), -/***/ 12339: +/***/ 63859: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; /* MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra + Author Ivan Kopeykin @vankop */ -const createHash = __webpack_require__(24123); - -/** @typedef {import("../util/Hash")} Hash */ -/** @typedef {typeof import("../util/Hash")} HashConstructor */ - -/** - * @typedef {Object} HashableObject - * @property {function(Hash): void} updateHash - */ - -class LazyHashedEtag { - /** - * @param {HashableObject} obj object with updateHash method - * @param {string | HashConstructor} hashFunction the hash function to use - */ - constructor(obj, hashFunction = "md4") { - this._obj = obj; - this._hash = undefined; - this._hashFunction = hashFunction; - } +const WebpackError = __webpack_require__(68422); +const makeSerializable = __webpack_require__(26522); +class UnhandledSchemeError extends WebpackError { /** - * @returns {string} hash of object + * @param {string} scheme scheme + * @param {string} resource resource */ - toString() { - if (this._hash === undefined) { - const hash = createHash(this._hashFunction); - this._obj.updateHash(hash); - this._hash = /** @type {string} */ (hash.digest("base64")); - } - return this._hash; + constructor(scheme, resource) { + super( + `Reading from "${resource}" is not handled by plugins (Unhandled scheme).` + + '\nWebpack supports "data:" and "file:" URIs by default.' + + `\nYou may need an additional plugin to handle "${scheme}:" URIs.` + ); + this.file = resource; + this.name = "UnhandledSchemeError"; } } -/** @type {Map>} */ -const mapStrings = new Map(); - -/** @type {WeakMap>} */ -const mapObjects = new WeakMap(); - -/** - * @param {HashableObject} obj object with updateHash method - * @param {string | HashConstructor} hashFunction the hash function to use - * @returns {LazyHashedEtag} etag - */ -const getter = (obj, hashFunction = "md4") => { - let innerMap; - if (typeof hashFunction === "string") { - innerMap = mapStrings.get(hashFunction); - if (innerMap === undefined) { - const newHash = new LazyHashedEtag(obj, hashFunction); - innerMap = new WeakMap(); - innerMap.set(obj, newHash); - mapStrings.set(hashFunction, innerMap); - return newHash; - } - } else { - innerMap = mapObjects.get(hashFunction); - if (innerMap === undefined) { - const newHash = new LazyHashedEtag(obj, hashFunction); - innerMap = new WeakMap(); - innerMap.set(obj, newHash); - mapObjects.set(hashFunction, innerMap); - return newHash; - } - } - const hash = innerMap.get(obj); - if (hash !== undefined) return hash; - const newHash = new LazyHashedEtag(obj, hashFunction); - innerMap.set(obj, newHash); - return newHash; -}; +makeSerializable( + UnhandledSchemeError, + "webpack/lib/UnhandledSchemeError", + "UnhandledSchemeError" +); -module.exports = getter; +module.exports = UnhandledSchemeError; /***/ }), -/***/ 53885: -/***/ (function(module) { +/***/ 9532: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; /* @@ -67975,79 +63467,37 @@ module.exports = getter; -/** @typedef {import("../Cache").Etag} Etag */ +const WebpackError = __webpack_require__(68422); +const makeSerializable = __webpack_require__(26522); -class MergedEtag { +/** @typedef {import("./Dependency").DependencyLocation} DependencyLocation */ + +class UnsupportedFeatureWarning extends WebpackError { /** - * @param {Etag} a first - * @param {Etag} b second + * @param {string} message description of warning + * @param {DependencyLocation} loc location start and end positions of the module */ - constructor(a, b) { - this.a = a; - this.b = b; - } + constructor(message, loc) { + super(message); - toString() { - return `${this.a.toString()}|${this.b.toString()}`; + this.name = "UnsupportedFeatureWarning"; + this.loc = loc; + this.hideStack = true; } } -const dualObjectMap = new WeakMap(); -const objectStringMap = new WeakMap(); - -/** - * @param {Etag} a first - * @param {Etag} b second - * @returns {Etag} result - */ -const mergeEtags = (a, b) => { - if (typeof a === "string") { - if (typeof b === "string") { - return `${a}|${b}`; - } else { - const temp = b; - b = a; - a = temp; - } - } else { - if (typeof b !== "string") { - // both a and b are objects - let map = dualObjectMap.get(a); - if (map === undefined) { - dualObjectMap.set(a, (map = new WeakMap())); - } - const mergedEtag = map.get(b); - if (mergedEtag === undefined) { - const newMergedEtag = new MergedEtag(a, b); - map.set(b, newMergedEtag); - return newMergedEtag; - } else { - return mergedEtag; - } - } - } - // a is object, b is string - let map = objectStringMap.get(a); - if (map === undefined) { - objectStringMap.set(a, (map = new Map())); - } - const mergedEtag = map.get(b); - if (mergedEtag === undefined) { - const newMergedEtag = new MergedEtag(a, b); - map.set(b, newMergedEtag); - return newMergedEtag; - } else { - return mergedEtag; - } -}; +makeSerializable( + UnsupportedFeatureWarning, + "webpack/lib/UnsupportedFeatureWarning" +); -module.exports = mergeEtags; +module.exports = UnsupportedFeatureWarning; /***/ }), -/***/ 26040: -/***/ (function(__unused_webpack_module, exports, __webpack_require__) { +/***/ 15466: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; /* @@ -68057,4089 +63507,4028 @@ module.exports = mergeEtags; -const path = __webpack_require__(85622); -const webpackSchema = __webpack_require__(1863); +const ConstDependency = __webpack_require__(60864); -// TODO add originPath to PathItem for better errors -/** - * @typedef {Object} PathItem - * @property {any} schema the part of the schema - * @property {string} path the path in the config - */ +/** @typedef {import("./Compiler")} Compiler */ -/** @typedef {"unknown-argument" | "unexpected-non-array-in-path" | "unexpected-non-object-in-path" | "multiple-values-unexpected" | "invalid-value"} ProblemType */ +class UseStrictPlugin { + /** + * Apply the plugin + * @param {Compiler} compiler the compiler instance + * @returns {void} + */ + apply(compiler) { + compiler.hooks.compilation.tap( + "UseStrictPlugin", + (compilation, { normalModuleFactory }) => { + const handler = parser => { + parser.hooks.program.tap("UseStrictPlugin", ast => { + const firstNode = ast.body[0]; + if ( + firstNode && + firstNode.type === "ExpressionStatement" && + firstNode.expression.type === "Literal" && + firstNode.expression.value === "use strict" + ) { + // Remove "use strict" expression. It will be added later by the renderer again. + // This is necessary in order to not break the strict mode when webpack prepends code. + // @see https://github.com/webpack/webpack/issues/1970 + const dep = new ConstDependency("", firstNode.range); + dep.loc = firstNode.loc; + parser.state.module.addPresentationalDependency(dep); + parser.state.module.buildInfo.strict = true; + } + }); + }; -/** - * @typedef {Object} Problem - * @property {ProblemType} type - * @property {string} path - * @property {string} argument - * @property {any=} value - * @property {number=} index - * @property {string=} expected - */ + normalModuleFactory.hooks.parser + .for("javascript/auto") + .tap("UseStrictPlugin", handler); + normalModuleFactory.hooks.parser + .for("javascript/dynamic") + .tap("UseStrictPlugin", handler); + normalModuleFactory.hooks.parser + .for("javascript/esm") + .tap("UseStrictPlugin", handler); + } + ); + } +} -/** - * @typedef {Object} LocalProblem - * @property {ProblemType} type - * @property {string} path - * @property {string=} expected - */ +module.exports = UseStrictPlugin; -/** - * @typedef {Object} ArgumentConfig - * @property {string} description - * @property {string} path - * @property {boolean} multiple - * @property {"enum"|"string"|"path"|"number"|"boolean"|"RegExp"|"reset"} type - * @property {any[]=} values - */ -/** - * @typedef {Object} Argument - * @property {string} description - * @property {"string"|"number"|"boolean"} simpleType - * @property {boolean} multiple - * @property {ArgumentConfig[]} configs - */ +/***/ }), -/** - * @param {any=} schema a json schema to create arguments for (by default webpack schema is used) - * @returns {Record} object of arguments - */ -const getArguments = (schema = webpackSchema) => { - /** @type {Record} */ - const flags = {}; +/***/ 33304: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - const pathToArgumentName = input => { - return input - .replace(/\./g, "-") - .replace(/\[\]/g, "") - .replace( - /(\p{Uppercase_Letter}+|\p{Lowercase_Letter}|\d)(\p{Uppercase_Letter}+)/gu, - "$1-$2" - ) - .replace(/-?[^\p{Uppercase_Letter}\p{Lowercase_Letter}\d]+/gu, "-") - .toLowerCase(); - }; +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ - const getSchemaPart = path => { - const newPath = path.split("/"); - let schemaPart = schema; - for (let i = 1; i < newPath.length; i++) { - const inner = schemaPart[newPath[i]]; +const CaseSensitiveModulesWarning = __webpack_require__(42444); - if (!inner) { - break; +/** @typedef {import("./Compiler")} Compiler */ +/** @typedef {import("./Module")} Module */ + +class WarnCaseSensitiveModulesPlugin { + /** + * Apply the plugin + * @param {Compiler} compiler the compiler instance + * @returns {void} + */ + apply(compiler) { + compiler.hooks.compilation.tap( + "WarnCaseSensitiveModulesPlugin", + compilation => { + compilation.hooks.seal.tap("WarnCaseSensitiveModulesPlugin", () => { + /** @type {Map>} */ + const moduleWithoutCase = new Map(); + for (const module of compilation.modules) { + const identifier = module.identifier(); + const lowerIdentifier = identifier.toLowerCase(); + let map = moduleWithoutCase.get(lowerIdentifier); + if (map === undefined) { + map = new Map(); + moduleWithoutCase.set(lowerIdentifier, map); + } + map.set(identifier, module); + } + for (const pair of moduleWithoutCase) { + const map = pair[1]; + if (map.size > 1) { + compilation.warnings.push( + new CaseSensitiveModulesWarning( + map.values(), + compilation.moduleGraph + ) + ); + } + } + }); } + ); + } +} - schemaPart = inner; - } +module.exports = WarnCaseSensitiveModulesPlugin; - return schemaPart; - }; - /** - * - * @param {PathItem[]} path path in the schema - * @returns {string | undefined} description - */ - const getDescription = path => { - for (const { schema } of path) { - if (schema.cli && schema.cli.helper) continue; - if (schema.description) return schema.description; - } - }; +/***/ }), - /** - * - * @param {any} schemaPart schema - * @returns {Pick} partial argument config - */ - const schemaToArgumentConfig = schemaPart => { - if (schemaPart.enum) { - return { - type: "enum", - values: schemaPart.enum - }; - } - switch (schemaPart.type) { - case "number": - return { - type: "number" - }; - case "string": - return { - type: schemaPart.absolutePath ? "path" : "string" - }; - case "boolean": - return { - type: "boolean" - }; - } - if (schemaPart.instanceof === "RegExp") { - return { - type: "RegExp" - }; - } - return undefined; - }; +/***/ 85024: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - /** - * @param {PathItem[]} path path in the schema - * @returns {void} - */ - const addResetFlag = path => { - const schemaPath = path[0].path; - const name = pathToArgumentName(`${schemaPath}.reset`); - const description = getDescription(path); - flags[name] = { - configs: [ - { - type: "reset", - multiple: false, - description: `Clear all items provided in '${schemaPath}' configuration. ${description}`, - path: schemaPath - } - ], - description: undefined, - simpleType: undefined, - multiple: undefined - }; - }; +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Florent Cailhol @ooflorent +*/ - /** - * @param {PathItem[]} path full path in schema - * @param {boolean} multiple inside of an array - * @returns {number} number of arguments added - */ - const addFlag = (path, multiple) => { - const argConfigBase = schemaToArgumentConfig(path[0].schema); - if (!argConfigBase) return 0; - const name = pathToArgumentName(path[0].path); - /** @type {ArgumentConfig} */ - const argConfig = { - ...argConfigBase, - multiple, - description: getDescription(path), - path: path[0].path - }; - if (!flags[name]) { - flags[name] = { - configs: [], - description: undefined, - simpleType: undefined, - multiple: undefined - }; - } +const WebpackError = __webpack_require__(68422); - if ( - flags[name].configs.some( - item => JSON.stringify(item) === JSON.stringify(argConfig) - ) - ) { - return 0; - } +/** @typedef {import("./Compiler")} Compiler */ - if ( - flags[name].configs.some( - item => item.type === argConfig.type && item.multiple !== multiple - ) - ) { - if (multiple) { - throw new Error( - `Conflicting schema for ${path[0].path} with ${argConfig.type} type (array type must be before single item type)` +class WarnDeprecatedOptionPlugin { + /** + * Create an instance of the plugin + * @param {string} option the target option + * @param {string | number} value the deprecated option value + * @param {string} suggestion the suggestion replacement + */ + constructor(option, value, suggestion) { + this.option = option; + this.value = value; + this.suggestion = suggestion; + } + + /** + * Apply the plugin + * @param {Compiler} compiler the compiler instance + * @returns {void} + */ + apply(compiler) { + compiler.hooks.thisCompilation.tap( + "WarnDeprecatedOptionPlugin", + compilation => { + compilation.warnings.push( + new DeprecatedOptionWarning(this.option, this.value, this.suggestion) ); } - return 0; - } + ); + } +} - flags[name].configs.push(argConfig); +class DeprecatedOptionWarning extends WebpackError { + constructor(option, value, suggestion) { + super(); + + this.name = "DeprecatedOptionWarning"; + this.message = + "configuration\n" + + `The value '${value}' for option '${option}' is deprecated. ` + + `Use '${suggestion}' instead.`; + } +} + +module.exports = WarnDeprecatedOptionPlugin; - return 1; - }; - // TODO support `not` and `if/then/else` - // TODO support `const`, but we don't use it on our schema - /** - * - * @param {object} schemaPart the current schema - * @param {string} schemaPath the current path in the schema - * @param {{schema: object, path: string}[]} path all previous visited schemaParts - * @param {string | null} inArray if inside of an array, the path to the array - * @returns {number} added arguments - */ - const traverse = (schemaPart, schemaPath = "", path = [], inArray = null) => { - while (schemaPart.$ref) { - schemaPart = getSchemaPart(schemaPart.$ref); - } +/***/ }), - const repetitions = path.filter(({ schema }) => schema === schemaPart); - if ( - repetitions.length >= 2 || - repetitions.some(({ path }) => path === schemaPath) - ) { - return 0; - } +/***/ 70308: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - if (schemaPart.cli && schemaPart.cli.exclude) return 0; +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ - const fullPath = [{ schema: schemaPart, path: schemaPath }, ...path]; - let addedArguments = 0; - addedArguments += addFlag(fullPath, !!inArray); +const NoModeWarning = __webpack_require__(84991); - if (schemaPart.type === "object") { - if (schemaPart.properties) { - for (const property of Object.keys(schemaPart.properties)) { - addedArguments += traverse( - schemaPart.properties[property], - schemaPath ? `${schemaPath}.${property}` : property, - fullPath, - inArray - ); - } - } +/** @typedef {import("./Compiler")} Compiler */ - return addedArguments; - } +class WarnNoModeSetPlugin { + /** + * Apply the plugin + * @param {Compiler} compiler the compiler instance + * @returns {void} + */ + apply(compiler) { + compiler.hooks.thisCompilation.tap("WarnNoModeSetPlugin", compilation => { + compilation.warnings.push(new NoModeWarning()); + }); + } +} - if (schemaPart.type === "array") { - if (inArray) { - return 0; - } - if (Array.isArray(schemaPart.items)) { - let i = 0; - for (const item of schemaPart.items) { - addedArguments += traverse( - item, - `${schemaPath}.${i}`, - fullPath, - schemaPath - ); - } +module.exports = WarnNoModeSetPlugin; - return addedArguments; - } - addedArguments += traverse( - schemaPart.items, - `${schemaPath}[]`, - fullPath, - schemaPath - ); +/***/ }), - if (addedArguments > 0) { - addResetFlag(fullPath); - addedArguments++; - } +/***/ 90187: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - return addedArguments; - } +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ - const maybeOf = schemaPart.oneOf || schemaPart.anyOf || schemaPart.allOf; - if (maybeOf) { - const items = maybeOf; - for (let i = 0; i < items.length; i++) { - addedArguments += traverse(items[i], schemaPath, fullPath, inArray); - } +const { groupBy } = __webpack_require__(21537); +const createSchemaValidation = __webpack_require__(77695); - return addedArguments; - } +/** @typedef {import("../declarations/plugins/WatchIgnorePlugin").WatchIgnorePluginOptions} WatchIgnorePluginOptions */ +/** @typedef {import("./Compiler")} Compiler */ +/** @typedef {import("./util/fs").WatchFileSystem} WatchFileSystem */ - return addedArguments; - }; +const validate = createSchemaValidation( + __webpack_require__(16779), + () => __webpack_require__(66489), + { + name: "Watch Ignore Plugin", + baseDataPath: "options" + } +); - traverse(schema); +const IGNORE_TIME_ENTRY = "ignore"; - // Summarize flags - for (const name of Object.keys(flags)) { - const argument = flags[name]; - argument.description = argument.configs.reduce((desc, { description }) => { - if (!desc) return description; - if (!description) return desc; - if (desc.includes(description)) return desc; - return `${desc} ${description}`; - }, /** @type {string | undefined} */ (undefined)); - argument.simpleType = argument.configs.reduce((t, argConfig) => { - /** @type {"string" | "number" | "boolean"} */ - let type = "string"; - switch (argConfig.type) { - case "number": - type = "number"; - break; - case "reset": - case "boolean": - type = "boolean"; - break; - case "enum": - if (argConfig.values.every(v => typeof v === "boolean")) - type = "boolean"; - if (argConfig.values.every(v => typeof v === "number")) - type = "number"; - break; - } - if (t === undefined) return type; - return t === type ? t : "string"; - }, /** @type {"string" | "number" | "boolean" | undefined} */ (undefined)); - argument.multiple = argument.configs.some(c => c.multiple); +class IgnoringWatchFileSystem { + /** + * @param {WatchFileSystem} wfs original file system + * @param {(string|RegExp)[]} paths ignored paths + */ + constructor(wfs, paths) { + this.wfs = wfs; + this.paths = paths; } - return flags; -}; + watch(files, dirs, missing, startTime, options, callback, callbackUndelayed) { + files = Array.from(files); + dirs = Array.from(dirs); + const ignored = path => + this.paths.some(p => + p instanceof RegExp ? p.test(path) : path.indexOf(p) === 0 + ); -const cliAddedItems = new WeakMap(); + const [ignoredFiles, notIgnoredFiles] = groupBy(files, ignored); + const [ignoredDirs, notIgnoredDirs] = groupBy(dirs, ignored); -/** - * @param {any} config configuration - * @param {string} schemaPath path in the config - * @param {number | undefined} index index of value when multiple values are provided, otherwise undefined - * @returns {{ problem?: LocalProblem, object?: any, property?: string | number, value?: any }} problem or object with property and value - */ -const getObjectAndProperty = (config, schemaPath, index = 0) => { - if (!schemaPath) return { value: config }; - const parts = schemaPath.split("."); - let property = parts.pop(); - let current = config; - let i = 0; - for (const part of parts) { - const isArray = part.endsWith("[]"); - const name = isArray ? part.slice(0, -2) : part; - let value = current[name]; - if (isArray) { - if (value === undefined) { - value = {}; - current[name] = [...Array.from({ length: index }), value]; - cliAddedItems.set(current[name], index + 1); - } else if (!Array.isArray(value)) { - return { - problem: { - type: "unexpected-non-array-in-path", - path: parts.slice(0, i).join(".") - } - }; - } else { - let addedItems = cliAddedItems.get(value) || 0; - while (addedItems <= index) { - value.push(undefined); - addedItems++; + const watcher = this.wfs.watch( + notIgnoredFiles, + notIgnoredDirs, + missing, + startTime, + options, + (err, fileTimestamps, dirTimestamps, changedFiles, removedFiles) => { + if (err) return callback(err); + for (const path of ignoredFiles) { + fileTimestamps.set(path, IGNORE_TIME_ENTRY); } - cliAddedItems.set(value, addedItems); - const x = value.length - addedItems + index; - if (value[x] === undefined) { - value[x] = {}; - } else if (value[x] === null || typeof value[x] !== "object") { - return { - problem: { - type: "unexpected-non-object-in-path", - path: parts.slice(0, i).join(".") - } - }; + + for (const path of ignoredDirs) { + dirTimestamps.set(path, IGNORE_TIME_ENTRY); } - value = value[x]; - } - } else { - if (value === undefined) { - value = current[name] = {}; - } else if (value === null || typeof value !== "object") { - return { - problem: { - type: "unexpected-non-object-in-path", - path: parts.slice(0, i).join(".") - } - }; - } - } - current = value; - i++; - } - let value = current[property]; - if (property.endsWith("[]")) { - const name = property.slice(0, -2); - const value = current[name]; - if (value === undefined) { - current[name] = [...Array.from({ length: index }), undefined]; - cliAddedItems.set(current[name], index + 1); - return { object: current[name], property: index, value: undefined }; - } else if (!Array.isArray(value)) { - current[name] = [value, ...Array.from({ length: index }), undefined]; - cliAddedItems.set(current[name], index + 1); - return { object: current[name], property: index + 1, value: undefined }; - } else { - let addedItems = cliAddedItems.get(value) || 0; - while (addedItems <= index) { - value.push(undefined); - addedItems++; - } - cliAddedItems.set(value, addedItems); - const x = value.length - addedItems + index; - if (value[x] === undefined) { - value[x] = {}; - } else if (value[x] === null || typeof value[x] !== "object") { - return { - problem: { - type: "unexpected-non-object-in-path", - path: schemaPath - } - }; - } - return { - object: value, - property: x, - value: value[x] - }; - } - } - return { object: current, property, value }; -}; -/** - * @param {any} config configuration - * @param {string} schemaPath path in the config - * @param {any} value parsed value - * @param {number | undefined} index index of value when multiple values are provided, otherwise undefined - * @returns {LocalProblem | null} problem or null for success - */ -const setValue = (config, schemaPath, value, index) => { - const { problem, object, property } = getObjectAndProperty( - config, - schemaPath, - index - ); - if (problem) return problem; - object[property] = value; - return null; -}; + callback( + err, + fileTimestamps, + dirTimestamps, + changedFiles, + removedFiles + ); + }, + callbackUndelayed + ); -/** - * @param {ArgumentConfig} argConfig processing instructions - * @param {any} config configuration - * @param {any} value the value - * @param {number | undefined} index the index if multiple values provided - * @returns {LocalProblem | null} a problem if any - */ -const processArgumentConfig = (argConfig, config, value, index) => { - if (index !== undefined && !argConfig.multiple) { return { - type: "multiple-values-unexpected", - path: argConfig.path + close: () => watcher.close(), + pause: () => watcher.pause(), + getContextTimeInfoEntries: () => { + const dirTimestamps = watcher.getContextTimeInfoEntries(); + for (const path of ignoredDirs) { + dirTimestamps.set(path, IGNORE_TIME_ENTRY); + } + return dirTimestamps; + }, + getFileTimeInfoEntries: () => { + const fileTimestamps = watcher.getFileTimeInfoEntries(); + for (const path of ignoredFiles) { + fileTimestamps.set(path, IGNORE_TIME_ENTRY); + } + return fileTimestamps; + } }; } - const parsed = parseValueForArgumentConfig(argConfig, value); - if (parsed === undefined) { - return { - type: "invalid-value", - path: argConfig.path, - expected: getExpectedValue(argConfig) - }; +} + +class WatchIgnorePlugin { + /** + * @param {WatchIgnorePluginOptions} options options + */ + constructor(options) { + validate(options); + this.paths = options.paths; } - const problem = setValue(config, argConfig.path, parsed, index); - if (problem) return problem; - return null; -}; -/** - * @param {ArgumentConfig} argConfig processing instructions - * @returns {string | undefined} expected message - */ -const getExpectedValue = argConfig => { - switch (argConfig.type) { - default: - return argConfig.type; - case "boolean": - return "true | false"; - case "RegExp": - return "regular expression (example: /ab?c*/)"; - case "enum": - return argConfig.values.map(v => `${v}`).join(" | "); - case "reset": - return "true (will reset the previous value to an empty array)"; + /** + * Apply the plugin + * @param {Compiler} compiler the compiler instance + * @returns {void} + */ + apply(compiler) { + compiler.hooks.afterEnvironment.tap("WatchIgnorePlugin", () => { + compiler.watchFileSystem = new IgnoringWatchFileSystem( + compiler.watchFileSystem, + this.paths + ); + }); } -}; +} + +module.exports = WatchIgnorePlugin; + + +/***/ }), + +/***/ 49819: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ + + + +const Stats = __webpack_require__(87797); + +/** @typedef {import("../declarations/WebpackOptions").WatchOptions} WatchOptions */ +/** @typedef {import("./Compilation")} Compilation */ +/** @typedef {import("./Compiler")} Compiler */ +/** @typedef {import("./FileSystemInfo").FileSystemInfoEntry} FileSystemInfoEntry */ /** - * @param {ArgumentConfig} argConfig processing instructions - * @param {any} value the value - * @returns {any | undefined} parsed value + * @template T + * @callback Callback + * @param {Error=} err + * @param {T=} result */ -const parseValueForArgumentConfig = (argConfig, value) => { - switch (argConfig.type) { - case "string": - if (typeof value === "string") { - return value; - } - break; - case "path": - if (typeof value === "string") { - return path.resolve(value); - } - break; - case "number": - if (typeof value === "number") return value; - if (typeof value === "string" && /^[+-]?\d*(\.\d*)[eE]\d+$/) { - const n = +value; - if (!isNaN(n)) return n; - } - break; - case "boolean": - if (typeof value === "boolean") return value; - if (value === "true") return true; - if (value === "false") return false; - break; - case "RegExp": - if (value instanceof RegExp) return value; - if (typeof value === "string") { - // cspell:word yugi - const match = /^\/(.*)\/([yugi]*)$/.exec(value); - if (match && !/[^\\]\//.test(match[1])) - return new RegExp(match[1], match[2]); - } - break; - case "enum": - if (argConfig.values.includes(value)) return value; - for (const item of argConfig.values) { - if (`${item}` === value) return item; - } - break; - case "reset": - if (value === true) return []; - break; + +class Watching { + /** + * @param {Compiler} compiler the compiler + * @param {WatchOptions} watchOptions options + * @param {Callback} handler completion handler + */ + constructor(compiler, watchOptions, handler) { + this.startTime = null; + this.invalid = false; + this.handler = handler; + /** @type {Callback[]} */ + this.callbacks = []; + /** @type {Callback[] | undefined} */ + this._closeCallbacks = undefined; + this.closed = false; + this.suspended = false; + this.blocked = false; + this._isBlocked = () => false; + this._onChange = () => {}; + this._onInvalid = () => {}; + if (typeof watchOptions === "number") { + this.watchOptions = { + aggregateTimeout: watchOptions + }; + } else if (watchOptions && typeof watchOptions === "object") { + this.watchOptions = { ...watchOptions }; + } else { + this.watchOptions = {}; + } + if (typeof this.watchOptions.aggregateTimeout !== "number") { + this.watchOptions.aggregateTimeout = 200; + } + this.compiler = compiler; + this.running = false; + this._initial = true; + this._invalidReported = true; + this._needRecords = true; + this.watcher = undefined; + this.pausedWatcher = undefined; + /** @type {Set} */ + this._collectedChangedFiles = undefined; + /** @type {Set} */ + this._collectedRemovedFiles = undefined; + this._done = this._done.bind(this); + process.nextTick(() => { + if (this._initial) this._invalidate(); + }); } -}; -/** - * @param {Record} args object of arguments - * @param {any} config configuration - * @param {Record} values object with values - * @returns {Problem[] | null} problems or null for success - */ -const processArguments = (args, config, values) => { - /** @type {Problem[]} */ - const problems = []; - for (const key of Object.keys(values)) { - const arg = args[key]; - if (!arg) { - problems.push({ - type: "unknown-argument", - path: "", - argument: key - }); - continue; - } - const processValue = (value, i) => { - const currentProblems = []; - for (const argConfig of arg.configs) { - const problem = processArgumentConfig(argConfig, config, value, i); - if (!problem) { - return; - } - currentProblems.push({ - ...problem, - argument: key, - value: value, - index: i - }); + /** + * @param {ReadonlySet} changedFiles changed files + * @param {ReadonlySet} removedFiles removed files + */ + _mergeWithCollected(changedFiles, removedFiles) { + if (!changedFiles) return; + if (!this._collectedChangedFiles) { + this._collectedChangedFiles = new Set(changedFiles); + this._collectedRemovedFiles = new Set(removedFiles); + } else { + for (const file of changedFiles) { + this._collectedChangedFiles.add(file); + this._collectedRemovedFiles.delete(file); } - problems.push(...currentProblems); - }; - let value = values[key]; - if (Array.isArray(value)) { - for (let i = 0; i < value.length; i++) { - processValue(value[i], i); + for (const file of removedFiles) { + this._collectedChangedFiles.delete(file); + this._collectedRemovedFiles.add(file); } - } else { - processValue(value, undefined); } } - if (problems.length === 0) return null; - return problems; -}; -exports.getArguments = getArguments; -exports.processArguments = processArguments; + /** + * @param {ReadonlyMap=} fileTimeInfoEntries info for files + * @param {ReadonlyMap=} contextTimeInfoEntries info for directories + * @param {ReadonlySet=} changedFiles changed files + * @param {ReadonlySet=} removedFiles removed files + * @returns {void} + */ + _go(fileTimeInfoEntries, contextTimeInfoEntries, changedFiles, removedFiles) { + this._initial = false; + if (this.startTime === null) this.startTime = Date.now(); + this.running = true; + if (this.watcher) { + this.pausedWatcher = this.watcher; + this.lastWatcherStartTime = Date.now(); + this.watcher.pause(); + this.watcher = null; + } else if (!this.lastWatcherStartTime) { + this.lastWatcherStartTime = Date.now(); + } + this.compiler.fsStartTime = Date.now(); + this._mergeWithCollected( + changedFiles || + (this.pausedWatcher && + this.pausedWatcher.getAggregatedChanges && + this.pausedWatcher.getAggregatedChanges()), + (this.compiler.removedFiles = + removedFiles || + (this.pausedWatcher && + this.pausedWatcher.getAggregatedRemovals && + this.pausedWatcher.getAggregatedRemovals())) + ); + this.compiler.modifiedFiles = this._collectedChangedFiles; + this._collectedChangedFiles = undefined; + this.compiler.removedFiles = this._collectedRemovedFiles; + this._collectedRemovedFiles = undefined; -/***/ }), + this.compiler.fileTimestamps = + fileTimeInfoEntries || + (this.pausedWatcher && this.pausedWatcher.getFileTimeInfoEntries()); + this.compiler.contextTimestamps = + contextTimeInfoEntries || + (this.pausedWatcher && this.pausedWatcher.getContextTimeInfoEntries()); -/***/ 82852: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + const run = () => { + if (this.compiler.idle) { + return this.compiler.cache.endIdle(err => { + if (err) return this._done(err); + this.compiler.idle = false; + run(); + }); + } + if (this._needRecords) { + return this.compiler.readRecords(err => { + if (err) return this._done(err); -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Sergey Melyukov @smelukov -*/ + this._needRecords = false; + run(); + }); + } + this.invalid = false; + this._invalidReported = false; + this.compiler.hooks.watchRun.callAsync(this.compiler, err => { + if (err) return this._done(err); + const onCompiled = (err, compilation) => { + if (err) return this._done(err, compilation); + if (this.invalid) return this._done(null, compilation); + if (this.compiler.hooks.shouldEmit.call(compilation) === false) { + return this._done(null, compilation); + } + process.nextTick(() => { + const logger = compilation.getLogger("webpack.Compiler"); + logger.time("emitAssets"); + this.compiler.emitAssets(compilation, err => { + logger.timeEnd("emitAssets"); + if (err) return this._done(err, compilation); + if (this.invalid) return this._done(null, compilation); -const browserslist = __webpack_require__(3561); -const path = __webpack_require__(85622); + logger.time("emitRecords"); + this.compiler.emitRecords(err => { + logger.timeEnd("emitRecords"); + if (err) return this._done(err, compilation); -/** @typedef {import("./target").ApiTargetProperties} ApiTargetProperties */ -/** @typedef {import("./target").EcmaTargetProperties} EcmaTargetProperties */ -/** @typedef {import("./target").PlatformTargetProperties} PlatformTargetProperties */ + if (compilation.hooks.needAdditionalPass.call()) { + compilation.needAdditionalPass = true; -// [[C:]/path/to/config][:env] -const inputRx = /^(?:((?:[A-Z]:)?[/\\].*?))?(?::(.+?))?$/i; + compilation.startTime = this.startTime; + compilation.endTime = Date.now(); + logger.time("done hook"); + const stats = new Stats(compilation); + this.compiler.hooks.done.callAsync(stats, err => { + logger.timeEnd("done hook"); + if (err) return this._done(err, compilation); -/** - * @typedef {Object} BrowserslistHandlerConfig - * @property {string=} configPath - * @property {string=} env - * @property {string=} query - */ + this.compiler.hooks.additionalPass.callAsync(err => { + if (err) return this._done(err, compilation); + this.compiler.compile(onCompiled); + }); + }); + return; + } + return this._done(null, compilation); + }); + }); + }); + }; + this.compiler.compile(onCompiled); + }); + }; -/** - * @param {string} input input string - * @param {string} context the context directory - * @returns {BrowserslistHandlerConfig} config - */ -const parse = (input, context) => { - if (!input) { - return {}; + run(); } - if (path.isAbsolute(input)) { - const [, configPath, env] = inputRx.exec(input) || []; - return { configPath, env }; + /** + * @param {Compilation} compilation the compilation + * @returns {Stats} the compilation stats + */ + _getStats(compilation) { + const stats = new Stats(compilation); + return stats; } - const config = browserslist.findConfig(context); + /** + * @param {Error=} err an optional error + * @param {Compilation=} compilation the compilation + * @returns {void} + */ + _done(err, compilation) { + this.running = false; - if (config && Object.keys(config).includes(input)) { - return { env: input }; - } + const logger = compilation && compilation.getLogger("webpack.Watching"); - return { query: input }; -}; + let stats = null; -/** - * @param {string} input input string - * @param {string} context the context directory - * @returns {string[] | undefined} selected browsers - */ -const load = (input, context) => { - const { configPath, env, query } = parse(input, context); + const handleError = (err, cbs) => { + this.compiler.hooks.failed.call(err); + this.compiler.cache.beginIdle(); + this.compiler.idle = true; + this.handler(err, stats); + if (!cbs) { + cbs = this.callbacks; + this.callbacks = []; + } + for (const cb of cbs) cb(err); + }; - // if a query is specified, then use it, else - // if a path to a config is specified then load it, else - // find a nearest config - const config = query - ? query - : configPath - ? browserslist.loadConfig({ - config: configPath, - env - }) - : browserslist.loadConfig({ path: context, env }); + if ( + this.invalid && + !this.suspended && + !this.blocked && + !(this._isBlocked() && (this.blocked = true)) + ) { + if (compilation) { + logger.time("storeBuildDependencies"); + this.compiler.cache.storeBuildDependencies( + compilation.buildDependencies, + err => { + logger.timeEnd("storeBuildDependencies"); + if (err) return handleError(err); + this._go(); + } + ); + } else { + this._go(); + } + return; + } - if (!config) return null; - return browserslist(config); -}; + if (compilation) { + compilation.startTime = this.startTime; + compilation.endTime = Date.now(); + stats = new Stats(compilation); + } + this.startTime = null; + if (err) return handleError(err); -/** - * @param {string[]} browsers supported browsers list - * @returns {EcmaTargetProperties & PlatformTargetProperties & ApiTargetProperties} target properties - */ -const resolve = browsers => { - /** - * Checks all against a version number - * @param {Record} versions first supported version - * @returns {boolean} true if supports - */ - const rawChecker = versions => { - return browsers.every(v => { - const [name, parsedVersion] = v.split(" "); - if (!name) return false; - const requiredVersion = versions[name]; - if (!requiredVersion) return false; - const [parsedMajor, parserMinor] = - // safari TP supports all features for normal safari - parsedVersion === "TP" - ? [Infinity, Infinity] - : parsedVersion.split("."); - if (typeof requiredVersion === "number") { - return +parsedMajor >= requiredVersion; - } - return requiredVersion[0] === +parsedMajor - ? +parserMinor >= requiredVersion[1] - : +parsedMajor > requiredVersion[0]; + const cbs = this.callbacks; + this.callbacks = []; + logger.time("done hook"); + this.compiler.hooks.done.callAsync(stats, err => { + logger.timeEnd("done hook"); + if (err) return handleError(err, cbs); + this.handler(null, stats); + logger.time("storeBuildDependencies"); + this.compiler.cache.storeBuildDependencies( + compilation.buildDependencies, + err => { + logger.timeEnd("storeBuildDependencies"); + if (err) return handleError(err, cbs); + logger.time("beginIdle"); + this.compiler.cache.beginIdle(); + this.compiler.idle = true; + logger.timeEnd("beginIdle"); + process.nextTick(() => { + if (!this.closed) { + this.watch( + compilation.fileDependencies, + compilation.contextDependencies, + compilation.missingDependencies + ); + } + }); + for (const cb of cbs) cb(null); + this.compiler.hooks.afterDone.call(stats); + } + ); }); - }; - const anyNode = browsers.some(b => /^node /.test(b)); - const anyBrowser = browsers.some(b => /^(?!node)/.test(b)); - const browserProperty = !anyBrowser ? false : anyNode ? null : true; - const nodeProperty = !anyNode ? false : anyBrowser ? null : true; - // Internet Explorer Mobile, Blackberry browser and Opera Mini are very old browsers, they do not support new features - const es6DynamicImport = rawChecker({ - chrome: 63, - and_chr: 63, - edge: 79, - firefox: 67, - and_ff: 67, - // ie: Not supported - opera: 50, - op_mob: 46, - safari: [11, 1], - ios_saf: [11, 3], - samsung: [8, 2], - android: 63, - and_qq: [10, 4], - // baidu: Not supported - // and_uc: Not supported - // kaios: Not supported - // Since Node.js 13.14.0 no warning about usage, but it was added 8.5.0 with some limitations and it was improved in 12.0.0 and 13.2.0 - node: [13, 14] - }); - - return { - const: rawChecker({ - chrome: 49, - and_chr: 49, - edge: 12, - // Prior to Firefox 13, const is implemented, but re-assignment is not failing. - // Prior to Firefox 46, a TypeError was thrown on redeclaration instead of a SyntaxError. - firefox: 36, - and_ff: 36, - // Not supported in for-in and for-of loops - // ie: Not supported - opera: 36, - op_mob: 36, - safari: [10, 0], - ios_saf: [10, 0], - // Before 5.0 supported correctly in strict mode, otherwise supported without block scope - samsung: [5, 0], - android: 37, - and_qq: [10, 4], - // Supported correctly in strict mode, otherwise supported without block scope - // baidu: Not supported - and_uc: [12, 12], - kaios: [2, 5], - node: [6, 0] - }), - arrowFunction: rawChecker({ - chrome: 45, - and_chr: 45, - edge: 12, - // The initial implementation of arrow functions in Firefox made them automatically strict. This has been changed as of Firefox 24. The use of 'use strict'; is now required. - // Prior to Firefox 39, a line terminator (\\n) was incorrectly allowed after arrow function arguments. This has been fixed to conform to the ES2015 specification and code like () \\n => {} will now throw a SyntaxError in this and later versions. - firefox: 39, - and_ff: 39, - // ie: Not supported, - opera: 32, - op_mob: 32, - safari: 10, - ios_saf: 10, - samsung: [5, 0], - android: 45, - and_qq: [10, 4], - baidu: [7, 12], - and_uc: [12, 12], - kaios: [2, 5], - node: [6, 0] - }), - forOf: rawChecker({ - chrome: 38, - and_chr: 38, - edge: 12, - // Prior to Firefox 51, using the for...of loop construct with the const keyword threw a SyntaxError ("missing = in const declaration"). - firefox: 51, - and_ff: 51, - // ie: Not supported, - opera: 25, - op_mob: 25, - safari: 7, - ios_saf: 7, - samsung: [3, 0], - android: 38, - // and_qq: Unknown support - // baidu: Unknown support - // and_uc: Unknown support - // kaios: Unknown support - node: [0, 12] - }), - destructuring: rawChecker({ - chrome: 49, - and_chr: 49, - edge: 14, - firefox: 41, - and_ff: 41, - // ie: Not supported, - opera: 36, - op_mob: 36, - safari: 8, - ios_saf: 8, - samsung: [5, 0], - android: 49, - // and_qq: Unknown support - // baidu: Unknown support - // and_uc: Unknown support - // kaios: Unknown support - node: [6, 0] - }), - bigIntLiteral: rawChecker({ - chrome: 67, - and_chr: 67, - edge: 79, - firefox: 68, - and_ff: 68, - // ie: Not supported, - opera: 54, - op_mob: 48, - safari: 14, - ios_saf: 14, - samsung: [9, 2], - android: 67, - // and_qq: Not supported - // baidu: Not supported - // and_uc: Not supported - // kaios: Not supported - node: [10, 4] - }), - // Support syntax `import` and `export` and no limitations and bugs on Node.js - // Not include `export * as namespace` - module: rawChecker({ - chrome: 61, - and_chr: 61, - edge: 16, - firefox: 60, - and_ff: 60, - // ie: Not supported, - opera: 48, - op_mob: 45, - safari: [10, 1], - ios_saf: [10, 3], - samsung: [8, 0], - android: 61, - and_qq: [10, 4], - // baidu: Not supported - // and_uc: Not supported - // kaios: Not supported - // Since Node.js 13.14.0 no warning about usage, but it was added 8.5.0 with some limitations and it was improved in 12.0.0 and 13.2.0 - node: [13, 14] - }), - dynamicImport: es6DynamicImport, - dynamicImportInWorker: es6DynamicImport && !anyNode, - // browserslist does not have info about globalThis - // so this is based on mdn-browser-compat-data - globalThis: rawChecker({ - chrome: 71, - and_chr: 71, - edge: 79, - firefox: 65, - and_ff: 65, - // ie: Not supported, - opera: 58, - op_mob: 50, - safari: [12, 1], - ios_saf: [12, 2], - samsung: [10, 1], - android: 71, - // and_qq: Unknown support - // baidu: Unknown support - // and_uc: Unknown support - // kaios: Unknown support - node: [12, 0] - }), + } - browser: browserProperty, - electron: false, - node: nodeProperty, - nwjs: false, - web: browserProperty, - webworker: false, + /** + * @param {Iterable} files watched files + * @param {Iterable} dirs watched directories + * @param {Iterable} missing watched existence entries + * @returns {void} + */ + watch(files, dirs, missing) { + this.pausedWatcher = null; + this.watcher = this.compiler.watchFileSystem.watch( + files, + dirs, + missing, + this.lastWatcherStartTime, + this.watchOptions, + ( + err, + fileTimeInfoEntries, + contextTimeInfoEntries, + changedFiles, + removedFiles + ) => { + if (err) { + this.compiler.modifiedFiles = undefined; + this.compiler.removedFiles = undefined; + this.compiler.fileTimestamps = undefined; + this.compiler.contextTimestamps = undefined; + this.compiler.fsStartTime = undefined; + return this.handler(err); + } + this._invalidate( + fileTimeInfoEntries, + contextTimeInfoEntries, + changedFiles, + removedFiles + ); + this._onChange(); + }, + (fileName, changeTime) => { + if (!this._invalidReported) { + this._invalidReported = true; + this.compiler.hooks.invalid.call(fileName, changeTime); + } + this._onInvalid(); + } + ); + } - document: browserProperty, - fetchWasm: browserProperty, - global: nodeProperty, - importScripts: false, - importScriptsInWorker: true, - nodeBuiltins: nodeProperty, - require: nodeProperty - }; -}; + /** + * @param {Callback=} callback signals when the build has completed again + * @returns {void} + */ + invalidate(callback) { + if (callback) { + this.callbacks.push(callback); + } + if (!this._invalidReported) { + this._invalidReported = true; + this.compiler.hooks.invalid.call(null, Date.now()); + } + this._onChange(); + this._invalidate(); + } -module.exports = { - resolve, - load -}; + _invalidate( + fileTimeInfoEntries, + contextTimeInfoEntries, + changedFiles, + removedFiles + ) { + if (this.suspended || (this._isBlocked() && (this.blocked = true))) { + this._mergeWithCollected(changedFiles, removedFiles); + return; + } + + if (this.running) { + this._mergeWithCollected(changedFiles, removedFiles); + this.invalid = true; + } else { + this._go( + fileTimeInfoEntries, + contextTimeInfoEntries, + changedFiles, + removedFiles + ); + } + } + + suspend() { + this.suspended = true; + } + + resume() { + if (this.suspended) { + this.suspended = false; + this._invalidate(); + } + } + + /** + * @param {Callback} callback signals when the watcher is closed + * @returns {void} + */ + close(callback) { + if (this._closeCallbacks) { + if (callback) { + this._closeCallbacks.push(callback); + } + return; + } + const finalCallback = (err, compilation) => { + this.running = false; + this.compiler.running = false; + this.compiler.watching = undefined; + this.compiler.watchMode = false; + this.compiler.modifiedFiles = undefined; + this.compiler.removedFiles = undefined; + this.compiler.fileTimestamps = undefined; + this.compiler.contextTimestamps = undefined; + this.compiler.fsStartTime = undefined; + const shutdown = err => { + this.compiler.hooks.watchClose.call(); + const closeCallbacks = this._closeCallbacks; + this._closeCallbacks = undefined; + for (const cb of closeCallbacks) cb(err); + }; + if (compilation) { + const logger = compilation.getLogger("webpack.Watching"); + logger.time("storeBuildDependencies"); + this.compiler.cache.storeBuildDependencies( + compilation.buildDependencies, + err2 => { + logger.timeEnd("storeBuildDependencies"); + shutdown(err || err2); + } + ); + } else { + shutdown(err); + } + }; + + this.closed = true; + if (this.watcher) { + this.watcher.close(); + this.watcher = null; + } + if (this.pausedWatcher) { + this.pausedWatcher.close(); + this.pausedWatcher = null; + } + this._closeCallbacks = []; + if (callback) { + this._closeCallbacks.push(callback); + } + if (this.running) { + this.invalid = true; + this._done = finalCallback; + } else { + finalCallback(); + } + } +} + +module.exports = Watching; /***/ }), -/***/ 27057: -/***/ (function(__unused_webpack_module, exports, __webpack_require__) { +/***/ 68422: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; /* MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra + Author Jarid Margolin @jaridmargolin */ -const fs = __webpack_require__(35747); -const path = __webpack_require__(85622); -const Template = __webpack_require__(92066); -const { cleverMerge } = __webpack_require__(11217); -const { - getTargetsProperties, - getTargetProperties, - getDefaultTarget -} = __webpack_require__(23451); +const inspect = __webpack_require__(31669).inspect.custom; +const makeSerializable = __webpack_require__(26522); -/** @typedef {import("../../declarations/WebpackOptions").CacheOptionsNormalized} CacheOptions */ -/** @typedef {import("../../declarations/WebpackOptions").EntryDescription} EntryDescription */ -/** @typedef {import("../../declarations/WebpackOptions").EntryNormalized} Entry */ -/** @typedef {import("../../declarations/WebpackOptions").Experiments} Experiments */ -/** @typedef {import("../../declarations/WebpackOptions").ExperimentsNormalized} ExperimentsNormalized */ -/** @typedef {import("../../declarations/WebpackOptions").ExternalsPresets} ExternalsPresets */ -/** @typedef {import("../../declarations/WebpackOptions").ExternalsType} ExternalsType */ -/** @typedef {import("../../declarations/WebpackOptions").InfrastructureLogging} InfrastructureLogging */ -/** @typedef {import("../../declarations/WebpackOptions").JavascriptParserOptions} JavascriptParserOptions */ -/** @typedef {import("../../declarations/WebpackOptions").Library} Library */ -/** @typedef {import("../../declarations/WebpackOptions").LibraryName} LibraryName */ -/** @typedef {import("../../declarations/WebpackOptions").LibraryOptions} LibraryOptions */ -/** @typedef {import("../../declarations/WebpackOptions").Loader} Loader */ -/** @typedef {import("../../declarations/WebpackOptions").Mode} Mode */ -/** @typedef {import("../../declarations/WebpackOptions").ModuleOptionsNormalized} ModuleOptions */ -/** @typedef {import("../../declarations/WebpackOptions").Node} WebpackNode */ -/** @typedef {import("../../declarations/WebpackOptions").Optimization} Optimization */ -/** @typedef {import("../../declarations/WebpackOptions").OutputNormalized} Output */ -/** @typedef {import("../../declarations/WebpackOptions").Performance} Performance */ -/** @typedef {import("../../declarations/WebpackOptions").ResolveOptions} ResolveOptions */ -/** @typedef {import("../../declarations/WebpackOptions").RuleSetRules} RuleSetRules */ -/** @typedef {import("../../declarations/WebpackOptions").SnapshotOptions} SnapshotOptions */ -/** @typedef {import("../../declarations/WebpackOptions").Target} Target */ -/** @typedef {import("../../declarations/WebpackOptions").WebpackOptionsNormalized} WebpackOptions */ -/** @typedef {import("./target").TargetProperties} TargetProperties */ +/** @typedef {import("./Chunk")} Chunk */ +/** @typedef {import("./Dependency").DependencyLocation} DependencyLocation */ +/** @typedef {import("./Module")} Module */ -const NODE_MODULES_REGEXP = /[\\/]node_modules[\\/]/i; +class WebpackError extends Error { + /** + * Creates an instance of WebpackError. + * @param {string=} message error message + */ + constructor(message) { + super(message); -/** - * Sets a constant default value when undefined - * @template T - * @template {keyof T} P - * @param {T} obj an object - * @param {P} prop a property of this object - * @param {T[P]} value a default value of the property - * @returns {void} - */ -const D = (obj, prop, value) => { - if (obj[prop] === undefined) { - obj[prop] = value; + this.details = undefined; + /** @type {Module} */ + this.module = undefined; + /** @type {DependencyLocation} */ + this.loc = undefined; + /** @type {boolean} */ + this.hideStack = undefined; + /** @type {Chunk} */ + this.chunk = undefined; + /** @type {string} */ + this.file = undefined; } -}; -/** - * Sets a dynamic default value when undefined, by calling the factory function - * @template T - * @template {keyof T} P - * @param {T} obj an object - * @param {P} prop a property of this object - * @param {function(): T[P]} factory a default value factory for the property - * @returns {void} - */ -const F = (obj, prop, factory) => { - if (obj[prop] === undefined) { - obj[prop] = factory(); + [inspect]() { + return this.stack + (this.details ? `\n${this.details}` : ""); } -}; -/** - * Sets a dynamic default value when undefined, by calling the factory function. - * factory must return an array or undefined - * When the current value is already an array an contains "..." it's replaced with - * the result of the factory function - * @template T - * @template {keyof T} P - * @param {T} obj an object - * @param {P} prop a property of this object - * @param {function(): T[P]} factory a default value factory for the property - * @returns {void} - */ -const A = (obj, prop, factory) => { - const value = obj[prop]; - if (value === undefined) { - obj[prop] = factory(); - } else if (Array.isArray(value)) { - /** @type {any[]} */ - let newArray = undefined; - for (let i = 0; i < value.length; i++) { - const item = value[i]; - if (item === "...") { - if (newArray === undefined) { - newArray = value.slice(0, i); - obj[prop] = /** @type {T[P]} */ (/** @type {unknown} */ (newArray)); - } - const items = /** @type {any[]} */ (/** @type {unknown} */ (factory())); - if (items !== undefined) { - for (const item of items) { - newArray.push(item); - } - } - } else if (newArray !== undefined) { - newArray.push(item); - } - } + serialize({ write }) { + write(this.name); + write(this.message); + write(this.stack); + write(this.details); + write(this.loc); + write(this.hideStack); } -}; -/** - * @param {WebpackOptions} options options to be modified - * @returns {void} - */ -const applyWebpackOptionsBaseDefaults = options => { - F(options, "context", () => process.cwd()); - applyInfrastructureLoggingDefaults(options.infrastructureLogging); -}; + deserialize({ read }) { + this.name = read(); + this.message = read(); + this.stack = read(); + this.details = read(); + this.loc = read(); + this.hideStack = read(); + } +} -/** - * @param {WebpackOptions} options options to be modified - * @returns {void} - */ -const applyWebpackOptionsDefaults = options => { - F(options, "context", () => process.cwd()); - F(options, "target", () => { - return getDefaultTarget(options.context); - }); +makeSerializable(WebpackError, "webpack/lib/WebpackError"); - const { mode, name, target } = options; +module.exports = WebpackError; - let targetProperties = - target === false - ? /** @type {false} */ (false) - : typeof target === "string" - ? getTargetProperties(target, options.context) - : getTargetsProperties(target, options.context); - const development = mode === "development"; - const production = mode === "production" || !mode; +/***/ }), - if (typeof options.entry !== "function") { - for (const key of Object.keys(options.entry)) { - F( - options.entry[key], - "import", - () => /** @type {[string]} */ (["./src"]) - ); - } - } +/***/ 60823: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - F(options, "devtool", () => (development ? "eval" : false)); - D(options, "watch", false); - D(options, "profile", false); - D(options, "parallelism", 100); - D(options, "recordsInputPath", false); - D(options, "recordsOutputPath", false); +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Ivan Kopeykin @vankop +*/ - applyExperimentsDefaults(options.experiments, { production, development }); - const futureDefaults = options.experiments.futureDefaults; - F(options, "cache", () => - development ? { type: /** @type {"memory"} */ ("memory") } : false - ); - applyCacheDefaults(options.cache, { - name: name || "default", - mode: mode || "production", - development, - cacheUnaffected: options.experiments.cacheUnaffected - }); - const cache = !!options.cache; +const IgnoreErrorModuleFactory = __webpack_require__(91471); +const WebpackIsIncludedDependency = __webpack_require__(41744); +const { + toConstantDependency +} = __webpack_require__(28723); - applySnapshotDefaults(options.snapshot, { - production, - futureDefaults - }); +/** @typedef {import("enhanced-resolve/lib/Resolver")} Resolver */ +/** @typedef {import("./Compiler")} Compiler */ +/** @typedef {import("./Module")} Module */ +/** @typedef {import("./javascript/JavascriptParser")} JavascriptParser */ - applyModuleDefaults(options.module, { - cache, - syncWebAssembly: options.experiments.syncWebAssembly, - asyncWebAssembly: options.experiments.asyncWebAssembly, - futureDefaults - }); +class WebpackIsIncludedPlugin { + /** + * @param {Compiler} compiler the compiler instance + * @returns {void} + */ + apply(compiler) { + compiler.hooks.compilation.tap( + "WebpackIsIncludedPlugin", + (compilation, { normalModuleFactory }) => { + compilation.dependencyFactories.set( + WebpackIsIncludedDependency, + new IgnoreErrorModuleFactory(normalModuleFactory) + ); + compilation.dependencyTemplates.set( + WebpackIsIncludedDependency, + new WebpackIsIncludedDependency.Template() + ); - applyOutputDefaults(options.output, { - context: options.context, - targetProperties, - isAffectedByBrowserslist: - target === undefined || - (typeof target === "string" && target.startsWith("browserslist")) || - (Array.isArray(target) && - target.some(target => target.startsWith("browserslist"))), - outputModule: options.experiments.outputModule, - development, - entry: options.entry, - module: options.module, - futureDefaults - }); + /** + * @param {JavascriptParser} parser the parser + * @returns {void} + */ + const handler = parser => { + parser.hooks.call + .for("__webpack_is_included__") + .tap("WebpackIsIncludedPlugin", expr => { + if ( + expr.type !== "CallExpression" || + expr.arguments.length !== 1 || + expr.arguments[0].type === "SpreadElement" + ) + return; - applyExternalsPresetsDefaults(options.externalsPresets, { - targetProperties, - buildHttp: !!options.experiments.buildHttp - }); + const request = parser.evaluateExpression(expr.arguments[0]); + + if (!request.isString()) return; + + const dep = new WebpackIsIncludedDependency( + request.string, + expr.range + ); + dep.loc = expr.loc; + parser.state.module.addDependency(dep); + return true; + }); + parser.hooks.typeof + .for("__webpack_is_included__") + .tap( + "WebpackIsIncludedPlugin", + toConstantDependency(parser, JSON.stringify("function")) + ); + }; + normalModuleFactory.hooks.parser + .for("javascript/auto") + .tap("WebpackIsIncludedPlugin", handler); + normalModuleFactory.hooks.parser + .for("javascript/dynamic") + .tap("WebpackIsIncludedPlugin", handler); + normalModuleFactory.hooks.parser + .for("javascript/esm") + .tap("WebpackIsIncludedPlugin", handler); + } + ); + } +} + +module.exports = WebpackIsIncludedPlugin; + + +/***/ }), + +/***/ 44137: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ - applyLoaderDefaults(options.loader, { targetProperties }); - F(options, "externalsType", () => { - const validExternalTypes = __webpack_require__(1863).definitions.ExternalsType.enum; - return options.output.library && - validExternalTypes.includes(options.output.library.type) - ? /** @type {ExternalsType} */ (options.output.library.type) - : options.output.module - ? "module" - : "var"; - }); - applyNodeDefaults(options.node, { - futureDefaults: options.experiments.futureDefaults, - targetProperties - }); +const OptionsApply = __webpack_require__(88104); - F(options, "performance", () => - production && - targetProperties && - (targetProperties.browser || targetProperties.browser === null) - ? {} - : false - ); - applyPerformanceDefaults(options.performance, { - production - }); +const AssetModulesPlugin = __webpack_require__(42553); +const JavascriptModulesPlugin = __webpack_require__(76767); +const JsonModulesPlugin = __webpack_require__(8841); - applyOptimizationDefaults(options.optimization, { - development, - production, - records: !!(options.recordsInputPath || options.recordsOutputPath) - }); +const ChunkPrefetchPreloadPlugin = __webpack_require__(17839); - options.resolve = cleverMerge( - getResolveDefaults({ - cache, - context: options.context, - targetProperties, - mode: options.mode - }), - options.resolve - ); +const EntryOptionPlugin = __webpack_require__(59526); +const RecordIdsPlugin = __webpack_require__(64122); - options.resolveLoader = cleverMerge( - getResolveLoaderDefaults({ cache }), - options.resolveLoader - ); -}; +const RuntimePlugin = __webpack_require__(86809); -/** - * @param {ExperimentsNormalized} experiments options - * @param {Object} options options - * @param {boolean} options.production is production - * @param {boolean} options.development is development mode - * @returns {void} - */ -const applyExperimentsDefaults = (experiments, { production, development }) => { - D(experiments, "futureDefaults", false); - D(experiments, "backCompat", !experiments.futureDefaults); - D(experiments, "topLevelAwait", experiments.futureDefaults); - D(experiments, "syncWebAssembly", false); - D(experiments, "asyncWebAssembly", experiments.futureDefaults); - D(experiments, "outputModule", false); - D(experiments, "layers", false); - D(experiments, "lazyCompilation", undefined); - D(experiments, "buildHttp", undefined); - D(experiments, "cacheUnaffected", experiments.futureDefaults); +const APIPlugin = __webpack_require__(46806); +const CompatibilityPlugin = __webpack_require__(27847); +const ConstPlugin = __webpack_require__(53042); +const ExportsInfoApiPlugin = __webpack_require__(75529); +const WebpackIsIncludedPlugin = __webpack_require__(60823); - if (typeof experiments.buildHttp === "object") { - D(experiments.buildHttp, "frozen", production); - D(experiments.buildHttp, "upgrade", false); - } -}; +const TemplatedPathPlugin = __webpack_require__(54642); +const UseStrictPlugin = __webpack_require__(15466); +const WarnCaseSensitiveModulesPlugin = __webpack_require__(33304); -/** - * @param {CacheOptions} cache options - * @param {Object} options options - * @param {string} options.name name - * @param {string} options.mode mode - * @param {boolean} options.development is development mode - * @param {boolean} options.cacheUnaffected the cacheUnaffected experiment is enabled - * @returns {void} - */ -const applyCacheDefaults = ( - cache, - { name, mode, development, cacheUnaffected } -) => { - if (cache === false) return; - switch (cache.type) { - case "filesystem": - F(cache, "name", () => name + "-" + mode); - D(cache, "version", ""); - F(cache, "cacheDirectory", () => { - const cwd = process.cwd(); - let dir = cwd; - for (;;) { - try { - if (fs.statSync(path.join(dir, "package.json")).isFile()) break; - // eslint-disable-next-line no-empty - } catch (e) {} - const parent = path.dirname(dir); - if (dir === parent) { - dir = undefined; - break; - } - dir = parent; - } - if (!dir) { - return path.resolve(cwd, ".cache/webpack"); - } else if (process.versions.pnp === "1") { - return path.resolve(dir, ".pnp/.cache/webpack"); - } else if (process.versions.pnp === "3") { - return path.resolve(dir, ".yarn/.cache/webpack"); - } else { - return path.resolve(dir, "node_modules/.cache/webpack"); - } - }); - F(cache, "cacheLocation", () => - path.resolve(cache.cacheDirectory, cache.name) - ); - D(cache, "hashAlgorithm", "md4"); - D(cache, "store", "pack"); - D(cache, "compression", false); - D(cache, "profile", false); - D(cache, "idleTimeout", 60000); - D(cache, "idleTimeoutForInitialStore", 5000); - D(cache, "idleTimeoutAfterLargeChanges", 1000); - D(cache, "maxMemoryGenerations", development ? 5 : Infinity); - D(cache, "maxAge", 1000 * 60 * 60 * 24 * 60); // 1 month - D(cache, "allowCollectingMemory", development); - D(cache, "memoryCacheUnaffected", development && cacheUnaffected); - D(cache.buildDependencies, "defaultWebpack", [ - path.resolve(__dirname, "..") + path.sep - ]); - break; - case "memory": - D(cache, "maxGenerations", Infinity); - D(cache, "cacheUnaffected", development && cacheUnaffected); - break; - } -}; +const DataUriPlugin = __webpack_require__(71276); +const FileUriPlugin = __webpack_require__(75275); -/** - * @param {SnapshotOptions} snapshot options - * @param {Object} options options - * @param {boolean} options.production is production - * @param {boolean} options.futureDefaults is future defaults enabled - * @returns {void} - */ -const applySnapshotDefaults = (snapshot, { production, futureDefaults }) => { - if (futureDefaults) { - F(snapshot, "managedPaths", () => - process.versions.pnp === "3" - ? [ - /^(.+?(?:[\\/]\.yarn[\\/]unplugged[\\/][^\\/]+)?[\\/]node_modules[\\/])/ - ] - : [/^(.+?[\\/]node_modules[\\/])/] - ); - F(snapshot, "immutablePaths", () => - process.versions.pnp === "3" - ? [/^(.+?[\\/]cache[\\/][^\\/]+\.zip[\\/]node_modules[\\/])/] - : [] - ); - } else { - A(snapshot, "managedPaths", () => { - if (process.versions.pnp === "3") { - const match = - /^(.+?)[\\/]cache[\\/]watchpack-npm-[^\\/]+\.zip[\\/]node_modules[\\/]/.exec( - /*require.resolve*/(98342) - ); - if (match) { - return [path.resolve(match[1], "unplugged")]; - } - } else { - const match = /^(.+?[\\/]node_modules[\\/])/.exec( - // eslint-disable-next-line node/no-extraneous-require - /*require.resolve*/(98342) - ); - if (match) { - return [match[1]]; - } - } - return []; - }); - A(snapshot, "immutablePaths", () => { - if (process.versions.pnp === "1") { - const match = - /^(.+?[\\/]v4)[\\/]npm-watchpack-[^\\/]+-[\da-f]{40}[\\/]node_modules[\\/]/.exec( - /*require.resolve*/(98342) - ); - if (match) { - return [match[1]]; - } - } else if (process.versions.pnp === "3") { - const match = - /^(.+?)[\\/]watchpack-npm-[^\\/]+\.zip[\\/]node_modules[\\/]/.exec( - /*require.resolve*/(98342) - ); - if (match) { - return [match[1]]; - } - } - return []; - }); - } - F(snapshot, "resolveBuildDependencies", () => ({ - timestamp: true, - hash: true - })); - F(snapshot, "buildDependencies", () => ({ timestamp: true, hash: true })); - F(snapshot, "module", () => - production ? { timestamp: true, hash: true } : { timestamp: true } - ); - F(snapshot, "resolve", () => - production ? { timestamp: true, hash: true } : { timestamp: true } - ); -}; +const ResolverCachePlugin = __webpack_require__(11740); -/** - * @param {JavascriptParserOptions} parserOptions parser options - * @param {Object} options options - * @param {boolean} options.futureDefaults is future defaults enabled - * @returns {void} - */ -const applyJavascriptParserOptionsDefaults = ( - parserOptions, - { futureDefaults } -) => { - D(parserOptions, "unknownContextRequest", "."); - D(parserOptions, "unknownContextRegExp", false); - D(parserOptions, "unknownContextRecursive", true); - D(parserOptions, "unknownContextCritical", true); - D(parserOptions, "exprContextRequest", "."); - D(parserOptions, "exprContextRegExp", false); - D(parserOptions, "exprContextRecursive", true); - D(parserOptions, "exprContextCritical", true); - D(parserOptions, "wrappedContextRegExp", /.*/); - D(parserOptions, "wrappedContextRecursive", true); - D(parserOptions, "wrappedContextCritical", false); - D(parserOptions, "strictThisContextOnImports", false); - if (futureDefaults) D(parserOptions, "exportsPresence", "error"); -}; +const CommonJsPlugin = __webpack_require__(8615); +const HarmonyModulesPlugin = __webpack_require__(73365); +const ImportMetaPlugin = __webpack_require__(81841); +const ImportPlugin = __webpack_require__(77199); +const LoaderPlugin = __webpack_require__(34204); +const RequireContextPlugin = __webpack_require__(30738); +const RequireEnsurePlugin = __webpack_require__(66697); +const RequireIncludePlugin = __webpack_require__(83683); +const SystemPlugin = __webpack_require__(88768); +const URLPlugin = __webpack_require__(97950); +const WorkerPlugin = __webpack_require__(93493); -/** - * @param {ModuleOptions} module options - * @param {Object} options options - * @param {boolean} options.cache is caching enabled - * @param {boolean} options.syncWebAssembly is syncWebAssembly enabled - * @param {boolean} options.asyncWebAssembly is asyncWebAssembly enabled - * @param {boolean} options.futureDefaults is future defaults enabled - * @returns {void} - */ -const applyModuleDefaults = ( - module, - { cache, syncWebAssembly, asyncWebAssembly, futureDefaults } -) => { - if (cache) { - D(module, "unsafeCache", module => { - const name = module.nameForCondition(); - return name && NODE_MODULES_REGEXP.test(name); - }); - } else { - D(module, "unsafeCache", false); - } +const InferAsyncModulesPlugin = __webpack_require__(79471); - F(module.parser, "asset", () => ({})); - F(module.parser.asset, "dataUrlCondition", () => ({})); - if (typeof module.parser.asset.dataUrlCondition === "object") { - D(module.parser.asset.dataUrlCondition, "maxSize", 8096); - } +const JavascriptMetaInfoPlugin = __webpack_require__(38197); +const DefaultStatsFactoryPlugin = __webpack_require__(91293); +const DefaultStatsPresetPlugin = __webpack_require__(2130); +const DefaultStatsPrinterPlugin = __webpack_require__(78303); - F(module.parser, "javascript", () => ({})); - applyJavascriptParserOptionsDefaults(module.parser.javascript, { - futureDefaults - }); +const { cleverMerge } = __webpack_require__(11217); - A(module, "defaultRules", () => { - const esm = { - type: "javascript/esm", - resolve: { - byDependency: { - esm: { - fullySpecified: true - } - } - } - }; - const commonjs = { - type: "javascript/dynamic" - }; - /** @type {RuleSetRules} */ - const rules = [ - { - mimetype: "application/node", - type: "javascript/auto" - }, - { - test: /\.json$/i, - type: "json" - }, - { - mimetype: "application/json", - type: "json" - }, - { - test: /\.mjs$/i, - ...esm - }, - { - test: /\.js$/i, - descriptionData: { - type: "module" - }, - ...esm - }, - { - test: /\.cjs$/i, - ...commonjs - }, - { - test: /\.js$/i, - descriptionData: { - type: "commonjs" - }, - ...commonjs - }, - { - mimetype: { - or: ["text/javascript", "application/javascript"] - }, - ...esm - } - ]; - if (asyncWebAssembly) { - const wasm = { - type: "webassembly/async", - rules: [ - { - descriptionData: { - type: "module" - }, - resolve: { - fullySpecified: true - } - } - ] - }; - rules.push({ - test: /\.wasm$/i, - ...wasm - }); - rules.push({ - mimetype: "application/wasm", - ...wasm - }); - } else if (syncWebAssembly) { - const wasm = { - type: "webassembly/sync", - rules: [ - { - descriptionData: { - type: "module" - }, - resolve: { - fullySpecified: true - } - } - ] - }; - rules.push({ - test: /\.wasm$/i, - ...wasm - }); - rules.push({ - mimetype: "application/wasm", - ...wasm - }); - } - rules.push( - { - dependency: "url", - oneOf: [ - { - scheme: /^data$/, - type: "asset/inline" - }, - { - type: "asset/resource" - } - ] - }, - { - assert: { type: "json" }, - type: "json" - } - ); - return rules; - }); -}; +/** @typedef {import("../declarations/WebpackOptions").WebpackOptionsNormalized} WebpackOptions */ +/** @typedef {import("./Compiler")} Compiler */ -/** - * @param {Output} output options - * @param {Object} options options - * @param {string} options.context context - * @param {TargetProperties | false} options.targetProperties target properties - * @param {boolean} options.isAffectedByBrowserslist is affected by browserslist - * @param {boolean} options.outputModule is outputModule experiment enabled - * @param {boolean} options.development is development mode - * @param {Entry} options.entry entry option - * @param {ModuleOptions} options.module module option - * @param {boolean} options.futureDefaults is future defaults enabled - * @returns {void} - */ -const applyOutputDefaults = ( - output, - { - context, - targetProperties: tp, - isAffectedByBrowserslist, - outputModule, - development, - entry, - module, - futureDefaults +class WebpackOptionsApply extends OptionsApply { + constructor() { + super(); } -) => { + /** - * @param {Library=} library the library option - * @returns {string} a readable library name + * @param {WebpackOptions} options options object + * @param {Compiler} compiler compiler object + * @returns {WebpackOptions} options object */ - const getLibraryName = library => { - const libraryName = - typeof library === "object" && - library && - !Array.isArray(library) && - "type" in library - ? library.name - : /** @type {LibraryName=} */ (library); - if (Array.isArray(libraryName)) { - return libraryName.join("."); - } else if (typeof libraryName === "object") { - return getLibraryName(libraryName.root); - } else if (typeof libraryName === "string") { - return libraryName; + process(options, compiler) { + compiler.outputPath = options.output.path; + compiler.recordsInputPath = options.recordsInputPath || null; + compiler.recordsOutputPath = options.recordsOutputPath || null; + compiler.name = options.name; + + if (options.externals) { + //@ts-expect-error https://github.com/microsoft/TypeScript/issues/41697 + const ExternalsPlugin = __webpack_require__(361); + new ExternalsPlugin(options.externalsType, options.externals).apply( + compiler + ); + } + + if (options.externalsPresets.node) { + const NodeTargetPlugin = __webpack_require__(28037); + new NodeTargetPlugin().apply(compiler); + } + if (options.externalsPresets.electronMain) { + //@ts-expect-error https://github.com/microsoft/TypeScript/issues/41697 + const ElectronTargetPlugin = __webpack_require__(88362); + new ElectronTargetPlugin("main").apply(compiler); + } + if (options.externalsPresets.electronPreload) { + //@ts-expect-error https://github.com/microsoft/TypeScript/issues/41697 + const ElectronTargetPlugin = __webpack_require__(88362); + new ElectronTargetPlugin("preload").apply(compiler); + } + if (options.externalsPresets.electronRenderer) { + //@ts-expect-error https://github.com/microsoft/TypeScript/issues/41697 + const ElectronTargetPlugin = __webpack_require__(88362); + new ElectronTargetPlugin("renderer").apply(compiler); + } + if ( + options.externalsPresets.electron && + !options.externalsPresets.electronMain && + !options.externalsPresets.electronPreload && + !options.externalsPresets.electronRenderer + ) { + //@ts-expect-error https://github.com/microsoft/TypeScript/issues/41697 + const ElectronTargetPlugin = __webpack_require__(88362); + new ElectronTargetPlugin().apply(compiler); + } + if (options.externalsPresets.nwjs) { + //@ts-expect-error https://github.com/microsoft/TypeScript/issues/41697 + const ExternalsPlugin = __webpack_require__(361); + new ExternalsPlugin("node-commonjs", "nw.gui").apply(compiler); + } + if (options.externalsPresets.webAsync) { + //@ts-expect-error https://github.com/microsoft/TypeScript/issues/41697 + const ExternalsPlugin = __webpack_require__(361); + new ExternalsPlugin("import", /^(https?:\/\/|std:)/).apply(compiler); + } else if (options.externalsPresets.web) { + //@ts-expect-error https://github.com/microsoft/TypeScript/issues/41697 + const ExternalsPlugin = __webpack_require__(361); + new ExternalsPlugin("module", /^(https?:\/\/|std:)/).apply(compiler); } - return ""; - }; - F(output, "uniqueName", () => { - const libraryName = getLibraryName(output.library); - if (libraryName) return libraryName; - const pkgPath = path.resolve(context, "package.json"); - try { - const packageInfo = JSON.parse(fs.readFileSync(pkgPath, "utf-8")); - return packageInfo.name || ""; - } catch (e) { - if (e.code !== "ENOENT") { - e.message += `\nwhile determining default 'output.uniqueName' from 'name' in ${pkgPath}`; - throw e; + new ChunkPrefetchPreloadPlugin().apply(compiler); + + if (typeof options.output.chunkFormat === "string") { + switch (options.output.chunkFormat) { + case "array-push": { + const ArrayPushCallbackChunkFormatPlugin = __webpack_require__(86189); + new ArrayPushCallbackChunkFormatPlugin().apply(compiler); + break; + } + case "commonjs": { + const CommonJsChunkFormatPlugin = __webpack_require__(57634); + new CommonJsChunkFormatPlugin().apply(compiler); + break; + } + case "module": { + const ModuleChunkFormatPlugin = __webpack_require__(29181); + new ModuleChunkFormatPlugin().apply(compiler); + break; + } + default: + throw new Error( + "Unsupported chunk format '" + options.output.chunkFormat + "'." + ); } - return ""; } - }); - F(output, "module", () => !!outputModule); - D(output, "filename", output.module ? "[name].mjs" : "[name].js"); - F(output, "iife", () => !output.module); - D(output, "importFunctionName", "import"); - D(output, "importMetaName", "import.meta"); - F(output, "chunkFilename", () => { - const filename = output.filename; - if (typeof filename !== "function") { - const hasName = filename.includes("[name]"); - const hasId = filename.includes("[id]"); - const hasChunkHash = filename.includes("[chunkhash]"); - const hasContentHash = filename.includes("[contenthash]"); - // Anything changing depending on chunk is fine - if (hasChunkHash || hasContentHash || hasName || hasId) return filename; - // Otherwise prefix "[id]." in front of the basename to make it changing - return filename.replace(/(^|\/)([^/]*(?:\?|$))/, "$1[id].$2"); + if (options.output.enabledChunkLoadingTypes.length > 0) { + for (const type of options.output.enabledChunkLoadingTypes) { + const EnableChunkLoadingPlugin = __webpack_require__(34726); + new EnableChunkLoadingPlugin(type).apply(compiler); + } } - return output.module ? "[id].mjs" : "[id].js"; - }); - D(output, "assetModuleFilename", "[hash][ext][query]"); - D(output, "webassemblyModuleFilename", "[hash].module.wasm"); - D(output, "compareBeforeEmit", true); - D(output, "charset", true); - F(output, "hotUpdateGlobal", () => - Template.toIdentifier( - "webpackHotUpdate" + Template.toIdentifier(output.uniqueName) - ) - ); - F(output, "chunkLoadingGlobal", () => - Template.toIdentifier( - "webpackChunk" + Template.toIdentifier(output.uniqueName) - ) - ); - F(output, "globalObject", () => { - if (tp) { - if (tp.global) return "global"; - if (tp.globalThis) return "globalThis"; + + if (options.output.enabledWasmLoadingTypes.length > 0) { + for (const type of options.output.enabledWasmLoadingTypes) { + const EnableWasmLoadingPlugin = __webpack_require__(93943); + new EnableWasmLoadingPlugin(type).apply(compiler); + } } - return "self"; - }); - F(output, "chunkFormat", () => { - if (tp) { - const helpMessage = isAffectedByBrowserslist - ? "Make sure that your 'browserslist' includes only platforms that support these features or select an appropriate 'target' to allow selecting a chunk format by default. Alternatively specify the 'output.chunkFormat' directly." - : "Select an appropriate 'target' to allow selecting one by default, or specify the 'output.chunkFormat' directly."; - if (output.module) { - if (tp.dynamicImport) return "module"; - if (tp.document) return "array-push"; + + if (options.output.enabledLibraryTypes.length > 0) { + for (const type of options.output.enabledLibraryTypes) { + const EnableLibraryPlugin = __webpack_require__(35613); + new EnableLibraryPlugin(type).apply(compiler); + } + } + + if (options.output.pathinfo) { + const ModuleInfoHeaderPlugin = __webpack_require__(45095); + new ModuleInfoHeaderPlugin(options.output.pathinfo !== true).apply( + compiler + ); + } + + if (options.output.clean) { + const CleanPlugin = __webpack_require__(49129); + new CleanPlugin( + options.output.clean === true ? {} : options.output.clean + ).apply(compiler); + } + + if (options.devtool) { + if (options.devtool.includes("source-map")) { + const hidden = options.devtool.includes("hidden"); + const inline = options.devtool.includes("inline"); + const evalWrapped = options.devtool.includes("eval"); + const cheap = options.devtool.includes("cheap"); + const moduleMaps = options.devtool.includes("module"); + const noSources = options.devtool.includes("nosources"); + const Plugin = evalWrapped + ? __webpack_require__(42053) + : __webpack_require__(79917); + new Plugin({ + filename: inline ? null : options.output.sourceMapFilename, + moduleFilenameTemplate: options.output.devtoolModuleFilenameTemplate, + fallbackModuleFilenameTemplate: + options.output.devtoolFallbackModuleFilenameTemplate, + append: hidden ? false : undefined, + module: moduleMaps ? true : cheap ? false : true, + columns: cheap ? false : true, + noSources: noSources, + namespace: options.output.devtoolNamespace + }).apply(compiler); + } else if (options.devtool.includes("eval")) { + const EvalDevToolModulePlugin = __webpack_require__(4125); + new EvalDevToolModulePlugin({ + moduleFilenameTemplate: options.output.devtoolModuleFilenameTemplate, + namespace: options.output.devtoolNamespace + }).apply(compiler); + } + } + + new JavascriptModulesPlugin().apply(compiler); + new JsonModulesPlugin().apply(compiler); + new AssetModulesPlugin().apply(compiler); + + if (!options.experiments.outputModule) { + if (options.output.module) { throw new Error( - "For the selected environment is no default ESM chunk format available:\n" + - "ESM exports can be chosen when 'import()' is available.\n" + - "JSONP Array push can be chosen when 'document' is available.\n" + - helpMessage + "'output.module: true' is only allowed when 'experiments.outputModule' is enabled" ); - } else { - if (tp.document) return "array-push"; - if (tp.require) return "commonjs"; - if (tp.nodeBuiltins) return "commonjs"; - if (tp.importScripts) return "array-push"; + } + if (options.output.enabledLibraryTypes.includes("module")) { throw new Error( - "For the selected environment is no default script chunk format available:\n" + - "JSONP Array push can be chosen when 'document' or 'importScripts' is available.\n" + - "CommonJs exports can be chosen when 'require' or node builtins are available.\n" + - helpMessage + "library type \"module\" is only allowed when 'experiments.outputModule' is enabled" ); } - } - throw new Error( - "Chunk format can't be selected by default when no target is specified" - ); - }); - D(output, "asyncChunks", true); - F(output, "chunkLoading", () => { - if (tp) { - switch (output.chunkFormat) { - case "array-push": - if (tp.document) return "jsonp"; - if (tp.importScripts) return "import-scripts"; - break; - case "commonjs": - if (tp.require) return "require"; - if (tp.nodeBuiltins) return "async-node"; - break; - case "module": - if (tp.dynamicImport) return "import"; - break; - } - if ( - tp.require === null || - tp.nodeBuiltins === null || - tp.document === null || - tp.importScripts === null - ) { - return "universal"; + if (options.externalsType === "module") { + throw new Error( + "'externalsType: \"module\"' is only allowed when 'experiments.outputModule' is enabled" + ); } } - return false; - }); - F(output, "workerChunkLoading", () => { - if (tp) { - switch (output.chunkFormat) { - case "array-push": - if (tp.importScriptsInWorker) return "import-scripts"; - break; - case "commonjs": - if (tp.require) return "require"; - if (tp.nodeBuiltins) return "async-node"; - break; - case "module": - if (tp.dynamicImportInWorker) return "import"; - break; - } - if ( - tp.require === null || - tp.nodeBuiltins === null || - tp.importScriptsInWorker === null - ) { - return "universal"; - } + + if (options.experiments.syncWebAssembly) { + const WebAssemblyModulesPlugin = __webpack_require__(93813); + new WebAssemblyModulesPlugin({ + mangleImports: options.optimization.mangleWasmImports + }).apply(compiler); } - return false; - }); - F(output, "wasmLoading", () => { - if (tp) { - if (tp.fetchWasm) return "fetch"; - if (tp.nodeBuiltins) - return output.module ? "async-node-module" : "async-node"; - if (tp.nodeBuiltins === null || tp.fetchWasm === null) { - return "universal"; - } + + if (options.experiments.asyncWebAssembly) { + const AsyncWebAssemblyModulesPlugin = __webpack_require__(13804); + new AsyncWebAssemblyModulesPlugin({ + mangleImports: options.optimization.mangleWasmImports + }).apply(compiler); } - return false; - }); - F(output, "workerWasmLoading", () => output.wasmLoading); - F(output, "devtoolNamespace", () => output.uniqueName); - if (output.library) { - F(output.library, "type", () => (output.module ? "module" : "var")); - } - F(output, "path", () => path.join(process.cwd(), "dist")); - F(output, "pathinfo", () => development); - D(output, "sourceMapFilename", "[file].map[query]"); - D( - output, - "hotUpdateChunkFilename", - `[id].[fullhash].hot-update.${output.module ? "mjs" : "js"}` - ); - D(output, "hotUpdateMainFilename", "[runtime].[fullhash].hot-update.json"); - D(output, "crossOriginLoading", false); - F(output, "scriptType", () => (output.module ? "module" : false)); - D( - output, - "publicPath", - (tp && (tp.document || tp.importScripts)) || output.scriptType === "module" - ? "auto" - : "" - ); - D(output, "chunkLoadTimeout", 120000); - D(output, "hashFunction", futureDefaults ? "xxhash64" : "md4"); - D(output, "hashDigest", "hex"); - D(output, "hashDigestLength", 20); - D(output, "strictModuleExceptionHandling", false); - const optimistic = v => v || v === undefined; - F( - output.environment, - "arrowFunction", - () => tp && optimistic(tp.arrowFunction) - ); - F(output.environment, "const", () => tp && optimistic(tp.const)); - F( - output.environment, - "destructuring", - () => tp && optimistic(tp.destructuring) - ); - F(output.environment, "forOf", () => tp && optimistic(tp.forOf)); - F(output.environment, "bigIntLiteral", () => tp && tp.bigIntLiteral); - F(output.environment, "dynamicImport", () => tp && tp.dynamicImport); - F(output.environment, "module", () => tp && tp.module); + if (options.experiments.lazyCompilation) { + const LazyCompilationPlugin = __webpack_require__(70839); + const lazyOptions = + typeof options.experiments.lazyCompilation === "object" + ? options.experiments.lazyCompilation + : null; + new LazyCompilationPlugin({ + backend: + typeof lazyOptions.backend === "function" + ? lazyOptions.backend + : __webpack_require__(46574)({ + ...lazyOptions.backend, + client: + (lazyOptions.backend && lazyOptions.backend.client) || + options.externalsPresets.node ? __webpack_require__.ab + "lazy-compilation-node.js" : __webpack_require__.ab + "lazy-compilation-web.js" + }), + entries: !lazyOptions || lazyOptions.entries !== false, + imports: !lazyOptions || lazyOptions.imports !== false, + test: (lazyOptions && lazyOptions.test) || undefined + }).apply(compiler); + } - const { trustedTypes } = output; - if (trustedTypes) { - F( - trustedTypes, - "policyName", - () => - output.uniqueName.replace(/[^a-zA-Z0-9\-#=_/@.%]+/g, "_") || "webpack" - ); - } + if (options.experiments.buildHttp) { + const HttpUriPlugin = __webpack_require__(34747); + const httpOptions = options.experiments.buildHttp; + new HttpUriPlugin(httpOptions).apply(compiler); + } - /** - * @param {function(EntryDescription): void} fn iterator - * @returns {void} - */ - const forEachEntry = fn => { - for (const name of Object.keys(entry)) { - fn(entry[name]); + new EntryOptionPlugin().apply(compiler); + compiler.hooks.entryOption.call(options.context, options.entry); + + new RuntimePlugin().apply(compiler); + + new InferAsyncModulesPlugin().apply(compiler); + + new DataUriPlugin().apply(compiler); + new FileUriPlugin().apply(compiler); + + new CompatibilityPlugin().apply(compiler); + new HarmonyModulesPlugin({ + topLevelAwait: options.experiments.topLevelAwait + }).apply(compiler); + if (options.amd !== false) { + const AMDPlugin = __webpack_require__(82916); + const RequireJsStuffPlugin = __webpack_require__(81898); + new AMDPlugin(options.amd || {}).apply(compiler); + new RequireJsStuffPlugin().apply(compiler); } - }; - A(output, "enabledLibraryTypes", () => { - const enabledLibraryTypes = []; - if (output.library) { - enabledLibraryTypes.push(output.library.type); + new CommonJsPlugin().apply(compiler); + new LoaderPlugin({}).apply(compiler); + if (options.node !== false) { + const NodeStuffPlugin = __webpack_require__(14290); + new NodeStuffPlugin(options.node).apply(compiler); } - forEachEntry(desc => { - if (desc.library) { - enabledLibraryTypes.push(desc.library.type); - } - }); - return enabledLibraryTypes; - }); + new APIPlugin().apply(compiler); + new ExportsInfoApiPlugin().apply(compiler); + new WebpackIsIncludedPlugin().apply(compiler); + new ConstPlugin().apply(compiler); + new UseStrictPlugin().apply(compiler); + new RequireIncludePlugin().apply(compiler); + new RequireEnsurePlugin().apply(compiler); + new RequireContextPlugin().apply(compiler); + new ImportPlugin().apply(compiler); + new SystemPlugin().apply(compiler); + new ImportMetaPlugin().apply(compiler); + new URLPlugin().apply(compiler); + new WorkerPlugin( + options.output.workerChunkLoading, + options.output.workerWasmLoading, + options.output.module + ).apply(compiler); - A(output, "enabledChunkLoadingTypes", () => { - const enabledChunkLoadingTypes = new Set(); - if (output.chunkLoading) { - enabledChunkLoadingTypes.add(output.chunkLoading); + new DefaultStatsFactoryPlugin().apply(compiler); + new DefaultStatsPresetPlugin().apply(compiler); + new DefaultStatsPrinterPlugin().apply(compiler); + + new JavascriptMetaInfoPlugin().apply(compiler); + + if (typeof options.mode !== "string") { + const WarnNoModeSetPlugin = __webpack_require__(70308); + new WarnNoModeSetPlugin().apply(compiler); } - if (output.workerChunkLoading) { - enabledChunkLoadingTypes.add(output.workerChunkLoading); + + const EnsureChunkConditionsPlugin = __webpack_require__(91120); + new EnsureChunkConditionsPlugin().apply(compiler); + if (options.optimization.removeAvailableModules) { + const RemoveParentModulesPlugin = __webpack_require__(75072); + new RemoveParentModulesPlugin().apply(compiler); + } + if (options.optimization.removeEmptyChunks) { + const RemoveEmptyChunksPlugin = __webpack_require__(66290); + new RemoveEmptyChunksPlugin().apply(compiler); + } + if (options.optimization.mergeDuplicateChunks) { + const MergeDuplicateChunksPlugin = __webpack_require__(54450); + new MergeDuplicateChunksPlugin().apply(compiler); + } + if (options.optimization.flagIncludedChunks) { + const FlagIncludedChunksPlugin = __webpack_require__(48424); + new FlagIncludedChunksPlugin().apply(compiler); + } + if (options.optimization.sideEffects) { + const SideEffectsFlagPlugin = __webpack_require__(47844); + new SideEffectsFlagPlugin( + options.optimization.sideEffects === true + ).apply(compiler); + } + if (options.optimization.providedExports) { + const FlagDependencyExportsPlugin = __webpack_require__(395); + new FlagDependencyExportsPlugin().apply(compiler); + } + if (options.optimization.usedExports) { + const FlagDependencyUsagePlugin = __webpack_require__(13104); + new FlagDependencyUsagePlugin( + options.optimization.usedExports === "global" + ).apply(compiler); + } + if (options.optimization.innerGraph) { + const InnerGraphPlugin = __webpack_require__(57997); + new InnerGraphPlugin().apply(compiler); + } + if (options.optimization.mangleExports) { + const MangleExportsPlugin = __webpack_require__(7281); + new MangleExportsPlugin( + options.optimization.mangleExports !== "size" + ).apply(compiler); + } + if (options.optimization.concatenateModules) { + const ModuleConcatenationPlugin = __webpack_require__(29585); + new ModuleConcatenationPlugin().apply(compiler); + } + if (options.optimization.splitChunks) { + const SplitChunksPlugin = __webpack_require__(57073); + new SplitChunksPlugin(options.optimization.splitChunks).apply(compiler); + } + if (options.optimization.runtimeChunk) { + const RuntimeChunkPlugin = __webpack_require__(23821); + new RuntimeChunkPlugin(options.optimization.runtimeChunk).apply(compiler); + } + if (!options.optimization.emitOnErrors) { + const NoEmitOnErrorsPlugin = __webpack_require__(70760); + new NoEmitOnErrorsPlugin().apply(compiler); + } + if (options.optimization.realContentHash) { + const RealContentHashPlugin = __webpack_require__(6669); + new RealContentHashPlugin({ + hashFunction: options.output.hashFunction, + hashDigest: options.output.hashDigest + }).apply(compiler); + } + if (options.optimization.checkWasmTypes) { + const WasmFinalizeExportsPlugin = __webpack_require__(12995); + new WasmFinalizeExportsPlugin().apply(compiler); + } + const moduleIds = options.optimization.moduleIds; + if (moduleIds) { + switch (moduleIds) { + case "natural": { + const NaturalModuleIdsPlugin = __webpack_require__(96338); + new NaturalModuleIdsPlugin().apply(compiler); + break; + } + case "named": { + const NamedModuleIdsPlugin = __webpack_require__(88514); + new NamedModuleIdsPlugin().apply(compiler); + break; + } + case "hashed": { + const WarnDeprecatedOptionPlugin = __webpack_require__(85024); + const HashedModuleIdsPlugin = __webpack_require__(83635); + new WarnDeprecatedOptionPlugin( + "optimization.moduleIds", + "hashed", + "deterministic" + ).apply(compiler); + new HashedModuleIdsPlugin({ + hashFunction: options.output.hashFunction + }).apply(compiler); + break; + } + case "deterministic": { + const DeterministicModuleIdsPlugin = __webpack_require__(84965); + new DeterministicModuleIdsPlugin().apply(compiler); + break; + } + case "size": { + const OccurrenceModuleIdsPlugin = __webpack_require__(128); + new OccurrenceModuleIdsPlugin({ + prioritiseInitial: true + }).apply(compiler); + break; + } + default: + throw new Error( + `webpack bug: moduleIds: ${moduleIds} is not implemented` + ); + } } - forEachEntry(desc => { - if (desc.chunkLoading) { - enabledChunkLoadingTypes.add(desc.chunkLoading); + const chunkIds = options.optimization.chunkIds; + if (chunkIds) { + switch (chunkIds) { + case "natural": { + const NaturalChunkIdsPlugin = __webpack_require__(18326); + new NaturalChunkIdsPlugin().apply(compiler); + break; + } + case "named": { + const NamedChunkIdsPlugin = __webpack_require__(30483); + new NamedChunkIdsPlugin().apply(compiler); + break; + } + case "deterministic": { + const DeterministicChunkIdsPlugin = __webpack_require__(64801); + new DeterministicChunkIdsPlugin().apply(compiler); + break; + } + case "size": { + //@ts-expect-error https://github.com/microsoft/TypeScript/issues/41697 + const OccurrenceChunkIdsPlugin = __webpack_require__(98702); + new OccurrenceChunkIdsPlugin({ + prioritiseInitial: true + }).apply(compiler); + break; + } + case "total-size": { + //@ts-expect-error https://github.com/microsoft/TypeScript/issues/41697 + const OccurrenceChunkIdsPlugin = __webpack_require__(98702); + new OccurrenceChunkIdsPlugin({ + prioritiseInitial: false + }).apply(compiler); + break; + } + default: + throw new Error( + `webpack bug: chunkIds: ${chunkIds} is not implemented` + ); } - }); - return Array.from(enabledChunkLoadingTypes); - }); - - A(output, "enabledWasmLoadingTypes", () => { - const enabledWasmLoadingTypes = new Set(); - if (output.wasmLoading) { - enabledWasmLoadingTypes.add(output.wasmLoading); } - if (output.workerWasmLoading) { - enabledWasmLoadingTypes.add(output.workerWasmLoading); + if (options.optimization.nodeEnv) { + const DefinePlugin = __webpack_require__(46754); + new DefinePlugin({ + "process.env.NODE_ENV": JSON.stringify(options.optimization.nodeEnv) + }).apply(compiler); } - forEachEntry(desc => { - if (desc.wasmLoading) { - enabledWasmLoadingTypes.add(desc.wasmLoading); + if (options.optimization.minimize) { + for (const minimizer of options.optimization.minimizer) { + if (typeof minimizer === "function") { + minimizer.call(compiler, compiler); + } else if (minimizer !== "...") { + minimizer.apply(compiler); + } } - }); - return Array.from(enabledWasmLoadingTypes); - }); -}; - -/** - * @param {ExternalsPresets} externalsPresets options - * @param {Object} options options - * @param {TargetProperties | false} options.targetProperties target properties - * @param {boolean} options.buildHttp buildHttp experiment enabled - * @returns {void} - */ -const applyExternalsPresetsDefaults = ( - externalsPresets, - { targetProperties, buildHttp } -) => { - D( - externalsPresets, - "web", - !buildHttp && targetProperties && targetProperties.web - ); - D(externalsPresets, "node", targetProperties && targetProperties.node); - D(externalsPresets, "nwjs", targetProperties && targetProperties.nwjs); - D( - externalsPresets, - "electron", - targetProperties && targetProperties.electron - ); - D( - externalsPresets, - "electronMain", - targetProperties && - targetProperties.electron && - targetProperties.electronMain - ); - D( - externalsPresets, - "electronPreload", - targetProperties && - targetProperties.electron && - targetProperties.electronPreload - ); - D( - externalsPresets, - "electronRenderer", - targetProperties && - targetProperties.electron && - targetProperties.electronRenderer - ); -}; + } -/** - * @param {Loader} loader options - * @param {Object} options options - * @param {TargetProperties | false} options.targetProperties target properties - * @returns {void} - */ -const applyLoaderDefaults = (loader, { targetProperties }) => { - F(loader, "target", () => { - if (targetProperties) { - if (targetProperties.electron) { - if (targetProperties.electronMain) return "electron-main"; - if (targetProperties.electronPreload) return "electron-preload"; - if (targetProperties.electronRenderer) return "electron-renderer"; - return "electron"; - } - if (targetProperties.nwjs) return "nwjs"; - if (targetProperties.node) return "node"; - if (targetProperties.web) return "web"; + if (options.performance) { + const SizeLimitsPlugin = __webpack_require__(64025); + new SizeLimitsPlugin(options.performance).apply(compiler); } - }); -}; -/** - * @param {WebpackNode} node options - * @param {Object} options options - * @param {TargetProperties | false} options.targetProperties target properties - * @param {boolean} options.futureDefaults is future defaults enabled - * @returns {void} - */ -const applyNodeDefaults = (node, { futureDefaults, targetProperties }) => { - if (node === false) return; + new TemplatedPathPlugin().apply(compiler); - F(node, "global", () => { - if (targetProperties && targetProperties.global) return false; - // TODO webpack 6 should always default to false - return futureDefaults ? "warn" : true; - }); - F(node, "__filename", () => { - if (targetProperties && targetProperties.node) return "eval-only"; - // TODO webpack 6 should always default to false - return futureDefaults ? "warn-mock" : "mock"; - }); - F(node, "__dirname", () => { - if (targetProperties && targetProperties.node) return "eval-only"; - // TODO webpack 6 should always default to false - return futureDefaults ? "warn-mock" : "mock"; - }); -}; + new RecordIdsPlugin({ + portableIds: options.optimization.portableRecords + }).apply(compiler); -/** - * @param {Performance} performance options - * @param {Object} options options - * @param {boolean} options.production is production - * @returns {void} - */ -const applyPerformanceDefaults = (performance, { production }) => { - if (performance === false) return; - D(performance, "maxAssetSize", 250000); - D(performance, "maxEntrypointSize", 250000); - F(performance, "hints", () => (production ? "warning" : false)); -}; + new WarnCaseSensitiveModulesPlugin().apply(compiler); -/** - * @param {Optimization} optimization options - * @param {Object} options options - * @param {boolean} options.production is production - * @param {boolean} options.development is development - * @param {boolean} options.records using records - * @returns {void} - */ -const applyOptimizationDefaults = ( - optimization, - { production, development, records } -) => { - D(optimization, "removeAvailableModules", false); - D(optimization, "removeEmptyChunks", true); - D(optimization, "mergeDuplicateChunks", true); - D(optimization, "flagIncludedChunks", production); - F(optimization, "moduleIds", () => { - if (production) return "deterministic"; - if (development) return "named"; - return "natural"; - }); - F(optimization, "chunkIds", () => { - if (production) return "deterministic"; - if (development) return "named"; - return "natural"; - }); - F(optimization, "sideEffects", () => (production ? true : "flag")); - D(optimization, "providedExports", true); - D(optimization, "usedExports", production); - D(optimization, "innerGraph", production); - D(optimization, "mangleExports", production); - D(optimization, "concatenateModules", production); - D(optimization, "runtimeChunk", false); - D(optimization, "emitOnErrors", !production); - D(optimization, "checkWasmTypes", production); - D(optimization, "mangleWasmImports", false); - D(optimization, "portableRecords", records); - D(optimization, "realContentHash", production); - D(optimization, "minimize", production); - A(optimization, "minimizer", () => [ - { - apply: compiler => { - // Lazy load the Terser plugin - const TerserPlugin = __webpack_require__(56052); - new TerserPlugin({ - terserOptions: { - compress: { - passes: 2 + const AddManagedPathsPlugin = __webpack_require__(19724); + new AddManagedPathsPlugin( + options.snapshot.managedPaths, + options.snapshot.immutablePaths + ).apply(compiler); + + if (options.cache && typeof options.cache === "object") { + const cacheOptions = options.cache; + switch (cacheOptions.type) { + case "memory": { + if (isFinite(cacheOptions.maxGenerations)) { + //@ts-expect-error https://github.com/microsoft/TypeScript/issues/41697 + const MemoryWithGcCachePlugin = __webpack_require__(34854); + new MemoryWithGcCachePlugin({ + maxGenerations: cacheOptions.maxGenerations + }).apply(compiler); + } else { + //@ts-expect-error https://github.com/microsoft/TypeScript/issues/41697 + const MemoryCachePlugin = __webpack_require__(4045); + new MemoryCachePlugin().apply(compiler); + } + if (cacheOptions.cacheUnaffected) { + if (!options.experiments.cacheUnaffected) { + throw new Error( + "'cache.cacheUnaffected: true' is only allowed when 'experiments.cacheUnaffected' is enabled" + ); } + compiler.moduleMemCaches = new Map(); } - }).apply(compiler); + break; + } + case "filesystem": { + const AddBuildDependenciesPlugin = __webpack_require__(30743); + for (const key in cacheOptions.buildDependencies) { + const list = cacheOptions.buildDependencies[key]; + new AddBuildDependenciesPlugin(list).apply(compiler); + } + if (!isFinite(cacheOptions.maxMemoryGenerations)) { + //@ts-expect-error https://github.com/microsoft/TypeScript/issues/41697 + const MemoryCachePlugin = __webpack_require__(4045); + new MemoryCachePlugin().apply(compiler); + } else if (cacheOptions.maxMemoryGenerations !== 0) { + //@ts-expect-error https://github.com/microsoft/TypeScript/issues/41697 + const MemoryWithGcCachePlugin = __webpack_require__(34854); + new MemoryWithGcCachePlugin({ + maxGenerations: cacheOptions.maxMemoryGenerations + }).apply(compiler); + } + if (cacheOptions.memoryCacheUnaffected) { + if (!options.experiments.cacheUnaffected) { + throw new Error( + "'cache.memoryCacheUnaffected: true' is only allowed when 'experiments.cacheUnaffected' is enabled" + ); + } + compiler.moduleMemCaches = new Map(); + } + switch (cacheOptions.store) { + case "pack": { + const IdleFileCachePlugin = __webpack_require__(26277); + const PackFileCacheStrategy = __webpack_require__(46810); + new IdleFileCachePlugin( + new PackFileCacheStrategy({ + compiler, + fs: compiler.intermediateFileSystem, + context: options.context, + cacheLocation: cacheOptions.cacheLocation, + version: cacheOptions.version, + logger: compiler.getInfrastructureLogger( + "webpack.cache.PackFileCacheStrategy" + ), + snapshot: options.snapshot, + maxAge: cacheOptions.maxAge, + profile: cacheOptions.profile, + allowCollectingMemory: cacheOptions.allowCollectingMemory, + compression: cacheOptions.compression + }), + cacheOptions.idleTimeout, + cacheOptions.idleTimeoutForInitialStore, + cacheOptions.idleTimeoutAfterLargeChanges + ).apply(compiler); + break; + } + default: + throw new Error("Unhandled value for cache.store"); + } + break; + } + default: + // @ts-expect-error Property 'type' does not exist on type 'never'. ts(2339) + throw new Error(`Unknown cache type ${cacheOptions.type}`); } } - ]); - F(optimization, "nodeEnv", () => { - if (production) return "production"; - if (development) return "development"; - return false; - }); - const { splitChunks } = optimization; - if (splitChunks) { - A(splitChunks, "defaultSizeTypes", () => ["javascript", "unknown"]); - D(splitChunks, "hidePathInfo", production); - D(splitChunks, "chunks", "async"); - D(splitChunks, "usedExports", optimization.usedExports === true); - D(splitChunks, "minChunks", 1); - F(splitChunks, "minSize", () => (production ? 20000 : 10000)); - F(splitChunks, "minRemainingSize", () => (development ? 0 : undefined)); - F(splitChunks, "enforceSizeThreshold", () => (production ? 50000 : 30000)); - F(splitChunks, "maxAsyncRequests", () => (production ? 30 : Infinity)); - F(splitChunks, "maxInitialRequests", () => (production ? 30 : Infinity)); - D(splitChunks, "automaticNameDelimiter", "-"); - const { cacheGroups } = splitChunks; - F(cacheGroups, "default", () => ({ - idHint: "", - reuseExistingChunk: true, - minChunks: 2, - priority: -20 - })); - F(cacheGroups, "defaultVendors", () => ({ - idHint: "vendors", - reuseExistingChunk: true, - test: NODE_MODULES_REGEXP, - priority: -10 - })); - } -}; - -/** - * @param {Object} options options - * @param {boolean} options.cache is cache enable - * @param {string} options.context build context - * @param {TargetProperties | false} options.targetProperties target properties - * @param {Mode} options.mode mode - * @returns {ResolveOptions} resolve options - */ -const getResolveDefaults = ({ cache, context, targetProperties, mode }) => { - /** @type {string[]} */ - const conditions = ["webpack"]; + new ResolverCachePlugin().apply(compiler); - conditions.push(mode === "development" ? "development" : "production"); + if (options.ignoreWarnings && options.ignoreWarnings.length > 0) { + const IgnoreWarningsPlugin = __webpack_require__(18913); + new IgnoreWarningsPlugin(options.ignoreWarnings).apply(compiler); + } - if (targetProperties) { - if (targetProperties.webworker) conditions.push("worker"); - if (targetProperties.node) conditions.push("node"); - if (targetProperties.web) conditions.push("browser"); - if (targetProperties.electron) conditions.push("electron"); - if (targetProperties.nwjs) conditions.push("nwjs"); + compiler.hooks.afterPlugins.call(compiler); + if (!compiler.inputFileSystem) { + throw new Error("No input filesystem provided"); + } + compiler.resolverFactory.hooks.resolveOptions + .for("normal") + .tap("WebpackOptionsApply", resolveOptions => { + resolveOptions = cleverMerge(options.resolve, resolveOptions); + resolveOptions.fileSystem = compiler.inputFileSystem; + return resolveOptions; + }); + compiler.resolverFactory.hooks.resolveOptions + .for("context") + .tap("WebpackOptionsApply", resolveOptions => { + resolveOptions = cleverMerge(options.resolve, resolveOptions); + resolveOptions.fileSystem = compiler.inputFileSystem; + resolveOptions.resolveToContext = true; + return resolveOptions; + }); + compiler.resolverFactory.hooks.resolveOptions + .for("loader") + .tap("WebpackOptionsApply", resolveOptions => { + resolveOptions = cleverMerge(options.resolveLoader, resolveOptions); + resolveOptions.fileSystem = compiler.inputFileSystem; + return resolveOptions; + }); + compiler.hooks.afterResolvers.call(compiler); + return options; } +} - const jsExtensions = [".js", ".json", ".wasm"]; +module.exports = WebpackOptionsApply; - const tp = targetProperties; - const browserField = - tp && tp.web && (!tp.node || (tp.electron && tp.electronRenderer)); - /** @type {function(): ResolveOptions} */ - const cjsDeps = () => ({ - aliasFields: browserField ? ["browser"] : [], - mainFields: browserField ? ["browser", "module", "..."] : ["module", "..."], - conditionNames: ["require", "module", "..."], - extensions: [...jsExtensions] - }); - /** @type {function(): ResolveOptions} */ - const esmDeps = () => ({ - aliasFields: browserField ? ["browser"] : [], - mainFields: browserField ? ["browser", "module", "..."] : ["module", "..."], - conditionNames: ["import", "module", "..."], - extensions: [...jsExtensions] - }); +/***/ }), - /** @type {ResolveOptions} */ - const resolveOptions = { - cache, - modules: ["node_modules"], - conditionNames: conditions, - mainFiles: ["index"], - extensions: [], - aliasFields: [], - exportsFields: ["exports"], - roots: [context], - mainFields: ["main"], - byDependency: { - wasm: esmDeps(), - esm: esmDeps(), - loaderImport: esmDeps(), - url: { - preferRelative: true - }, - worker: { - ...esmDeps(), - preferRelative: true - }, - commonjs: cjsDeps(), - amd: cjsDeps(), - // for backward-compat: loadModule - loader: cjsDeps(), - // for backward-compat: Custom Dependency - unknown: cjsDeps(), - // for backward-compat: getResolve without dependencyType - undefined: cjsDeps() - } - }; +/***/ 547: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - return resolveOptions; -}; +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ -/** - * @param {Object} options options - * @param {boolean} options.cache is cache enable - * @returns {ResolveOptions} resolve options - */ -const getResolveLoaderDefaults = ({ cache }) => { - /** @type {ResolveOptions} */ - const resolveOptions = { - cache, - conditionNames: ["loader", "require", "node"], - exportsFields: ["exports"], - mainFields: ["loader", "main"], - extensions: [".js"], - mainFiles: ["index"] - }; - return resolveOptions; -}; -/** - * @param {InfrastructureLogging} infrastructureLogging options - * @returns {void} - */ -const applyInfrastructureLoggingDefaults = infrastructureLogging => { - F(infrastructureLogging, "stream", () => process.stderr); - const tty = - /** @type {any} */ (infrastructureLogging.stream).isTTY && - process.env.TERM !== "dumb"; - D(infrastructureLogging, "level", "info"); - D(infrastructureLogging, "debug", false); - D(infrastructureLogging, "colors", tty); - D(infrastructureLogging, "appendOnly", !tty); -}; +const { applyWebpackOptionsDefaults } = __webpack_require__(27057); +const { getNormalizedWebpackOptions } = __webpack_require__(52975); + +class WebpackOptionsDefaulter { + process(options) { + options = getNormalizedWebpackOptions(options); + applyWebpackOptionsDefaults(options); + return options; + } +} -exports.applyWebpackOptionsBaseDefaults = applyWebpackOptionsBaseDefaults; -exports.applyWebpackOptionsDefaults = applyWebpackOptionsDefaults; +module.exports = WebpackOptionsDefaulter; /***/ }), -/***/ 52975: -/***/ (function(__unused_webpack_module, exports, __webpack_require__) { +/***/ 18764: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; /* MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra + Author Sergey Melyukov @smelukov */ -const util = __webpack_require__(31669); - -/** @typedef {import("../../declarations/WebpackOptions").EntryStatic} EntryStatic */ -/** @typedef {import("../../declarations/WebpackOptions").EntryStaticNormalized} EntryStaticNormalized */ -/** @typedef {import("../../declarations/WebpackOptions").LibraryName} LibraryName */ -/** @typedef {import("../../declarations/WebpackOptions").LibraryOptions} LibraryOptions */ -/** @typedef {import("../../declarations/WebpackOptions").OptimizationRuntimeChunk} OptimizationRuntimeChunk */ -/** @typedef {import("../../declarations/WebpackOptions").OptimizationRuntimeChunkNormalized} OptimizationRuntimeChunkNormalized */ -/** @typedef {import("../../declarations/WebpackOptions").OutputNormalized} OutputNormalized */ -/** @typedef {import("../../declarations/WebpackOptions").WebpackOptions} WebpackOptions */ -/** @typedef {import("../../declarations/WebpackOptions").WebpackOptionsNormalized} WebpackOptionsNormalized */ - -const handledDeprecatedNoEmitOnErrors = util.deprecate( - (noEmitOnErrors, emitOnErrors) => { - if (emitOnErrors !== undefined && !noEmitOnErrors === !emitOnErrors) { - throw new Error( - "Conflicting use of 'optimization.noEmitOnErrors' and 'optimization.emitOnErrors'. Remove deprecated 'optimization.noEmitOnErrors' from config." - ); - } - return !noEmitOnErrors; - }, - "optimization.noEmitOnErrors is deprecated in favor of optimization.emitOnErrors", - "DEP_WEBPACK_CONFIGURATION_OPTIMIZATION_NO_EMIT_ON_ERRORS" -); +const mimeTypes = __webpack_require__(19338); +const path = __webpack_require__(85622); +const { RawSource } = __webpack_require__(96192); +const Generator = __webpack_require__(1826); +const RuntimeGlobals = __webpack_require__(49404); +const createHash = __webpack_require__(24123); +const { makePathsRelative } = __webpack_require__(96236); -/** - * @template T - * @template R - * @param {T|undefined} value value or not - * @param {function(T): R} fn nested handler - * @returns {R} result value - */ -const nestedConfig = (value, fn) => - value === undefined ? fn(/** @type {T} */ ({})) : fn(value); +/** @typedef {import("webpack-sources").Source} Source */ +/** @typedef {import("../../declarations/WebpackOptions").AssetGeneratorOptions} AssetGeneratorOptions */ +/** @typedef {import("../../declarations/WebpackOptions").RawPublicPath} RawPublicPath */ +/** @typedef {import("../Compilation")} Compilation */ +/** @typedef {import("../Compiler")} Compiler */ +/** @typedef {import("../Generator").GenerateContext} GenerateContext */ +/** @typedef {import("../Generator").UpdateHashContext} UpdateHashContext */ +/** @typedef {import("../Module")} Module */ +/** @typedef {import("../NormalModule")} NormalModule */ +/** @typedef {import("../RuntimeTemplate")} RuntimeTemplate */ +/** @typedef {import("../util/Hash")} Hash */ -/** - * @template T - * @param {T|undefined} value value or not - * @returns {T} result value - */ -const cloneObject = value => { - return /** @type {T} */ ({ ...value }); +const mergeMaybeArrays = (a, b) => { + const set = new Set(); + if (Array.isArray(a)) for (const item of a) set.add(item); + else set.add(a); + if (Array.isArray(b)) for (const item of b) set.add(item); + else set.add(b); + return Array.from(set); }; -/** - * @template T - * @template R - * @param {T|undefined} value value or not - * @param {function(T): R} fn nested handler - * @returns {R|undefined} result value - */ -const optionalNestedConfig = (value, fn) => - value === undefined ? undefined : fn(value); - -/** - * @template T - * @template R - * @param {T[]|undefined} value array or not - * @param {function(T[]): R[]} fn nested handler - * @returns {R[]|undefined} cloned value - */ -const nestedArray = (value, fn) => (Array.isArray(value) ? fn(value) : fn([])); - -/** - * @template T - * @template R - * @param {T[]|undefined} value array or not - * @param {function(T[]): R[]} fn nested handler - * @returns {R[]|undefined} cloned value - */ -const optionalNestedArray = (value, fn) => - Array.isArray(value) ? fn(value) : undefined; - -/** - * @template T - * @template R - * @param {Record|undefined} value value or not - * @param {function(T): R} fn nested handler - * @param {Record=} customKeys custom nested handler for some keys - * @returns {Record} result value - */ -const keyedNestedConfig = (value, fn, customKeys) => { - const result = - value === undefined - ? {} - : Object.keys(value).reduce( - (obj, key) => ( - (obj[key] = ( - customKeys && key in customKeys ? customKeys[key] : fn - )(value[key])), - obj - ), - /** @type {Record} */ ({}) - ); - if (customKeys) { - for (const key of Object.keys(customKeys)) { - if (!(key in result)) { - result[key] = customKeys[key](/** @type {T} */ ({})); +const mergeAssetInfo = (a, b) => { + const result = { ...a, ...b }; + for (const key of Object.keys(a)) { + if (key in b) { + if (a[key] === b[key]) continue; + switch (key) { + case "fullhash": + case "chunkhash": + case "modulehash": + case "contenthash": + result[key] = mergeMaybeArrays(a[key], b[key]); + break; + case "immutable": + case "development": + case "hotModuleReplacement": + case "javascriptModule ": + result[key] = a[key] || b[key]; + break; + case "related": + result[key] = mergeRelatedInfo(a[key], b[key]); + break; + default: + throw new Error(`Can't handle conflicting asset info for ${key}`); } } } return result; }; -/** - * @param {WebpackOptions} config input config - * @returns {WebpackOptionsNormalized} normalized options - */ -const getNormalizedWebpackOptions = config => { - return { - amd: config.amd, - bail: config.bail, - cache: optionalNestedConfig(config.cache, cache => { - if (cache === false) return false; - if (cache === true) { - return { - type: "memory", - maxGenerations: undefined - }; - } - switch (cache.type) { - case "filesystem": - return { - type: "filesystem", - allowCollectingMemory: cache.allowCollectingMemory, - maxMemoryGenerations: cache.maxMemoryGenerations, - maxAge: cache.maxAge, - profile: cache.profile, - buildDependencies: cloneObject(cache.buildDependencies), - cacheDirectory: cache.cacheDirectory, - cacheLocation: cache.cacheLocation, - hashAlgorithm: cache.hashAlgorithm, - compression: cache.compression, - idleTimeout: cache.idleTimeout, - idleTimeoutForInitialStore: cache.idleTimeoutForInitialStore, - idleTimeoutAfterLargeChanges: cache.idleTimeoutAfterLargeChanges, - name: cache.name, - store: cache.store, - version: cache.version - }; - case undefined: - case "memory": - return { - type: "memory", - maxGenerations: cache.maxGenerations - }; - default: - // @ts-expect-error Property 'type' does not exist on type 'never'. ts(2339) - throw new Error(`Not implemented cache.type ${cache.type}`); - } - }), - context: config.context, - dependencies: config.dependencies, - devServer: optionalNestedConfig(config.devServer, devServer => ({ - ...devServer - })), - devtool: config.devtool, - entry: - config.entry === undefined - ? { main: {} } - : typeof config.entry === "function" - ? ( - fn => () => - Promise.resolve().then(fn).then(getNormalizedEntryStatic) - )(config.entry) - : getNormalizedEntryStatic(config.entry), - experiments: nestedConfig(config.experiments, experiments => ({ - ...experiments, - buildHttp: optionalNestedConfig(experiments.buildHttp, options => - Array.isArray(options) ? { allowedUris: options } : options - ), - lazyCompilation: optionalNestedConfig( - experiments.lazyCompilation, - options => - options === true ? {} : options === false ? undefined : options - ) - })), - externals: config.externals, - externalsPresets: cloneObject(config.externalsPresets), - externalsType: config.externalsType, - ignoreWarnings: config.ignoreWarnings - ? config.ignoreWarnings.map(ignore => { - if (typeof ignore === "function") return ignore; - const i = ignore instanceof RegExp ? { message: ignore } : ignore; - return (warning, { requestShortener }) => { - if (!i.message && !i.module && !i.file) return false; - if (i.message && !i.message.test(warning.message)) { - return false; +const mergeRelatedInfo = (a, b) => { + const result = { ...a, ...b }; + for (const key of Object.keys(a)) { + if (key in b) { + if (a[key] === b[key]) continue; + result[key] = mergeMaybeArrays(a[key], b[key]); + } + } + return result; +}; + +const JS_TYPES = new Set(["javascript"]); +const JS_AND_ASSET_TYPES = new Set(["javascript", "asset"]); + +class AssetGenerator extends Generator { + /** + * @param {AssetGeneratorOptions["dataUrl"]=} dataUrlOptions the options for the data url + * @param {string=} filename override for output.assetModuleFilename + * @param {RawPublicPath=} publicPath override for output.assetModulePublicPath + * @param {boolean=} emit generate output asset + */ + constructor(dataUrlOptions, filename, publicPath, emit) { + super(); + this.dataUrlOptions = dataUrlOptions; + this.filename = filename; + this.publicPath = publicPath; + this.emit = emit; + } + + /** + * @param {NormalModule} module module for which the code should be generated + * @param {GenerateContext} generateContext context for generate + * @returns {Source} generated code + */ + generate( + module, + { runtime, chunkGraph, runtimeTemplate, runtimeRequirements, type, getData } + ) { + switch (type) { + case "asset": + return module.originalSource(); + default: { + runtimeRequirements.add(RuntimeGlobals.module); + + const originalSource = module.originalSource(); + if (module.buildInfo.dataUrl) { + let encodedSource; + if (typeof this.dataUrlOptions === "function") { + encodedSource = this.dataUrlOptions.call( + null, + originalSource.source(), + { + filename: module.matchResource || module.resource, + module + } + ); + } else { + /** @type {string | false | undefined} */ + let encoding = this.dataUrlOptions.encoding; + if (encoding === undefined) { + if ( + module.resourceResolveData && + module.resourceResolveData.encoding !== undefined + ) { + encoding = module.resourceResolveData.encoding; + } } - if ( - i.module && - (!warning.module || - !i.module.test( - warning.module.readableIdentifier(requestShortener) - )) - ) { - return false; + if (encoding === undefined) { + encoding = "base64"; } - if (i.file && (!warning.file || !i.file.test(warning.file))) { - return false; + let ext; + let mimeType = this.dataUrlOptions.mimetype; + if (mimeType === undefined) { + ext = path.extname(module.nameForCondition()); + if ( + module.resourceResolveData && + module.resourceResolveData.mimetype !== undefined + ) { + mimeType = + module.resourceResolveData.mimetype + + module.resourceResolveData.parameters; + } else if (ext) { + mimeType = mimeTypes.lookup(ext); + } } - return true; - }; - }) - : undefined, - infrastructureLogging: cloneObject(config.infrastructureLogging), - loader: cloneObject(config.loader), - mode: config.mode, - module: nestedConfig(config.module, module => ({ - noParse: module.noParse, - unsafeCache: module.unsafeCache, - parser: keyedNestedConfig(module.parser, cloneObject, { - javascript: parserOptions => ({ - unknownContextRequest: module.unknownContextRequest, - unknownContextRegExp: module.unknownContextRegExp, - unknownContextRecursive: module.unknownContextRecursive, - unknownContextCritical: module.unknownContextCritical, - exprContextRequest: module.exprContextRequest, - exprContextRegExp: module.exprContextRegExp, - exprContextRecursive: module.exprContextRecursive, - exprContextCritical: module.exprContextCritical, - wrappedContextRegExp: module.wrappedContextRegExp, - wrappedContextRecursive: module.wrappedContextRecursive, - wrappedContextCritical: module.wrappedContextCritical, - // TODO webpack 6 remove - strictExportPresence: module.strictExportPresence, - strictThisContextOnImports: module.strictThisContextOnImports, - ...parserOptions - }) - }), - generator: cloneObject(module.generator), - defaultRules: optionalNestedArray(module.defaultRules, r => [...r]), - rules: nestedArray(module.rules, r => [...r]) - })), - name: config.name, - node: nestedConfig( - config.node, - node => - node && { - ...node - } - ), - optimization: nestedConfig(config.optimization, optimization => { - return { - ...optimization, - runtimeChunk: getNormalizedOptimizationRuntimeChunk( - optimization.runtimeChunk - ), - splitChunks: nestedConfig( - optimization.splitChunks, - splitChunks => - splitChunks && { - ...splitChunks, - defaultSizeTypes: splitChunks.defaultSizeTypes - ? [...splitChunks.defaultSizeTypes] - : ["..."], - cacheGroups: cloneObject(splitChunks.cacheGroups) + if (typeof mimeType !== "string") { + throw new Error( + "DataUrl can't be generated automatically, " + + `because there is no mimetype for "${ext}" in mimetype database. ` + + 'Either pass a mimetype via "generator.mimetype" or ' + + 'use type: "asset/resource" to create a resource file instead of a DataUrl' + ); } - ), - emitOnErrors: - optimization.noEmitOnErrors !== undefined - ? handledDeprecatedNoEmitOnErrors( - optimization.noEmitOnErrors, - optimization.emitOnErrors - ) - : optimization.emitOnErrors - }; - }), - output: nestedConfig(config.output, output => { - const { library } = output; - const libraryAsName = /** @type {LibraryName} */ (library); - const libraryBase = - typeof library === "object" && - library && - !Array.isArray(library) && - "type" in library - ? library - : libraryAsName || output.libraryTarget - ? /** @type {LibraryOptions} */ ({ - name: libraryAsName - }) - : undefined; - /** @type {OutputNormalized} */ - const result = { - assetModuleFilename: output.assetModuleFilename, - asyncChunks: output.asyncChunks, - charset: output.charset, - chunkFilename: output.chunkFilename, - chunkFormat: output.chunkFormat, - chunkLoading: output.chunkLoading, - chunkLoadingGlobal: output.chunkLoadingGlobal, - chunkLoadTimeout: output.chunkLoadTimeout, - clean: output.clean, - compareBeforeEmit: output.compareBeforeEmit, - crossOriginLoading: output.crossOriginLoading, - devtoolFallbackModuleFilenameTemplate: - output.devtoolFallbackModuleFilenameTemplate, - devtoolModuleFilenameTemplate: output.devtoolModuleFilenameTemplate, - devtoolNamespace: output.devtoolNamespace, - environment: cloneObject(output.environment), - enabledChunkLoadingTypes: output.enabledChunkLoadingTypes - ? [...output.enabledChunkLoadingTypes] - : ["..."], - enabledLibraryTypes: output.enabledLibraryTypes - ? [...output.enabledLibraryTypes] - : ["..."], - enabledWasmLoadingTypes: output.enabledWasmLoadingTypes - ? [...output.enabledWasmLoadingTypes] - : ["..."], - filename: output.filename, - globalObject: output.globalObject, - hashDigest: output.hashDigest, - hashDigestLength: output.hashDigestLength, - hashFunction: output.hashFunction, - hashSalt: output.hashSalt, - hotUpdateChunkFilename: output.hotUpdateChunkFilename, - hotUpdateGlobal: output.hotUpdateGlobal, - hotUpdateMainFilename: output.hotUpdateMainFilename, - iife: output.iife, - importFunctionName: output.importFunctionName, - importMetaName: output.importMetaName, - scriptType: output.scriptType, - library: libraryBase && { - type: - output.libraryTarget !== undefined - ? output.libraryTarget - : libraryBase.type, - auxiliaryComment: - output.auxiliaryComment !== undefined - ? output.auxiliaryComment - : libraryBase.auxiliaryComment, - export: - output.libraryExport !== undefined - ? output.libraryExport - : libraryBase.export, - name: libraryBase.name, - umdNamedDefine: - output.umdNamedDefine !== undefined - ? output.umdNamedDefine - : libraryBase.umdNamedDefine - }, - module: output.module, - path: output.path, - pathinfo: output.pathinfo, - publicPath: output.publicPath, - sourceMapFilename: output.sourceMapFilename, - sourcePrefix: output.sourcePrefix, - strictModuleExceptionHandling: output.strictModuleExceptionHandling, - trustedTypes: optionalNestedConfig( - output.trustedTypes, - trustedTypes => { - if (trustedTypes === true) return {}; - if (typeof trustedTypes === "string") - return { policyName: trustedTypes }; - return { ...trustedTypes }; + + let encodedContent; + if ( + module.resourceResolveData && + module.resourceResolveData.encoding === encoding + ) { + encodedContent = module.resourceResolveData.encodedContent; + } else { + switch (encoding) { + case "base64": { + encodedContent = originalSource.buffer().toString("base64"); + break; + } + case false: { + const content = originalSource.source(); + + if (typeof content !== "string") { + encodedContent = content.toString("utf-8"); + } + + encodedContent = encodeURIComponent(encodedContent).replace( + /[!'()*]/g, + character => "%" + character.codePointAt(0).toString(16) + ); + break; + } + default: + throw new Error(`Unsupported encoding '${encoding}'`); + } + } + + encodedSource = `data:${mimeType}${ + encoding ? `;${encoding}` : "" + },${encodedContent}`; + } + return new RawSource( + `${RuntimeGlobals.module}.exports = ${JSON.stringify( + encodedSource + )};` + ); + } else { + const assetModuleFilename = + this.filename || runtimeTemplate.outputOptions.assetModuleFilename; + const hash = createHash(runtimeTemplate.outputOptions.hashFunction); + if (runtimeTemplate.outputOptions.hashSalt) { + hash.update(runtimeTemplate.outputOptions.hashSalt); + } + hash.update(originalSource.buffer()); + const fullHash = /** @type {string} */ ( + hash.digest(runtimeTemplate.outputOptions.hashDigest) + ); + const contentHash = fullHash.slice( + 0, + runtimeTemplate.outputOptions.hashDigestLength + ); + module.buildInfo.fullContentHash = fullHash; + const sourceFilename = makePathsRelative( + runtimeTemplate.compilation.compiler.context, + module.matchResource || module.resource, + runtimeTemplate.compilation.compiler.root + ).replace(/^\.\//, ""); + let { path: filename, info: assetInfo } = + runtimeTemplate.compilation.getAssetPathWithInfo( + assetModuleFilename, + { + module, + runtime, + filename: sourceFilename, + chunkGraph, + contentHash + } + ); + let publicPath; + if (this.publicPath !== undefined) { + const { path, info } = + runtimeTemplate.compilation.getAssetPathWithInfo( + this.publicPath, + { + module, + runtime, + filename: sourceFilename, + chunkGraph, + contentHash + } + ); + publicPath = JSON.stringify(path); + assetInfo = mergeAssetInfo(assetInfo, info); + } else { + publicPath = RuntimeGlobals.publicPath; + runtimeRequirements.add(RuntimeGlobals.publicPath); // add __webpack_require__.p + } + assetInfo = { + sourceFilename, + ...assetInfo + }; + module.buildInfo.filename = filename; + module.buildInfo.assetInfo = assetInfo; + if (getData) { + // Due to code generation caching module.buildInfo.XXX can't used to store such information + // It need to be stored in the code generation results instead, where it's cached too + // TODO webpack 6 For back-compat reasons we also store in on module.buildInfo + const data = getData(); + data.set("fullContentHash", fullHash); + data.set("filename", filename); + data.set("assetInfo", assetInfo); } - ), - uniqueName: output.uniqueName, - wasmLoading: output.wasmLoading, - webassemblyModuleFilename: output.webassemblyModuleFilename, - workerChunkLoading: output.workerChunkLoading, - workerWasmLoading: output.workerWasmLoading - }; - return result; - }), - parallelism: config.parallelism, - performance: optionalNestedConfig(config.performance, performance => { - if (performance === false) return false; - return { - ...performance - }; - }), - plugins: nestedArray(config.plugins, p => [...p]), - profile: config.profile, - recordsInputPath: - config.recordsInputPath !== undefined - ? config.recordsInputPath - : config.recordsPath, - recordsOutputPath: - config.recordsOutputPath !== undefined - ? config.recordsOutputPath - : config.recordsPath, - resolve: nestedConfig(config.resolve, resolve => ({ - ...resolve, - byDependency: keyedNestedConfig(resolve.byDependency, cloneObject) - })), - resolveLoader: cloneObject(config.resolveLoader), - snapshot: nestedConfig(config.snapshot, snapshot => ({ - resolveBuildDependencies: optionalNestedConfig( - snapshot.resolveBuildDependencies, - resolveBuildDependencies => ({ - timestamp: resolveBuildDependencies.timestamp, - hash: resolveBuildDependencies.hash - }) - ), - buildDependencies: optionalNestedConfig( - snapshot.buildDependencies, - buildDependencies => ({ - timestamp: buildDependencies.timestamp, - hash: buildDependencies.hash - }) - ), - resolve: optionalNestedConfig(snapshot.resolve, resolve => ({ - timestamp: resolve.timestamp, - hash: resolve.hash - })), - module: optionalNestedConfig(snapshot.module, module => ({ - timestamp: module.timestamp, - hash: module.hash - })), - immutablePaths: optionalNestedArray(snapshot.immutablePaths, p => [...p]), - managedPaths: optionalNestedArray(snapshot.managedPaths, p => [...p]) - })), - stats: nestedConfig(config.stats, stats => { - if (stats === false) { - return { - preset: "none" - }; - } - if (stats === true) { - return { - preset: "normal" - }; - } - if (typeof stats === "string") { - return { - preset: stats - }; - } - return { - ...stats - }; - }), - target: config.target, - watch: config.watch, - watchOptions: cloneObject(config.watchOptions) - }; -}; -/** - * @param {EntryStatic} entry static entry options - * @returns {EntryStaticNormalized} normalized static entry options - */ -const getNormalizedEntryStatic = entry => { - if (typeof entry === "string") { - return { - main: { - import: [entry] - } - }; - } - if (Array.isArray(entry)) { - return { - main: { - import: entry + return new RawSource( + `${ + RuntimeGlobals.module + }.exports = ${publicPath} + ${JSON.stringify(filename)};` + ); + } } - }; + } } - /** @type {EntryStaticNormalized} */ - const result = {}; - for (const key of Object.keys(entry)) { - const value = entry[key]; - if (typeof value === "string") { - result[key] = { - import: [value] - }; - } else if (Array.isArray(value)) { - result[key] = { - import: value - }; + + /** + * @param {NormalModule} module fresh module + * @returns {Set} available types (do not mutate) + */ + getTypes(module) { + if ((module.buildInfo && module.buildInfo.dataUrl) || this.emit === false) { + return JS_TYPES; } else { - result[key] = { - import: - value.import && - (Array.isArray(value.import) ? value.import : [value.import]), - filename: value.filename, - layer: value.layer, - runtime: value.runtime, - publicPath: value.publicPath, - chunkLoading: value.chunkLoading, - asyncChunks: value.asyncChunks, - wasmLoading: value.wasmLoading, - dependOn: - value.dependOn && - (Array.isArray(value.dependOn) ? value.dependOn : [value.dependOn]), - library: value.library - }; + return JS_AND_ASSET_TYPES; } } - return result; -}; -/** - * @param {OptimizationRuntimeChunk=} runtimeChunk runtimeChunk option - * @returns {OptimizationRuntimeChunkNormalized=} normalized runtimeChunk option - */ -const getNormalizedOptimizationRuntimeChunk = runtimeChunk => { - if (runtimeChunk === undefined) return undefined; - if (runtimeChunk === false) return false; - if (runtimeChunk === "single") { - return { - name: () => "runtime" - }; + /** + * @param {NormalModule} module the module + * @param {string=} type source type + * @returns {number} estimate size of the module + */ + getSize(module, type) { + switch (type) { + case "asset": { + const originalSource = module.originalSource(); + + if (!originalSource) { + return 0; + } + + return originalSource.size(); + } + default: + if (module.buildInfo && module.buildInfo.dataUrl) { + const originalSource = module.originalSource(); + + if (!originalSource) { + return 0; + } + + // roughly for data url + // Example: m.exports="data:image/png;base64,ag82/f+2==" + // 4/3 = base64 encoding + // 34 = ~ data url header + footer + rounding + return originalSource.size() * 1.34 + 36; + } else { + // it's only estimated so this number is probably fine + // Example: m.exports=r.p+"0123456789012345678901.ext" + return 42; + } + } } - if (runtimeChunk === true || runtimeChunk === "multiple") { - return { - name: entrypoint => `runtime~${entrypoint.name}` - }; + + /** + * @param {Hash} hash hash that will be modified + * @param {UpdateHashContext} updateHashContext context for updating hash + */ + updateHash(hash, { module }) { + hash.update(module.buildInfo.dataUrl ? "data-url" : "resource"); } - const { name } = runtimeChunk; - return { - name: typeof name === "function" ? name : () => name - }; -}; +} -exports.getNormalizedWebpackOptions = getNormalizedWebpackOptions; +module.exports = AssetGenerator; /***/ }), -/***/ 23451: -/***/ (function(__unused_webpack_module, exports, __webpack_require__) { +/***/ 42553: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; /* MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra + Author Yuta Hiroto @hiroppy */ +const { cleverMerge } = __webpack_require__(11217); +const { compareModulesByIdentifier } = __webpack_require__(26296); +const createSchemaValidation = __webpack_require__(77695); const memoize = __webpack_require__(84297); -const getBrowserslistTargetHandler = memoize(() => - __webpack_require__(82852) -); +/** @typedef {import("webpack-sources").Source} Source */ +/** @typedef {import("../Chunk")} Chunk */ +/** @typedef {import("../Compiler")} Compiler */ +/** @typedef {import("../Module")} Module */ -/** - * @param {string} context the context directory - * @returns {string} default target - */ -const getDefaultTarget = context => { - const browsers = getBrowserslistTargetHandler().load(null, context); - return browsers ? "browserslist" : "web"; +const getSchema = name => { + const { definitions } = __webpack_require__(1863); + return { + definitions, + oneOf: [{ $ref: `#/definitions/${name}` }] + }; }; -/** - * @typedef {Object} PlatformTargetProperties - * @property {boolean | null} web web platform, importing of http(s) and std: is available - * @property {boolean | null} browser browser platform, running in a normal web browser - * @property {boolean | null} webworker (Web)Worker platform, running in a web/shared/service worker - * @property {boolean | null} node node platform, require of node built-in modules is available - * @property {boolean | null} nwjs nwjs platform, require of legacy nw.gui is available - * @property {boolean | null} electron electron platform, require of some electron built-in modules is available - */ +const generatorValidationOptions = { + name: "Asset Modules Plugin", + baseDataPath: "generator" +}; +const validateGeneratorOptions = { + asset: createSchemaValidation( + __webpack_require__(76961), + () => getSchema("AssetGeneratorOptions"), + generatorValidationOptions + ), + "asset/resource": createSchemaValidation( + __webpack_require__(15643), + () => getSchema("AssetResourceGeneratorOptions"), + generatorValidationOptions + ), + "asset/inline": createSchemaValidation( + __webpack_require__(40851), + () => getSchema("AssetInlineGeneratorOptions"), + generatorValidationOptions + ) +}; -/** - * @typedef {Object} ElectronContextTargetProperties - * @property {boolean | null} electronMain in main context - * @property {boolean | null} electronPreload in preload context - * @property {boolean | null} electronRenderer in renderer context with node integration - */ +const validateParserOptions = createSchemaValidation( + __webpack_require__(85912), + () => getSchema("AssetParserOptions"), + { + name: "Asset Modules Plugin", + baseDataPath: "parser" + } +); -/** - * @typedef {Object} ApiTargetProperties - * @property {boolean | null} require has require function available - * @property {boolean | null} nodeBuiltins has node.js built-in modules available - * @property {boolean | null} document has document available (allows script tags) - * @property {boolean | null} importScripts has importScripts available - * @property {boolean | null} importScriptsInWorker has importScripts available when creating a worker - * @property {boolean | null} fetchWasm has fetch function available for WebAssembly - * @property {boolean | null} global has global variable available - */ +const getAssetGenerator = memoize(() => __webpack_require__(18764)); +const getAssetParser = memoize(() => __webpack_require__(13055)); +const getAssetSourceParser = memoize(() => __webpack_require__(75925)); +const getAssetSourceGenerator = memoize(() => + __webpack_require__(66511) +); -/** - * @typedef {Object} EcmaTargetProperties - * @property {boolean | null} globalThis has globalThis variable available - * @property {boolean | null} bigIntLiteral big int literal syntax is available - * @property {boolean | null} const const and let variable declarations are available - * @property {boolean | null} arrowFunction arrow functions are available - * @property {boolean | null} forOf for of iteration is available - * @property {boolean | null} destructuring destructuring is available - * @property {boolean | null} dynamicImport async import() is available - * @property {boolean | null} dynamicImportInWorker async import() is available when creating a worker - * @property {boolean | null} module ESM syntax is available (when in module) - */ +const type = "asset"; +const plugin = "AssetModulesPlugin"; -///** @typedef {PlatformTargetProperties | ApiTargetProperties | EcmaTargetProperties | PlatformTargetProperties & ApiTargetProperties | PlatformTargetProperties & EcmaTargetProperties | ApiTargetProperties & EcmaTargetProperties} TargetProperties */ -/** @template T @typedef {{ [P in keyof T]?: never }} Never */ -/** @template A @template B @typedef {(A & Never) | (Never & B) | (A & B)} Mix */ -/** @typedef {Mix, Mix>} TargetProperties */ +class AssetModulesPlugin { + /** + * Apply the plugin + * @param {Compiler} compiler the compiler instance + * @returns {void} + */ + apply(compiler) { + compiler.hooks.compilation.tap( + plugin, + (compilation, { normalModuleFactory }) => { + normalModuleFactory.hooks.createParser + .for("asset") + .tap(plugin, parserOptions => { + validateParserOptions(parserOptions); + parserOptions = cleverMerge( + compiler.options.module.parser.asset, + parserOptions + ); -const versionDependent = (major, minor) => { - if (!major) return () => /** @type {undefined} */ (undefined); - major = +major; - minor = minor ? +minor : 0; - return (vMajor, vMinor = 0) => { - return major > vMajor || (major === vMajor && minor >= vMinor); - }; -}; + let dataUrlCondition = parserOptions.dataUrlCondition; + if (!dataUrlCondition || typeof dataUrlCondition === "object") { + dataUrlCondition = { + maxSize: 8096, + ...dataUrlCondition + }; + } -/** @type {[string, string, RegExp, (...args: string[]) => TargetProperties | false][]} */ -const TARGETS = [ - [ - "browserslist / browserslist:env / browserslist:query / browserslist:path-to-config / browserslist:path-to-config:env", - "Resolve features from browserslist. Will resolve browserslist config automatically. Only browser or node queries are supported (electron is not supported). Examples: 'browserslist:modern' to use 'modern' environment from browserslist config", - /^browserslist(?::(.+))?$/, - (rest, context) => { - const browserslistTargetHandler = getBrowserslistTargetHandler(); - const browsers = browserslistTargetHandler.load( - rest ? rest.trim() : null, - context - ); - if (!browsers) { - throw new Error(`No browserslist config found to handle the 'browserslist' target. -See https://github.com/browserslist/browserslist#queries for possible ways to provide a config. -The recommended way is to add a 'browserslist' key to your package.json and list supported browsers (resp. node.js versions). -You can also more options via the 'target' option: 'browserslist' / 'browserslist:env' / 'browserslist:query' / 'browserslist:path-to-config' / 'browserslist:path-to-config:env'`); - } - return browserslistTargetHandler.resolve(browsers); - } - ], - [ - "web", - "Web browser.", - /^web$/, - () => { - return { - web: true, - browser: true, - webworker: null, - node: false, - electron: false, - nwjs: false, + const AssetParser = getAssetParser(); - document: true, - importScriptsInWorker: true, - fetchWasm: true, - nodeBuiltins: false, - importScripts: false, - require: false, - global: false - }; - } - ], - [ - "webworker", - "Web Worker, SharedWorker or Service Worker.", - /^webworker$/, - () => { - return { - web: true, - browser: true, - webworker: true, - node: false, - electron: false, - nwjs: false, + return new AssetParser(dataUrlCondition); + }); + normalModuleFactory.hooks.createParser + .for("asset/inline") + .tap(plugin, parserOptions => { + const AssetParser = getAssetParser(); + + return new AssetParser(true); + }); + normalModuleFactory.hooks.createParser + .for("asset/resource") + .tap(plugin, parserOptions => { + const AssetParser = getAssetParser(); + + return new AssetParser(false); + }); + normalModuleFactory.hooks.createParser + .for("asset/source") + .tap(plugin, parserOptions => { + const AssetSourceParser = getAssetSourceParser(); + + return new AssetSourceParser(); + }); - importScripts: true, - importScriptsInWorker: true, - fetchWasm: true, - nodeBuiltins: false, - require: false, - document: false, - global: false - }; - } - ], - [ - "[async-]node[X[.Y]]", - "Node.js in version X.Y. The 'async-' prefix will load chunks asynchronously via 'fs' and 'vm' instead of 'require()'. Examples: node14.5, async-node10.", - /^(async-)?node(\d+(?:\.(\d+))?)?$/, - (asyncFlag, major, minor) => { - const v = versionDependent(major, minor); - // see https://node.green/ - return { - node: true, - electron: false, - nwjs: false, - web: false, - webworker: false, - browser: false, + for (const type of ["asset", "asset/inline", "asset/resource"]) { + normalModuleFactory.hooks.createGenerator + .for(type) + .tap(plugin, generatorOptions => { + validateGeneratorOptions[type](generatorOptions); - require: !asyncFlag, - nodeBuiltins: true, - global: true, - document: false, - fetchWasm: false, - importScripts: false, - importScriptsInWorker: false, + let dataUrl = undefined; + if (type !== "asset/resource") { + dataUrl = generatorOptions.dataUrl; + if (!dataUrl || typeof dataUrl === "object") { + dataUrl = { + encoding: undefined, + mimetype: undefined, + ...dataUrl + }; + } + } - globalThis: v(12), - const: v(6), - arrowFunction: v(6), - forOf: v(5), - destructuring: v(6), - bigIntLiteral: v(10, 4), - dynamicImport: v(12, 17), - dynamicImportInWorker: major ? false : undefined, - module: v(12, 17) - }; - } - ], - [ - "electron[X[.Y]]-main/preload/renderer", - "Electron in version X.Y. Script is running in main, preload resp. renderer context.", - /^electron(\d+(?:\.(\d+))?)?-(main|preload|renderer)$/, - (major, minor, context) => { - const v = versionDependent(major, minor); - // see https://node.green/ + https://github.com/electron/releases - return { - node: true, - electron: true, - web: context !== "main", - webworker: false, - browser: false, - nwjs: false, + let filename = undefined; + let publicPath = undefined; + if (type !== "asset/inline") { + filename = generatorOptions.filename; + publicPath = generatorOptions.publicPath; + } - electronMain: context === "main", - electronPreload: context === "preload", - electronRenderer: context === "renderer", + const AssetGenerator = getAssetGenerator(); - global: true, - nodeBuiltins: true, - require: true, - document: context === "renderer", - fetchWasm: context === "renderer", - importScripts: false, - importScriptsInWorker: true, + return new AssetGenerator( + dataUrl, + filename, + publicPath, + generatorOptions.emit !== false + ); + }); + } + normalModuleFactory.hooks.createGenerator + .for("asset/source") + .tap(plugin, () => { + const AssetSourceGenerator = getAssetSourceGenerator(); - globalThis: v(5), - const: v(1, 1), - arrowFunction: v(1, 1), - forOf: v(0, 36), - destructuring: v(1, 1), - bigIntLiteral: v(4), - dynamicImport: v(11), - dynamicImportInWorker: major ? false : undefined, - module: v(11) - }; - } - ], - [ - "nwjs[X[.Y]] / node-webkit[X[.Y]]", - "NW.js in version X.Y.", - /^(?:nwjs|node-webkit)(\d+(?:\.(\d+))?)?$/, - (major, minor) => { - const v = versionDependent(major, minor); - // see https://node.green/ + https://github.com/nwjs/nw.js/blob/nw48/CHANGELOG.md - return { - node: true, - web: true, - nwjs: true, - webworker: null, - browser: false, - electron: false, + return new AssetSourceGenerator(); + }); - global: true, - nodeBuiltins: true, - document: false, - importScriptsInWorker: false, - fetchWasm: false, - importScripts: false, - require: false, + compilation.hooks.renderManifest.tap(plugin, (result, options) => { + const { chunkGraph } = compilation; + const { chunk, codeGenerationResults } = options; - globalThis: v(0, 43), - const: v(0, 15), - arrowFunction: v(0, 15), - forOf: v(0, 13), - destructuring: v(0, 15), - bigIntLiteral: v(0, 32), - dynamicImport: v(0, 43), - dynamicImportInWorker: major ? false : undefined, - module: v(0, 43) - }; - } - ], - [ - "esX", - "EcmaScript in this version. Examples: es2020, es5.", - /^es(\d+)$/, - version => { - let v = +version; - if (v < 1000) v = v + 2009; - return { - const: v >= 2015, - arrowFunction: v >= 2015, - forOf: v >= 2015, - destructuring: v >= 2015, - module: v >= 2015, - globalThis: v >= 2020, - bigIntLiteral: v >= 2020, - dynamicImport: v >= 2020, - dynamicImportInWorker: v >= 2020 - }; - } - ] -]; + const modules = chunkGraph.getOrderedChunkModulesIterableBySourceType( + chunk, + "asset", + compareModulesByIdentifier + ); + if (modules) { + for (const module of modules) { + try { + const codeGenResult = codeGenerationResults.get( + module, + chunk.runtime + ); + result.push({ + render: () => codeGenResult.sources.get(type), + filename: + module.buildInfo.filename || + codeGenResult.data.get("filename"), + info: + module.buildInfo.assetInfo || + codeGenResult.data.get("assetInfo"), + auxiliary: true, + identifier: `assetModule${chunkGraph.getModuleId(module)}`, + hash: + module.buildInfo.fullContentHash || + codeGenResult.data.get("fullContentHash") + }); + } catch (e) { + e.message += `\nduring rendering of asset ${module.identifier()}`; + throw e; + } + } + } -/** - * @param {string} target the target - * @param {string} context the context directory - * @returns {TargetProperties} target properties - */ -const getTargetProperties = (target, context) => { - for (const [, , regExp, handler] of TARGETS) { - const match = regExp.exec(target); - if (match) { - const [, ...args] = match; - const result = handler(...args, context); - if (result) return result; - } - } - throw new Error( - `Unknown target '${target}'. The following targets are supported:\n${TARGETS.map( - ([name, description]) => `* ${name}: ${description}` - ).join("\n")}` - ); -}; + return result; + }); -const mergeTargetProperties = targetProperties => { - const keys = new Set(); - for (const tp of targetProperties) { - for (const key of Object.keys(tp)) { - keys.add(key); - } - } - const result = {}; - for (const key of keys) { - let hasTrue = false; - let hasFalse = false; - for (const tp of targetProperties) { - const value = tp[key]; - switch (value) { - case true: - hasTrue = true; - break; - case false: - hasFalse = true; - break; + compilation.hooks.prepareModuleExecution.tap( + "AssetModulesPlugin", + (options, context) => { + const { codeGenerationResult } = options; + const source = codeGenerationResult.sources.get("asset"); + if (source === undefined) return; + context.assets.set(codeGenerationResult.data.get("filename"), { + source, + info: codeGenerationResult.data.get("assetInfo") + }); + } + ); } - } - if (hasTrue || hasFalse) - result[key] = hasFalse && hasTrue ? null : hasTrue ? true : false; + ); } - return /** @type {TargetProperties} */ (result); -}; - -/** - * @param {string[]} targets the targets - * @param {string} context the context directory - * @returns {TargetProperties} target properties - */ -const getTargetsProperties = (targets, context) => { - return mergeTargetProperties( - targets.map(t => getTargetProperties(t, context)) - ); -}; +} -exports.getDefaultTarget = getDefaultTarget; -exports.getTargetProperties = getTargetProperties; -exports.getTargetsProperties = getTargetsProperties; +module.exports = AssetModulesPlugin; /***/ }), -/***/ 44055: +/***/ 13055: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; /* MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra, Zackary Jackson @ScriptedAlchemy, Marais Rossouw @maraisr + Author Yuta Hiroto @hiroppy */ -const Dependency = __webpack_require__(50384); -const makeSerializable = __webpack_require__(26522); +const Parser = __webpack_require__(68214); -/** @typedef {import("./ContainerEntryModule").ExposeOptions} ExposeOptions */ +/** @typedef {import("../../declarations/WebpackOptions").AssetParserOptions} AssetParserOptions */ +/** @typedef {import("../Parser").ParserState} ParserState */ +/** @typedef {import("../Parser").PreparsedAst} PreparsedAst */ -class ContainerEntryDependency extends Dependency { +class AssetParser extends Parser { /** - * @param {string} name entry name - * @param {[string, ExposeOptions][]} exposes list of exposed modules - * @param {string} shareScope name of the share scope + * @param {AssetParserOptions["dataUrlCondition"] | boolean} dataUrlCondition condition for inlining as DataUrl */ - constructor(name, exposes, shareScope) { + constructor(dataUrlCondition) { super(); - this.name = name; - this.exposes = exposes; - this.shareScope = shareScope; + this.dataUrlCondition = dataUrlCondition; } /** - * @returns {string | null} an identifier to merge equal requests + * @param {string | Buffer | PreparsedAst} source the source to parse + * @param {ParserState} state the parser state + * @returns {ParserState} the parser state */ - getResourceIdentifier() { - return `container-entry-${this.name}`; - } + parse(source, state) { + if (typeof source === "object" && !Buffer.isBuffer(source)) { + throw new Error("AssetParser doesn't accept preparsed AST"); + } + state.module.buildInfo.strict = true; + state.module.buildMeta.exportsType = "default"; - get type() { - return "container entry"; - } + if (typeof this.dataUrlCondition === "function") { + state.module.buildInfo.dataUrl = this.dataUrlCondition(source, { + filename: state.module.matchResource || state.module.resource, + module: state.module + }); + } else if (typeof this.dataUrlCondition === "boolean") { + state.module.buildInfo.dataUrl = this.dataUrlCondition; + } else if ( + this.dataUrlCondition && + typeof this.dataUrlCondition === "object" + ) { + state.module.buildInfo.dataUrl = + Buffer.byteLength(source) <= this.dataUrlCondition.maxSize; + } else { + throw new Error("Unexpected dataUrlCondition type"); + } - get category() { - return "esm"; + return state; } } -makeSerializable( - ContainerEntryDependency, - "webpack/lib/container/ContainerEntryDependency" -); - -module.exports = ContainerEntryDependency; +module.exports = AssetParser; /***/ }), -/***/ 3234: +/***/ 66511: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; /* MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra, Zackary Jackson @ScriptedAlchemy, Marais Rossouw @maraisr + Author Sergey Melyukov @smelukov */ -const { OriginalSource, RawSource } = __webpack_require__(96192); -const AsyncDependenciesBlock = __webpack_require__(11315); -const Module = __webpack_require__(85887); +const { RawSource } = __webpack_require__(96192); +const Generator = __webpack_require__(1826); const RuntimeGlobals = __webpack_require__(49404); -const Template = __webpack_require__(92066); -const makeSerializable = __webpack_require__(26522); -const ContainerExposedDependency = __webpack_require__(50); - -/** @typedef {import("../../declarations/WebpackOptions").WebpackOptionsNormalized} WebpackOptions */ -/** @typedef {import("../ChunkGraph")} ChunkGraph */ -/** @typedef {import("../ChunkGroup")} ChunkGroup */ -/** @typedef {import("../Compilation")} Compilation */ -/** @typedef {import("../Module").CodeGenerationContext} CodeGenerationContext */ -/** @typedef {import("../Module").CodeGenerationResult} CodeGenerationResult */ -/** @typedef {import("../Module").LibIdentOptions} LibIdentOptions */ -/** @typedef {import("../Module").NeedBuildContext} NeedBuildContext */ -/** @typedef {import("../RequestShortener")} RequestShortener */ -/** @typedef {import("../ResolverFactory").ResolverWithOptions} ResolverWithOptions */ -/** @typedef {import("../WebpackError")} WebpackError */ -/** @typedef {import("../util/Hash")} Hash */ -/** @typedef {import("../util/fs").InputFileSystem} InputFileSystem */ -/** @typedef {import("./ContainerEntryDependency")} ContainerEntryDependency */ -/** - * @typedef {Object} ExposeOptions - * @property {string[]} import requests to exposed modules (last one is exported) - * @property {string} name custom chunk name for the exposed module - */ +/** @typedef {import("webpack-sources").Source} Source */ +/** @typedef {import("../Generator").GenerateContext} GenerateContext */ +/** @typedef {import("../NormalModule")} NormalModule */ -const SOURCE_TYPES = new Set(["javascript"]); +const TYPES = new Set(["javascript"]); -class ContainerEntryModule extends Module { +class AssetSourceGenerator extends Generator { /** - * @param {string} name container entry name - * @param {[string, ExposeOptions][]} exposes list of exposed modules - * @param {string} shareScope name of the share scope + * @param {NormalModule} module module for which the code should be generated + * @param {GenerateContext} generateContext context for generate + * @returns {Source} generated code */ - constructor(name, exposes, shareScope) { - super("javascript/dynamic", null); - this._name = name; - this._exposes = exposes; - this._shareScope = shareScope; - } + generate(module, { chunkGraph, runtimeTemplate, runtimeRequirements }) { + runtimeRequirements.add(RuntimeGlobals.module); - /** - * @returns {Set} types available (do not mutate) - */ - getSourceTypes() { - return SOURCE_TYPES; - } + const originalSource = module.originalSource(); - /** - * @returns {string} a unique identifier of the module - */ - identifier() { - return `container entry (${this._shareScope}) ${JSON.stringify( - this._exposes - )}`; - } + if (!originalSource) { + return new RawSource(""); + } - /** - * @param {RequestShortener} requestShortener the request shortener - * @returns {string} a user readable identifier of the module - */ - readableIdentifier(requestShortener) { - return `container entry`; + const content = originalSource.source(); + + let encodedSource; + if (typeof content === "string") { + encodedSource = content; + } else { + encodedSource = content.toString("utf-8"); + } + return new RawSource( + `${RuntimeGlobals.module}.exports = ${JSON.stringify(encodedSource)};` + ); } /** - * @param {LibIdentOptions} options options - * @returns {string | null} an identifier for library inclusion + * @param {NormalModule} module fresh module + * @returns {Set} available types (do not mutate) */ - libIdent(options) { - return `webpack/container/entry/${this._name}`; + getTypes(module) { + return TYPES; } /** - * @param {NeedBuildContext} context context info - * @param {function(WebpackError=, boolean=): void} callback callback function, returns true, if the module needs a rebuild - * @returns {void} + * @param {NormalModule} module the module + * @param {string=} type source type + * @returns {number} estimate size of the module */ - needBuild(context, callback) { - return callback(null, !this.buildMeta); + getSize(module, type) { + const originalSource = module.originalSource(); + + if (!originalSource) { + return 0; + } + + // Example: m.exports="abcd" + return originalSource.size() + 12; } +} - /** - * @param {WebpackOptions} options webpack options - * @param {Compilation} compilation the compilation - * @param {ResolverWithOptions} resolver the resolver - * @param {InputFileSystem} fs the file system - * @param {function(WebpackError=): void} callback callback function - * @returns {void} - */ - build(options, compilation, resolver, fs, callback) { - this.buildMeta = {}; - this.buildInfo = { - strict: true, - topLevelDeclarations: new Set(["moduleMap", "get", "init"]) - }; +module.exports = AssetSourceGenerator; - this.clearDependenciesAndBlocks(); - for (const [name, options] of this._exposes) { - const block = new AsyncDependenciesBlock( - { - name: options.name - }, - { name }, - options.import[options.import.length - 1] - ); - let idx = 0; - for (const request of options.import) { - const dep = new ContainerExposedDependency(name, request); - dep.loc = { - name, - index: idx++ - }; +/***/ }), - block.addDependency(dep); - } - this.addBlock(block); +/***/ 75925: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Yuta Hiroto @hiroppy +*/ + + + +const Parser = __webpack_require__(68214); + +/** @typedef {import("../Parser").ParserState} ParserState */ +/** @typedef {import("../Parser").PreparsedAst} PreparsedAst */ + +class AssetSourceParser extends Parser { + /** + * @param {string | Buffer | PreparsedAst} source the source to parse + * @param {ParserState} state the parser state + * @returns {ParserState} the parser state + */ + parse(source, state) { + if (typeof source === "object" && !Buffer.isBuffer(source)) { + throw new Error("AssetSourceParser doesn't accept preparsed AST"); } + const { module } = state; + module.buildInfo.strict = true; + module.buildMeta.exportsType = "default"; - callback(); + return state; } +} - /** - * @param {CodeGenerationContext} context context for code generation - * @returns {CodeGenerationResult} result - */ - codeGeneration({ moduleGraph, chunkGraph, runtimeTemplate }) { - const sources = new Map(); - const runtimeRequirements = new Set([ - RuntimeGlobals.definePropertyGetters, - RuntimeGlobals.hasOwnProperty, - RuntimeGlobals.exports - ]); - const getters = []; +module.exports = AssetSourceParser; - for (const block of this.blocks) { - const { dependencies } = block; - const modules = dependencies.map(dependency => { - const dep = /** @type {ContainerExposedDependency} */ (dependency); - return { - name: dep.exposedName, - module: moduleGraph.getModule(dep), - request: dep.userRequest - }; - }); +/***/ }), - let str; +/***/ 20911: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - if (modules.some(m => !m.module)) { - str = runtimeTemplate.throwMissingModuleErrorBlock({ - request: modules.map(m => m.request).join(", ") - }); - } else { - str = `return ${runtimeTemplate.blockPromise({ - block, - message: "", - chunkGraph, - runtimeRequirements - })}.then(${runtimeTemplate.returningFunction( - runtimeTemplate.returningFunction( - `(${modules - .map(({ module, request }) => - runtimeTemplate.moduleRaw({ - module, - chunkGraph, - request, - weak: false, - runtimeRequirements - }) - ) - .join(", ")})` - ) - )});`; - } +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ - getters.push( - `${JSON.stringify(modules[0].name)}: ${runtimeTemplate.basicFunction( - "", - str - )}` - ); - } - const source = Template.asString([ - `var moduleMap = {`, - Template.indent(getters.join(",\n")), - "};", - `var get = ${runtimeTemplate.basicFunction("module, getScope", [ - `${RuntimeGlobals.currentRemoteGetScope} = getScope;`, - // reusing the getScope variable to avoid creating a new var (and module is also used later) - "getScope = (", - Template.indent([ - `${RuntimeGlobals.hasOwnProperty}(moduleMap, module)`, - Template.indent([ - "? moduleMap[module]()", - `: Promise.resolve().then(${runtimeTemplate.basicFunction( - "", - "throw new Error('Module \"' + module + '\" does not exist in container.');" - )})` - ]) - ]), - ");", - `${RuntimeGlobals.currentRemoteGetScope} = undefined;`, - "return getScope;" - ])};`, - `var init = ${runtimeTemplate.basicFunction("shareScope, initScope", [ - `if (!${RuntimeGlobals.shareScopeMap}) return;`, - `var oldScope = ${RuntimeGlobals.shareScopeMap}[${JSON.stringify( - this._shareScope - )}];`, - `var name = ${JSON.stringify(this._shareScope)}`, - `if(oldScope && oldScope !== shareScope) throw new Error("Container initialization failed as it has already been initialized with a different share scope");`, - `${RuntimeGlobals.shareScopeMap}[name] = shareScope;`, - `return ${RuntimeGlobals.initializeSharing}(name, initScope);` - ])};`, - "", - "// This exports getters to disallow modifications", - `${RuntimeGlobals.definePropertyGetters}(exports, {`, - Template.indent([ - `get: ${runtimeTemplate.returningFunction("get")},`, - `init: ${runtimeTemplate.returningFunction("init")}` - ]), - "});" - ]); - sources.set( - "javascript", - this.useSourceMap || this.useSimpleSourceMap - ? new OriginalSource(source, "webpack/container-entry") - : new RawSource(source) - ); +const InitFragment = __webpack_require__(51739); +const RuntimeGlobals = __webpack_require__(49404); +const Template = __webpack_require__(92066); - return { - sources, - runtimeRequirements - }; - } +/** @typedef {import("webpack-sources").Source} Source */ +/** @typedef {import("../Generator").GenerateContext} GenerateContext */ +/** + * @typedef {GenerateContext} Context + */ +class AwaitDependenciesInitFragment extends InitFragment { /** - * @param {string=} type the source type for which the size should be estimated - * @returns {number} the estimated size of the module (must be non-zero) + * @param {Set} promises the promises that should be awaited */ - size(type) { - return 42; + constructor(promises) { + super( + undefined, + InitFragment.STAGE_ASYNC_DEPENDENCIES, + 0, + "await-dependencies" + ); + this.promises = promises; } - serialize(context) { - const { write } = context; - write(this._name); - write(this._exposes); - write(this._shareScope); - super.serialize(context); + merge(other) { + const promises = new Set(this.promises); + for (const p of other.promises) { + promises.add(p); + } + return new AwaitDependenciesInitFragment(promises); } - static deserialize(context) { - const { read } = context; - const obj = new ContainerEntryModule(read(), read(), read()); - obj.deserialize(context); - return obj; + /** + * @param {Context} context context + * @returns {string|Source} the source code that will be included as initialization code + */ + getContent({ runtimeRequirements }) { + runtimeRequirements.add(RuntimeGlobals.module); + const promises = this.promises; + if (promises.size === 0) { + return ""; + } + if (promises.size === 1) { + for (const p of promises) { + return Template.asString([ + `var __webpack_async_dependencies__ = __webpack_handle_async_dependencies__([${p}]);`, + `${p} = (__webpack_async_dependencies__.then ? await __webpack_async_dependencies__ : __webpack_async_dependencies__)[0];`, + "" + ]); + } + } + const sepPromises = Array.from(promises).join(", "); + // TODO check if destructuring is supported + return Template.asString([ + `var __webpack_async_dependencies__ = __webpack_handle_async_dependencies__([${sepPromises}]);`, + `([${sepPromises}] = __webpack_async_dependencies__.then ? await __webpack_async_dependencies__ : __webpack_async_dependencies__);`, + "" + ]); } } -makeSerializable( - ContainerEntryModule, - "webpack/lib/container/ContainerEntryModule" -); - -module.exports = ContainerEntryModule; +module.exports = AwaitDependenciesInitFragment; /***/ }), -/***/ 52644: +/***/ 79471: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; /* MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra, Zackary Jackson @ScriptedAlchemy, Marais Rossouw @maraisr + Author Tobias Koppers @sokra */ -const ModuleFactory = __webpack_require__(61574); -const ContainerEntryModule = __webpack_require__(3234); +const HarmonyImportDependency = __webpack_require__(19577); -/** @typedef {import("../ModuleFactory").ModuleFactoryCreateData} ModuleFactoryCreateData */ -/** @typedef {import("../ModuleFactory").ModuleFactoryResult} ModuleFactoryResult */ -/** @typedef {import("./ContainerEntryDependency")} ContainerEntryDependency */ +/** @typedef {import("../Compiler")} Compiler */ +/** @typedef {import("../Module")} Module */ -module.exports = class ContainerEntryModuleFactory extends ModuleFactory { +class InferAsyncModulesPlugin { /** - * @param {ModuleFactoryCreateData} data data object - * @param {function(Error=, ModuleFactoryResult=): void} callback callback + * Apply the plugin + * @param {Compiler} compiler the compiler instance * @returns {void} */ - create({ dependencies: [dependency] }, callback) { - const dep = /** @type {ContainerEntryDependency} */ (dependency); - callback(null, { - module: new ContainerEntryModule(dep.name, dep.exposes, dep.shareScope) + apply(compiler) { + compiler.hooks.compilation.tap("InferAsyncModulesPlugin", compilation => { + const { moduleGraph } = compilation; + compilation.hooks.finishModules.tap( + "InferAsyncModulesPlugin", + modules => { + /** @type {Set} */ + const queue = new Set(); + for (const module of modules) { + if (module.buildMeta && module.buildMeta.async) { + queue.add(module); + } + } + for (const module of queue) { + moduleGraph.setAsync(module); + for (const [ + originModule, + connections + ] of moduleGraph.getIncomingConnectionsByOriginModule(module)) { + if ( + connections.some( + c => + c.dependency instanceof HarmonyImportDependency && + c.isTargetActive(undefined) + ) + ) { + queue.add(originModule); + } + } + } + } + ); }); } -}; +} + +module.exports = InferAsyncModulesPlugin; /***/ }), -/***/ 50: +/***/ 21743: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; /* MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra, Zackary Jackson @ScriptedAlchemy, Marais Rossouw @maraisr + Author Tobias Koppers @sokra */ -const ModuleDependency = __webpack_require__(80944); -const makeSerializable = __webpack_require__(26522); +const AsyncDependencyToInitialChunkError = __webpack_require__(69073); +const { connectChunkGroupParentAndChild } = __webpack_require__(76652); +const ModuleGraphConnection = __webpack_require__(94144); +const { getEntryRuntime, mergeRuntime } = __webpack_require__(19655); + +/** @typedef {import("./AsyncDependenciesBlock")} AsyncDependenciesBlock */ +/** @typedef {import("./Chunk")} Chunk */ +/** @typedef {import("./ChunkGroup")} ChunkGroup */ +/** @typedef {import("./Compilation")} Compilation */ +/** @typedef {import("./DependenciesBlock")} DependenciesBlock */ +/** @typedef {import("./Dependency")} Dependency */ +/** @typedef {import("./Entrypoint")} Entrypoint */ +/** @typedef {import("./Module")} Module */ +/** @typedef {import("./ModuleGraph")} ModuleGraph */ +/** @typedef {import("./ModuleGraphConnection").ConnectionState} ConnectionState */ +/** @typedef {import("./logging/Logger").Logger} Logger */ +/** @typedef {import("./util/runtime").RuntimeSpec} RuntimeSpec */ + +/** + * @typedef {Object} QueueItem + * @property {number} action + * @property {DependenciesBlock} block + * @property {Module} module + * @property {Chunk} chunk + * @property {ChunkGroup} chunkGroup + * @property {ChunkGroupInfo} chunkGroupInfo + */ + +/** @typedef {Set & { plus: Set }} ModuleSetPlus */ + +/** + * @typedef {Object} ChunkGroupInfo + * @property {ChunkGroup} chunkGroup the chunk group + * @property {RuntimeSpec} runtime the runtimes + * @property {ModuleSetPlus} minAvailableModules current minimal set of modules available at this point + * @property {boolean} minAvailableModulesOwned true, if minAvailableModules is owned and can be modified + * @property {ModuleSetPlus[]} availableModulesToBeMerged enqueued updates to the minimal set of available modules + * @property {Set=} skippedItems modules that were skipped because module is already available in parent chunks (need to reconsider when minAvailableModules is shrinking) + * @property {Set<[Module, ConnectionState]>=} skippedModuleConnections referenced modules that where skipped because they were not active in this runtime + * @property {ModuleSetPlus} resultingAvailableModules set of modules available including modules from this chunk group + * @property {Set} children set of children chunk groups, that will be revisited when availableModules shrink + * @property {Set} availableSources set of chunk groups that are the source for minAvailableModules + * @property {Set} availableChildren set of chunk groups which depend on the this chunk group as availableSource + * @property {number} preOrderIndex next pre order index + * @property {number} postOrderIndex next post order index + * @property {boolean} chunkLoading has a chunk loading mechanism + * @property {boolean} asyncChunks create async chunks + */ + +/** + * @typedef {Object} BlockChunkGroupConnection + * @property {ChunkGroupInfo} originChunkGroupInfo origin chunk group + * @property {ChunkGroup} chunkGroup referenced chunk group + */ + +const EMPTY_SET = /** @type {ModuleSetPlus} */ (new Set()); +EMPTY_SET.plus = EMPTY_SET; + +/** + * @param {ModuleSetPlus} a first set + * @param {ModuleSetPlus} b second set + * @returns {number} cmp + */ +const bySetSize = (a, b) => { + return b.size + b.plus.size - a.size - a.plus.size; +}; + +const extractBlockModules = (module, moduleGraph, runtime, blockModulesMap) => { + let blockCache; + let modules; + + const arrays = []; + + const queue = [module]; + while (queue.length > 0) { + const block = queue.pop(); + const arr = []; + arrays.push(arr); + blockModulesMap.set(block, arr); + for (const b of block.blocks) { + queue.push(b); + } + } + + for (const connection of moduleGraph.getOutgoingConnections(module)) { + const d = connection.dependency; + // We skip connections without dependency + if (!d) continue; + const m = connection.module; + // We skip connections without Module pointer + if (!m) continue; + // We skip weak connections + if (connection.weak) continue; + const state = connection.getActiveState(runtime); + // We skip inactive connections + if (state === false) continue; + + const block = moduleGraph.getParentBlock(d); + let index = moduleGraph.getParentBlockIndex(d); + + // deprecated fallback + if (index < 0) { + index = block.dependencies.indexOf(d); + } + + if (blockCache !== block) { + modules = blockModulesMap.get((blockCache = block)); + } + + const i = index << 2; + modules[i] = m; + modules[i + 1] = state; + } + + for (const modules of arrays) { + if (modules.length === 0) continue; + let indexMap; + let length = 0; + outer: for (let j = 0; j < modules.length; j += 2) { + const m = modules[j]; + if (m === undefined) continue; + const state = modules[j + 1]; + if (indexMap === undefined) { + let i = 0; + for (; i < length; i += 2) { + if (modules[i] === m) { + const merged = modules[i + 1]; + if (merged === true) continue outer; + modules[i + 1] = ModuleGraphConnection.addConnectionStates( + merged, + state + ); + } + } + modules[length] = m; + length++; + modules[length] = state; + length++; + if (length > 30) { + // To avoid worse case performance, we will use an index map for + // linear cost access, which allows to maintain O(n) complexity + // while keeping allocations down to a minimum + indexMap = new Map(); + for (let i = 0; i < length; i += 2) { + indexMap.set(modules[i], i + 1); + } + } + } else { + const idx = indexMap.get(m); + if (idx !== undefined) { + const merged = modules[idx]; + if (merged === true) continue outer; + modules[idx] = ModuleGraphConnection.addConnectionStates( + merged, + state + ); + } else { + modules[length] = m; + length++; + modules[length] = state; + indexMap.set(m, length); + length++; + } + } + } + modules.length = length; + } +}; + +/** + * + * @param {Logger} logger a logger + * @param {Compilation} compilation the compilation + * @param {Map} inputEntrypointsAndModules chunk groups which are processed with the modules + * @param {Map} chunkGroupInfoMap mapping from chunk group to available modules + * @param {Map} blockConnections connection for blocks + * @param {Set} blocksWithNestedBlocks flag for blocks that have nested blocks + * @param {Set} allCreatedChunkGroups filled with all chunk groups that are created here + */ +const visitModules = ( + logger, + compilation, + inputEntrypointsAndModules, + chunkGroupInfoMap, + blockConnections, + blocksWithNestedBlocks, + allCreatedChunkGroups +) => { + const { moduleGraph, chunkGraph, moduleMemCaches } = compilation; + + const blockModulesRuntimeMap = new Map(); + + /** @type {RuntimeSpec | false} */ + let blockModulesMapRuntime = false; + let blockModulesMap; + + /** + * + * @param {DependenciesBlock} block block + * @param {RuntimeSpec} runtime runtime + * @returns {(Module | ConnectionState)[]} block modules in flatten tuples + */ + const getBlockModules = (block, runtime) => { + if (blockModulesMapRuntime !== runtime) { + blockModulesMap = blockModulesRuntimeMap.get(runtime); + if (blockModulesMap === undefined) { + blockModulesMap = new Map(); + blockModulesRuntimeMap.set(runtime, blockModulesMap); + } + } + let blockModules = blockModulesMap.get(block); + if (blockModules !== undefined) return blockModules; + const module = /** @type {Module} */ (block.getRootBlock()); + const memCache = moduleMemCaches && moduleMemCaches.get(module); + if (memCache !== undefined) { + const map = memCache.provide( + "bundleChunkGraph.blockModules", + runtime, + () => { + logger.time("visitModules: prepare"); + const map = new Map(); + extractBlockModules(module, moduleGraph, runtime, map); + logger.timeAggregate("visitModules: prepare"); + return map; + } + ); + for (const [block, blockModules] of map) + blockModulesMap.set(block, blockModules); + return map.get(block); + } else { + logger.time("visitModules: prepare"); + extractBlockModules(module, moduleGraph, runtime, blockModulesMap); + blockModules = blockModulesMap.get(block); + logger.timeAggregate("visitModules: prepare"); + return blockModules; + } + }; + + let statProcessedQueueItems = 0; + let statProcessedBlocks = 0; + let statConnectedChunkGroups = 0; + let statProcessedChunkGroupsForMerging = 0; + let statMergedAvailableModuleSets = 0; + let statForkedAvailableModules = 0; + let statForkedAvailableModulesCount = 0; + let statForkedAvailableModulesCountPlus = 0; + let statForkedMergedModulesCount = 0; + let statForkedMergedModulesCountPlus = 0; + let statForkedResultModulesCount = 0; + let statChunkGroupInfoUpdated = 0; + let statChildChunkGroupsReconnected = 0; + + let nextChunkGroupIndex = 0; + let nextFreeModulePreOrderIndex = 0; + let nextFreeModulePostOrderIndex = 0; + + /** @type {Map} */ + const blockChunkGroups = new Map(); + + /** @type {Map} */ + const namedChunkGroups = new Map(); -class ContainerExposedDependency extends ModuleDependency { - /** - * @param {string} exposedName public name - * @param {string} request request to module - */ - constructor(exposedName, request) { - super(request); - this.exposedName = exposedName; - } + /** @type {Map} */ + const namedAsyncEntrypoints = new Map(); - get type() { - return "container exposed"; - } + const ADD_AND_ENTER_ENTRY_MODULE = 0; + const ADD_AND_ENTER_MODULE = 1; + const ENTER_MODULE = 2; + const PROCESS_BLOCK = 3; + const PROCESS_ENTRY_BLOCK = 4; + const LEAVE_MODULE = 5; - get category() { - return "esm"; - } + /** @type {QueueItem[]} */ + let queue = []; - /** - * @returns {string | null} an identifier to merge equal requests - */ - getResourceIdentifier() { - return `exposed dependency ${this.exposedName}=${this.request}`; - } + /** @type {Map>} */ + const queueConnect = new Map(); + /** @type {Set} */ + const chunkGroupsForCombining = new Set(); - serialize(context) { - context.write(this.exposedName); - super.serialize(context); + // Fill queue with entrypoint modules + // Create ChunkGroupInfo for entrypoints + for (const [chunkGroup, modules] of inputEntrypointsAndModules) { + const runtime = getEntryRuntime( + compilation, + chunkGroup.name, + chunkGroup.options + ); + /** @type {ChunkGroupInfo} */ + const chunkGroupInfo = { + chunkGroup, + runtime, + minAvailableModules: undefined, + minAvailableModulesOwned: false, + availableModulesToBeMerged: [], + skippedItems: undefined, + resultingAvailableModules: undefined, + children: undefined, + availableSources: undefined, + availableChildren: undefined, + preOrderIndex: 0, + postOrderIndex: 0, + chunkLoading: + chunkGroup.options.chunkLoading !== undefined + ? chunkGroup.options.chunkLoading !== false + : compilation.outputOptions.chunkLoading !== false, + asyncChunks: + chunkGroup.options.asyncChunks !== undefined + ? chunkGroup.options.asyncChunks + : compilation.outputOptions.asyncChunks !== false + }; + chunkGroup.index = nextChunkGroupIndex++; + if (chunkGroup.getNumberOfParents() > 0) { + // minAvailableModules for child entrypoints are unknown yet, set to undefined. + // This means no module is added until other sets are merged into + // this minAvailableModules (by the parent entrypoints) + const skippedItems = new Set(); + for (const module of modules) { + skippedItems.add(module); + } + chunkGroupInfo.skippedItems = skippedItems; + chunkGroupsForCombining.add(chunkGroupInfo); + } else { + // The application may start here: We start with an empty list of available modules + chunkGroupInfo.minAvailableModules = EMPTY_SET; + const chunk = chunkGroup.getEntrypointChunk(); + for (const module of modules) { + queue.push({ + action: ADD_AND_ENTER_MODULE, + block: module, + module, + chunk, + chunkGroup, + chunkGroupInfo + }); + } + } + chunkGroupInfoMap.set(chunkGroup, chunkGroupInfo); + if (chunkGroup.name) { + namedChunkGroups.set(chunkGroup.name, chunkGroupInfo); + } } - - deserialize(context) { - this.exposedName = context.read(); - super.deserialize(context); + // Fill availableSources with parent-child dependencies between entrypoints + for (const chunkGroupInfo of chunkGroupsForCombining) { + const { chunkGroup } = chunkGroupInfo; + chunkGroupInfo.availableSources = new Set(); + for (const parent of chunkGroup.parentsIterable) { + const parentChunkGroupInfo = chunkGroupInfoMap.get(parent); + chunkGroupInfo.availableSources.add(parentChunkGroupInfo); + if (parentChunkGroupInfo.availableChildren === undefined) { + parentChunkGroupInfo.availableChildren = new Set(); + } + parentChunkGroupInfo.availableChildren.add(chunkGroupInfo); + } } -} - -makeSerializable( - ContainerExposedDependency, - "webpack/lib/container/ContainerExposedDependency" -); - -module.exports = ContainerExposedDependency; - + // pop() is used to read from the queue + // so it need to be reversed to be iterated in + // correct order + queue.reverse(); -/***/ }), + /** @type {Set} */ + const outdatedChunkGroupInfo = new Set(); + /** @type {Set} */ + const chunkGroupsForMerging = new Set(); + /** @type {QueueItem[]} */ + let queueDelayed = []; -/***/ 20962: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + /** @type {[Module, ConnectionState][]} */ + const skipConnectionBuffer = []; + /** @type {Module[]} */ + const skipBuffer = []; + /** @type {QueueItem[]} */ + const queueBuffer = []; -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra, Zackary Jackson @ScriptedAlchemy, Marais Rossouw @maraisr -*/ + /** @type {Module} */ + let module; + /** @type {Chunk} */ + let chunk; + /** @type {ChunkGroup} */ + let chunkGroup; + /** @type {DependenciesBlock} */ + let block; + /** @type {ChunkGroupInfo} */ + let chunkGroupInfo; + // For each async Block in graph + /** + * @param {AsyncDependenciesBlock} b iterating over each Async DepBlock + * @returns {void} + */ + const iteratorBlock = b => { + // 1. We create a chunk group with single chunk in it for this Block + // but only once (blockChunkGroups map) + let cgi = blockChunkGroups.get(b); + /** @type {ChunkGroup} */ + let c; + /** @type {Entrypoint} */ + let entrypoint; + const entryOptions = b.groupOptions && b.groupOptions.entryOptions; + if (cgi === undefined) { + const chunkName = (b.groupOptions && b.groupOptions.name) || b.chunkName; + if (entryOptions) { + cgi = namedAsyncEntrypoints.get(chunkName); + if (!cgi) { + entrypoint = compilation.addAsyncEntrypoint( + entryOptions, + module, + b.loc, + b.request + ); + entrypoint.index = nextChunkGroupIndex++; + cgi = { + chunkGroup: entrypoint, + runtime: entrypoint.options.runtime || entrypoint.name, + minAvailableModules: EMPTY_SET, + minAvailableModulesOwned: false, + availableModulesToBeMerged: [], + skippedItems: undefined, + resultingAvailableModules: undefined, + children: undefined, + availableSources: undefined, + availableChildren: undefined, + preOrderIndex: 0, + postOrderIndex: 0, + chunkLoading: + entryOptions.chunkLoading !== undefined + ? entryOptions.chunkLoading !== false + : chunkGroupInfo.chunkLoading, + asyncChunks: + entryOptions.asyncChunks !== undefined + ? entryOptions.asyncChunks + : chunkGroupInfo.asyncChunks + }; + chunkGroupInfoMap.set(entrypoint, cgi); + chunkGraph.connectBlockAndChunkGroup(b, entrypoint); + if (chunkName) { + namedAsyncEntrypoints.set(chunkName, cgi); + } + } else { + entrypoint = /** @type {Entrypoint} */ (cgi.chunkGroup); + // TODO merge entryOptions + entrypoint.addOrigin(module, b.loc, b.request); + chunkGraph.connectBlockAndChunkGroup(b, entrypoint); + } -const createSchemaValidation = __webpack_require__(77695); -const ContainerEntryDependency = __webpack_require__(44055); -const ContainerEntryModuleFactory = __webpack_require__(52644); -const ContainerExposedDependency = __webpack_require__(50); -const { parseOptions } = __webpack_require__(56084); + // 2. We enqueue the DependenciesBlock for traversal + queueDelayed.push({ + action: PROCESS_ENTRY_BLOCK, + block: b, + module: module, + chunk: entrypoint.chunks[0], + chunkGroup: entrypoint, + chunkGroupInfo: cgi + }); + } else if (!chunkGroupInfo.asyncChunks || !chunkGroupInfo.chunkLoading) { + // Just queue the block into the current chunk group + queue.push({ + action: PROCESS_BLOCK, + block: b, + module: module, + chunk, + chunkGroup, + chunkGroupInfo + }); + } else { + cgi = chunkName && namedChunkGroups.get(chunkName); + if (!cgi) { + c = compilation.addChunkInGroup( + b.groupOptions || b.chunkName, + module, + b.loc, + b.request + ); + c.index = nextChunkGroupIndex++; + cgi = { + chunkGroup: c, + runtime: chunkGroupInfo.runtime, + minAvailableModules: undefined, + minAvailableModulesOwned: undefined, + availableModulesToBeMerged: [], + skippedItems: undefined, + resultingAvailableModules: undefined, + children: undefined, + availableSources: undefined, + availableChildren: undefined, + preOrderIndex: 0, + postOrderIndex: 0, + chunkLoading: chunkGroupInfo.chunkLoading, + asyncChunks: chunkGroupInfo.asyncChunks + }; + allCreatedChunkGroups.add(c); + chunkGroupInfoMap.set(c, cgi); + if (chunkName) { + namedChunkGroups.set(chunkName, cgi); + } + } else { + c = cgi.chunkGroup; + if (c.isInitial()) { + compilation.errors.push( + new AsyncDependencyToInitialChunkError(chunkName, module, b.loc) + ); + c = chunkGroup; + } + c.addOptions(b.groupOptions); + c.addOrigin(module, b.loc, b.request); + } + blockConnections.set(b, []); + } + blockChunkGroups.set(b, cgi); + } else if (entryOptions) { + entrypoint = /** @type {Entrypoint} */ (cgi.chunkGroup); + } else { + c = cgi.chunkGroup; + } -/** @typedef {import("../../declarations/plugins/container/ContainerPlugin").ContainerPluginOptions} ContainerPluginOptions */ -/** @typedef {import("../Compiler")} Compiler */ + if (c !== undefined) { + // 2. We store the connection for the block + // to connect it later if needed + blockConnections.get(b).push({ + originChunkGroupInfo: chunkGroupInfo, + chunkGroup: c + }); -const validate = createSchemaValidation( - __webpack_require__(3844), - () => __webpack_require__(18374), - { - name: "Container Plugin", - baseDataPath: "options" - } -); + // 3. We enqueue the chunk group info creation/updating + let connectList = queueConnect.get(chunkGroupInfo); + if (connectList === undefined) { + connectList = new Set(); + queueConnect.set(chunkGroupInfo, connectList); + } + connectList.add(cgi); -const PLUGIN_NAME = "ContainerPlugin"; + // TODO check if this really need to be done for each traversal + // or if it is enough when it's queued when created + // 4. We enqueue the DependenciesBlock for traversal + queueDelayed.push({ + action: PROCESS_BLOCK, + block: b, + module: module, + chunk: c.chunks[0], + chunkGroup: c, + chunkGroupInfo: cgi + }); + } else if (entrypoint !== undefined) { + chunkGroupInfo.chunkGroup.addAsyncEntrypoint(entrypoint); + } + }; -class ContainerPlugin { /** - * @param {ContainerPluginOptions} options options + * @param {DependenciesBlock} block the block + * @returns {void} */ - constructor(options) { - validate(options); + const processBlock = block => { + statProcessedBlocks++; + // get prepared block info + const blockModules = getBlockModules(block, chunkGroupInfo.runtime); - this._options = { - name: options.name, - shareScope: options.shareScope || "default", - library: options.library || { - type: "var", - name: options.name - }, - runtime: options.runtime, - filename: options.filename || undefined, - exposes: parseOptions( - options.exposes, - item => ({ - import: Array.isArray(item) ? item : [item], - name: undefined - }), - item => ({ - import: Array.isArray(item.import) ? item.import : [item.import], - name: item.name || undefined - }) - ) - }; - } + if (blockModules !== undefined) { + const { minAvailableModules } = chunkGroupInfo; + // Buffer items because order need to be reversed to get indices correct + // Traverse all referenced modules + for (let i = 0; i < blockModules.length; i += 2) { + const refModule = /** @type {Module} */ (blockModules[i]); + if (chunkGraph.isModuleInChunk(refModule, chunk)) { + // skip early if already connected + continue; + } + const activeState = /** @type {ConnectionState} */ ( + blockModules[i + 1] + ); + if (activeState !== true) { + skipConnectionBuffer.push([refModule, activeState]); + if (activeState === false) continue; + } + if ( + activeState === true && + (minAvailableModules.has(refModule) || + minAvailableModules.plus.has(refModule)) + ) { + // already in parent chunks, skip it for now + skipBuffer.push(refModule); + continue; + } + // enqueue, then add and enter to be in the correct order + // this is relevant with circular dependencies + queueBuffer.push({ + action: activeState === true ? ADD_AND_ENTER_MODULE : PROCESS_BLOCK, + block: refModule, + module: refModule, + chunk, + chunkGroup, + chunkGroupInfo + }); + } + // Add buffered items in reverse order + if (skipConnectionBuffer.length > 0) { + let { skippedModuleConnections } = chunkGroupInfo; + if (skippedModuleConnections === undefined) { + chunkGroupInfo.skippedModuleConnections = skippedModuleConnections = + new Set(); + } + for (let i = skipConnectionBuffer.length - 1; i >= 0; i--) { + skippedModuleConnections.add(skipConnectionBuffer[i]); + } + skipConnectionBuffer.length = 0; + } + if (skipBuffer.length > 0) { + let { skippedItems } = chunkGroupInfo; + if (skippedItems === undefined) { + chunkGroupInfo.skippedItems = skippedItems = new Set(); + } + for (let i = skipBuffer.length - 1; i >= 0; i--) { + skippedItems.add(skipBuffer[i]); + } + skipBuffer.length = 0; + } + if (queueBuffer.length > 0) { + for (let i = queueBuffer.length - 1; i >= 0; i--) { + queue.push(queueBuffer[i]); + } + queueBuffer.length = 0; + } + } + + // Traverse all Blocks + for (const b of block.blocks) { + iteratorBlock(b); + } + + if (block.blocks.length > 0 && module !== block) { + blocksWithNestedBlocks.add(block); + } + }; /** - * Apply the plugin - * @param {Compiler} compiler the compiler instance + * @param {DependenciesBlock} block the block * @returns {void} */ - apply(compiler) { - const { name, exposes, shareScope, filename, library, runtime } = - this._options; - - compiler.options.output.enabledLibraryTypes.push(library.type); - - compiler.hooks.make.tapAsync(PLUGIN_NAME, (compilation, callback) => { - const dep = new ContainerEntryDependency(name, exposes, shareScope); - dep.loc = { name }; - compilation.addEntry( - compilation.options.context, - dep, - { - name, - filename, - runtime, - library - }, - error => { - if (error) return callback(error); - callback(); - } - ); - }); - - compiler.hooks.thisCompilation.tap( - PLUGIN_NAME, - (compilation, { normalModuleFactory }) => { - compilation.dependencyFactories.set( - ContainerEntryDependency, - new ContainerEntryModuleFactory() - ); + const processEntryBlock = block => { + statProcessedBlocks++; + // get prepared block info + const blockModules = getBlockModules(block, chunkGroupInfo.runtime); - compilation.dependencyFactories.set( - ContainerExposedDependency, - normalModuleFactory + if (blockModules !== undefined) { + // Traverse all referenced modules + for (let i = 0; i < blockModules.length; i += 2) { + const refModule = /** @type {Module} */ (blockModules[i]); + const activeState = /** @type {ConnectionState} */ ( + blockModules[i + 1] ); + // enqueue, then add and enter to be in the correct order + // this is relevant with circular dependencies + queueBuffer.push({ + action: + activeState === true ? ADD_AND_ENTER_ENTRY_MODULE : PROCESS_BLOCK, + block: refModule, + module: refModule, + chunk, + chunkGroup, + chunkGroupInfo + }); } - ); - } -} + // Add buffered items in reverse order + if (queueBuffer.length > 0) { + for (let i = queueBuffer.length - 1; i >= 0; i--) { + queue.push(queueBuffer[i]); + } + queueBuffer.length = 0; + } + } -module.exports = ContainerPlugin; + // Traverse all Blocks + for (const b of block.blocks) { + iteratorBlock(b); + } + if (block.blocks.length > 0 && module !== block) { + blocksWithNestedBlocks.add(block); + } + }; -/***/ }), + const processQueue = () => { + while (queue.length) { + statProcessedQueueItems++; + const queueItem = queue.pop(); + module = queueItem.module; + block = queueItem.block; + chunk = queueItem.chunk; + chunkGroup = queueItem.chunkGroup; + chunkGroupInfo = queueItem.chunkGroupInfo; -/***/ 17813: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + switch (queueItem.action) { + case ADD_AND_ENTER_ENTRY_MODULE: + chunkGraph.connectChunkAndEntryModule( + chunk, + module, + /** @type {Entrypoint} */ (chunkGroup) + ); + // fallthrough + case ADD_AND_ENTER_MODULE: { + if (chunkGraph.isModuleInChunk(module, chunk)) { + // already connected, skip it + break; + } + // We connect Module and Chunk + chunkGraph.connectChunkAndModule(chunk, module); + } + // fallthrough + case ENTER_MODULE: { + const index = chunkGroup.getModulePreOrderIndex(module); + if (index === undefined) { + chunkGroup.setModulePreOrderIndex( + module, + chunkGroupInfo.preOrderIndex++ + ); + } -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra and Zackary Jackson @ScriptedAlchemy -*/ + if ( + moduleGraph.setPreOrderIndexIfUnset( + module, + nextFreeModulePreOrderIndex + ) + ) { + nextFreeModulePreOrderIndex++; + } + // reuse queueItem + queueItem.action = LEAVE_MODULE; + queue.push(queueItem); + } + // fallthrough + case PROCESS_BLOCK: { + processBlock(block); + break; + } + case PROCESS_ENTRY_BLOCK: { + processEntryBlock(block); + break; + } + case LEAVE_MODULE: { + const index = chunkGroup.getModulePostOrderIndex(module); + if (index === undefined) { + chunkGroup.setModulePostOrderIndex( + module, + chunkGroupInfo.postOrderIndex++ + ); + } + if ( + moduleGraph.setPostOrderIndexIfUnset( + module, + nextFreeModulePostOrderIndex + ) + ) { + nextFreeModulePostOrderIndex++; + } + break; + } + } + } + }; -const ExternalsPlugin = __webpack_require__(361); -const RuntimeGlobals = __webpack_require__(49404); -const createSchemaValidation = __webpack_require__(77695); -const FallbackDependency = __webpack_require__(41061); -const FallbackItemDependency = __webpack_require__(33393); -const FallbackModuleFactory = __webpack_require__(88180); -const RemoteModule = __webpack_require__(581); -const RemoteRuntimeModule = __webpack_require__(4603); -const RemoteToExternalDependency = __webpack_require__(44637); -const { parseOptions } = __webpack_require__(56084); + const calculateResultingAvailableModules = chunkGroupInfo => { + if (chunkGroupInfo.resultingAvailableModules) + return chunkGroupInfo.resultingAvailableModules; -/** @typedef {import("../../declarations/plugins/container/ContainerReferencePlugin").ContainerReferencePluginOptions} ContainerReferencePluginOptions */ -/** @typedef {import("../../declarations/plugins/container/ContainerReferencePlugin").RemotesConfig} RemotesConfig */ -/** @typedef {import("../Compiler")} Compiler */ + const minAvailableModules = chunkGroupInfo.minAvailableModules; -const validate = createSchemaValidation( - __webpack_require__(4464), - () => - __webpack_require__(31339), - { - name: "Container Reference Plugin", - baseDataPath: "options" - } -); + // Create a new Set of available modules at this point + // We want to be as lazy as possible. There are multiple ways doing this: + // Note that resultingAvailableModules is stored as "(a) + (b)" as it's a ModuleSetPlus + // - resultingAvailableModules = (modules of chunk) + (minAvailableModules + minAvailableModules.plus) + // - resultingAvailableModules = (minAvailableModules + modules of chunk) + (minAvailableModules.plus) + // We choose one depending on the size of minAvailableModules vs minAvailableModules.plus -const slashCode = "/".charCodeAt(0); + let resultingAvailableModules; + if (minAvailableModules.size > minAvailableModules.plus.size) { + // resultingAvailableModules = (modules of chunk) + (minAvailableModules + minAvailableModules.plus) + resultingAvailableModules = + /** @type {Set & {plus: Set}} */ (new Set()); + for (const module of minAvailableModules.plus) + minAvailableModules.add(module); + minAvailableModules.plus = EMPTY_SET; + resultingAvailableModules.plus = minAvailableModules; + chunkGroupInfo.minAvailableModulesOwned = false; + } else { + // resultingAvailableModules = (minAvailableModules + modules of chunk) + (minAvailableModules.plus) + resultingAvailableModules = + /** @type {Set & {plus: Set}} */ ( + new Set(minAvailableModules) + ); + resultingAvailableModules.plus = minAvailableModules.plus; + } -class ContainerReferencePlugin { - /** - * @param {ContainerReferencePluginOptions} options options - */ - constructor(options) { - validate(options); + // add the modules from the chunk group to the set + for (const chunk of chunkGroupInfo.chunkGroup.chunks) { + for (const m of chunkGraph.getChunkModulesIterable(chunk)) { + resultingAvailableModules.add(m); + } + } + return (chunkGroupInfo.resultingAvailableModules = + resultingAvailableModules); + }; - this._remoteType = options.remoteType; - this._remotes = parseOptions( - options.remotes, - item => ({ - external: Array.isArray(item) ? item : [item], - shareScope: options.shareScope || "default" - }), - item => ({ - external: Array.isArray(item.external) - ? item.external - : [item.external], - shareScope: item.shareScope || options.shareScope || "default" - }) - ); - } + const processConnectQueue = () => { + // Figure out new parents for chunk groups + // to get new available modules for these children + for (const [chunkGroupInfo, targets] of queueConnect) { + // 1. Add new targets to the list of children + if (chunkGroupInfo.children === undefined) { + chunkGroupInfo.children = targets; + } else { + for (const target of targets) { + chunkGroupInfo.children.add(target); + } + } - /** - * Apply the plugin - * @param {Compiler} compiler the compiler instance - * @returns {void} - */ - apply(compiler) { - const { _remotes: remotes, _remoteType: remoteType } = this; + // 2. Calculate resulting available modules + const resultingAvailableModules = + calculateResultingAvailableModules(chunkGroupInfo); - /** @type {Record} */ - const remoteExternals = {}; - for (const [key, config] of remotes) { - let i = 0; - for (const external of config.external) { - if (external.startsWith("internal ")) continue; - remoteExternals[ - `webpack/container/reference/${key}${i ? `/fallback-${i}` : ""}` - ] = external; - i++; + const runtime = chunkGroupInfo.runtime; + + // 3. Update chunk group info + for (const target of targets) { + target.availableModulesToBeMerged.push(resultingAvailableModules); + chunkGroupsForMerging.add(target); + const oldRuntime = target.runtime; + const newRuntime = mergeRuntime(oldRuntime, runtime); + if (oldRuntime !== newRuntime) { + target.runtime = newRuntime; + outdatedChunkGroupInfo.add(target); + } } + + statConnectedChunkGroups += targets.size; } + queueConnect.clear(); + }; - new ExternalsPlugin(remoteType, remoteExternals).apply(compiler); + const processChunkGroupsForMerging = () => { + statProcessedChunkGroupsForMerging += chunkGroupsForMerging.size; - compiler.hooks.compilation.tap( - "ContainerReferencePlugin", - (compilation, { normalModuleFactory }) => { - compilation.dependencyFactories.set( - RemoteToExternalDependency, - normalModuleFactory - ); + // Execute the merge + for (const info of chunkGroupsForMerging) { + const availableModulesToBeMerged = info.availableModulesToBeMerged; + let cachedMinAvailableModules = info.minAvailableModules; - compilation.dependencyFactories.set( - FallbackItemDependency, - normalModuleFactory - ); + statMergedAvailableModuleSets += availableModulesToBeMerged.length; - compilation.dependencyFactories.set( - FallbackDependency, - new FallbackModuleFactory() - ); + // 1. Get minimal available modules + // It doesn't make sense to traverse a chunk again with more available modules. + // This step calculates the minimal available modules and skips traversal when + // the list didn't shrink. + if (availableModulesToBeMerged.length > 1) { + availableModulesToBeMerged.sort(bySetSize); + } + let changed = false; + merge: for (const availableModules of availableModulesToBeMerged) { + if (cachedMinAvailableModules === undefined) { + cachedMinAvailableModules = availableModules; + info.minAvailableModules = cachedMinAvailableModules; + info.minAvailableModulesOwned = false; + changed = true; + } else { + if (info.minAvailableModulesOwned) { + // We own it and can modify it + if (cachedMinAvailableModules.plus === availableModules.plus) { + for (const m of cachedMinAvailableModules) { + if (!availableModules.has(m)) { + cachedMinAvailableModules.delete(m); + changed = true; + } + } + } else { + for (const m of cachedMinAvailableModules) { + if (!availableModules.has(m) && !availableModules.plus.has(m)) { + cachedMinAvailableModules.delete(m); + changed = true; + } + } + for (const m of cachedMinAvailableModules.plus) { + if (!availableModules.has(m) && !availableModules.plus.has(m)) { + // We can't remove modules from the plus part + // so we need to merge plus into the normal part to allow modifying it + const iterator = + cachedMinAvailableModules.plus[Symbol.iterator](); + // fast forward add all modules until m + /** @type {IteratorResult} */ + let it; + while (!(it = iterator.next()).done) { + const module = it.value; + if (module === m) break; + cachedMinAvailableModules.add(module); + } + // check the remaining modules before adding + while (!(it = iterator.next()).done) { + const module = it.value; + if ( + availableModules.has(module) || + availableModules.plus.has(m) + ) { + cachedMinAvailableModules.add(module); + } + } + cachedMinAvailableModules.plus = EMPTY_SET; + changed = true; + continue merge; + } + } + } + } else if (cachedMinAvailableModules.plus === availableModules.plus) { + // Common and fast case when the plus part is shared + // We only need to care about the normal part + if (availableModules.size < cachedMinAvailableModules.size) { + // the new availableModules is smaller so it's faster to + // fork from the new availableModules + statForkedAvailableModules++; + statForkedAvailableModulesCount += availableModules.size; + statForkedMergedModulesCount += cachedMinAvailableModules.size; + // construct a new Set as intersection of cachedMinAvailableModules and availableModules + const newSet = /** @type {ModuleSetPlus} */ (new Set()); + newSet.plus = availableModules.plus; + for (const m of availableModules) { + if (cachedMinAvailableModules.has(m)) { + newSet.add(m); + } + } + statForkedResultModulesCount += newSet.size; + cachedMinAvailableModules = newSet; + info.minAvailableModulesOwned = true; + info.minAvailableModules = newSet; + changed = true; + continue merge; + } + for (const m of cachedMinAvailableModules) { + if (!availableModules.has(m)) { + // cachedMinAvailableModules need to be modified + // but we don't own it + statForkedAvailableModules++; + statForkedAvailableModulesCount += + cachedMinAvailableModules.size; + statForkedMergedModulesCount += availableModules.size; + // construct a new Set as intersection of cachedMinAvailableModules and availableModules + // as the plus part is equal we can just take over this one + const newSet = /** @type {ModuleSetPlus} */ (new Set()); + newSet.plus = availableModules.plus; + const iterator = cachedMinAvailableModules[Symbol.iterator](); + // fast forward add all modules until m + /** @type {IteratorResult} */ + let it; + while (!(it = iterator.next()).done) { + const module = it.value; + if (module === m) break; + newSet.add(module); + } + // check the remaining modules before adding + while (!(it = iterator.next()).done) { + const module = it.value; + if (availableModules.has(module)) { + newSet.add(module); + } + } + statForkedResultModulesCount += newSet.size; + cachedMinAvailableModules = newSet; + info.minAvailableModulesOwned = true; + info.minAvailableModules = newSet; + changed = true; + continue merge; + } + } + } else { + for (const m of cachedMinAvailableModules) { + if (!availableModules.has(m) && !availableModules.plus.has(m)) { + // cachedMinAvailableModules need to be modified + // but we don't own it + statForkedAvailableModules++; + statForkedAvailableModulesCount += + cachedMinAvailableModules.size; + statForkedAvailableModulesCountPlus += + cachedMinAvailableModules.plus.size; + statForkedMergedModulesCount += availableModules.size; + statForkedMergedModulesCountPlus += availableModules.plus.size; + // construct a new Set as intersection of cachedMinAvailableModules and availableModules + const newSet = /** @type {ModuleSetPlus} */ (new Set()); + newSet.plus = EMPTY_SET; + const iterator = cachedMinAvailableModules[Symbol.iterator](); + // fast forward add all modules until m + /** @type {IteratorResult} */ + let it; + while (!(it = iterator.next()).done) { + const module = it.value; + if (module === m) break; + newSet.add(module); + } + // check the remaining modules before adding + while (!(it = iterator.next()).done) { + const module = it.value; + if ( + availableModules.has(module) || + availableModules.plus.has(module) + ) { + newSet.add(module); + } + } + // also check all modules in cachedMinAvailableModules.plus + for (const module of cachedMinAvailableModules.plus) { + if ( + availableModules.has(module) || + availableModules.plus.has(module) + ) { + newSet.add(module); + } + } + statForkedResultModulesCount += newSet.size; + cachedMinAvailableModules = newSet; + info.minAvailableModulesOwned = true; + info.minAvailableModules = newSet; + changed = true; + continue merge; + } + } + for (const m of cachedMinAvailableModules.plus) { + if (!availableModules.has(m) && !availableModules.plus.has(m)) { + // cachedMinAvailableModules need to be modified + // but we don't own it + statForkedAvailableModules++; + statForkedAvailableModulesCount += + cachedMinAvailableModules.size; + statForkedAvailableModulesCountPlus += + cachedMinAvailableModules.plus.size; + statForkedMergedModulesCount += availableModules.size; + statForkedMergedModulesCountPlus += availableModules.plus.size; + // construct a new Set as intersection of cachedMinAvailableModules and availableModules + // we already know that all modules directly from cachedMinAvailableModules are in availableModules too + const newSet = /** @type {ModuleSetPlus} */ ( + new Set(cachedMinAvailableModules) + ); + newSet.plus = EMPTY_SET; + const iterator = + cachedMinAvailableModules.plus[Symbol.iterator](); + // fast forward add all modules until m + /** @type {IteratorResult} */ + let it; + while (!(it = iterator.next()).done) { + const module = it.value; + if (module === m) break; + newSet.add(module); + } + // check the remaining modules before adding + while (!(it = iterator.next()).done) { + const module = it.value; + if ( + availableModules.has(module) || + availableModules.plus.has(module) + ) { + newSet.add(module); + } + } + statForkedResultModulesCount += newSet.size; + cachedMinAvailableModules = newSet; + info.minAvailableModulesOwned = true; + info.minAvailableModules = newSet; + changed = true; + continue merge; + } + } + } + } + } + availableModulesToBeMerged.length = 0; + if (changed) { + info.resultingAvailableModules = undefined; + outdatedChunkGroupInfo.add(info); + } + } + chunkGroupsForMerging.clear(); + }; + + const processChunkGroupsForCombining = () => { + for (const info of chunkGroupsForCombining) { + for (const source of info.availableSources) { + if (!source.minAvailableModules) { + chunkGroupsForCombining.delete(info); + break; + } + } + } + for (const info of chunkGroupsForCombining) { + const availableModules = /** @type {ModuleSetPlus} */ (new Set()); + availableModules.plus = EMPTY_SET; + const mergeSet = set => { + if (set.size > availableModules.plus.size) { + for (const item of availableModules.plus) availableModules.add(item); + availableModules.plus = set; + } else { + for (const item of set) availableModules.add(item); + } + }; + // combine minAvailableModules from all resultingAvailableModules + for (const source of info.availableSources) { + const resultingAvailableModules = + calculateResultingAvailableModules(source); + mergeSet(resultingAvailableModules); + mergeSet(resultingAvailableModules.plus); + } + info.minAvailableModules = availableModules; + info.minAvailableModulesOwned = false; + info.resultingAvailableModules = undefined; + outdatedChunkGroupInfo.add(info); + } + chunkGroupsForCombining.clear(); + }; - normalModuleFactory.hooks.factorize.tap( - "ContainerReferencePlugin", - data => { - if (!data.request.includes("!")) { - for (const [key, config] of remotes) { - if ( - data.request.startsWith(`${key}`) && - (data.request.length === key.length || - data.request.charCodeAt(key.length) === slashCode) - ) { - return new RemoteModule( - data.request, - config.external.map((external, i) => - external.startsWith("internal ") - ? external.slice(9) - : `webpack/container/reference/${key}${ - i ? `/fallback-${i}` : "" - }` - ), - `.${data.request.slice(key.length)}`, - config.shareScope - ); - } - } - } + const processOutdatedChunkGroupInfo = () => { + statChunkGroupInfoUpdated += outdatedChunkGroupInfo.size; + // Revisit skipped elements + for (const info of outdatedChunkGroupInfo) { + // 1. Reconsider skipped items + if (info.skippedItems !== undefined) { + const { minAvailableModules } = info; + for (const module of info.skippedItems) { + if ( + !minAvailableModules.has(module) && + !minAvailableModules.plus.has(module) + ) { + queue.push({ + action: ADD_AND_ENTER_MODULE, + block: module, + module, + chunk: info.chunkGroup.chunks[0], + chunkGroup: info.chunkGroup, + chunkGroupInfo: info + }); + info.skippedItems.delete(module); } - ); + } + } - compilation.hooks.runtimeRequirementInTree - .for(RuntimeGlobals.ensureChunkHandlers) - .tap("ContainerReferencePlugin", (chunk, set) => { - set.add(RuntimeGlobals.module); - set.add(RuntimeGlobals.moduleFactoriesAddOnly); - set.add(RuntimeGlobals.hasOwnProperty); - set.add(RuntimeGlobals.initializeSharing); - set.add(RuntimeGlobals.shareScopeMap); - compilation.addRuntimeModule(chunk, new RemoteRuntimeModule()); + // 2. Reconsider skipped connections + if (info.skippedModuleConnections !== undefined) { + const { minAvailableModules } = info; + for (const entry of info.skippedModuleConnections) { + const [module, activeState] = entry; + if (activeState === false) continue; + if (activeState === true) { + info.skippedModuleConnections.delete(entry); + } + if ( + activeState === true && + (minAvailableModules.has(module) || + minAvailableModules.plus.has(module)) + ) { + info.skippedItems.add(module); + continue; + } + queue.push({ + action: activeState === true ? ADD_AND_ENTER_MODULE : PROCESS_BLOCK, + block: module, + module, + chunk: info.chunkGroup.chunks[0], + chunkGroup: info.chunkGroup, + chunkGroupInfo: info }); + } } - ); - } -} - -module.exports = ContainerReferencePlugin; - - -/***/ }), - -/***/ 41061: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ - + // 2. Reconsider children chunk groups + if (info.children !== undefined) { + statChildChunkGroupsReconnected += info.children.size; + for (const cgi of info.children) { + let connectList = queueConnect.get(info); + if (connectList === undefined) { + connectList = new Set(); + queueConnect.set(info, connectList); + } + connectList.add(cgi); + } + } -const Dependency = __webpack_require__(50384); -const makeSerializable = __webpack_require__(26522); + // 3. Reconsider chunk groups for combining + if (info.availableChildren !== undefined) { + for (const cgi of info.availableChildren) { + chunkGroupsForCombining.add(cgi); + } + } + } + outdatedChunkGroupInfo.clear(); + }; -class FallbackDependency extends Dependency { - constructor(requests) { - super(); - this.requests = requests; - } + // Iterative traversal of the Module graph + // Recursive would be simpler to write but could result in Stack Overflows + while (queue.length || queueConnect.size) { + logger.time("visitModules: visiting"); + processQueue(); + logger.timeAggregateEnd("visitModules: prepare"); + logger.timeEnd("visitModules: visiting"); - /** - * @returns {string | null} an identifier to merge equal requests - */ - getResourceIdentifier() { - return `fallback ${this.requests.join(" ")}`; - } + if (chunkGroupsForCombining.size > 0) { + logger.time("visitModules: combine available modules"); + processChunkGroupsForCombining(); + logger.timeEnd("visitModules: combine available modules"); + } - get type() { - return "fallback"; - } + if (queueConnect.size > 0) { + logger.time("visitModules: calculating available modules"); + processConnectQueue(); + logger.timeEnd("visitModules: calculating available modules"); - get category() { - return "esm"; - } + if (chunkGroupsForMerging.size > 0) { + logger.time("visitModules: merging available modules"); + processChunkGroupsForMerging(); + logger.timeEnd("visitModules: merging available modules"); + } + } - serialize(context) { - const { write } = context; - write(this.requests); - super.serialize(context); - } + if (outdatedChunkGroupInfo.size > 0) { + logger.time("visitModules: check modules for revisit"); + processOutdatedChunkGroupInfo(); + logger.timeEnd("visitModules: check modules for revisit"); + } - static deserialize(context) { - const { read } = context; - const obj = new FallbackDependency(read()); - obj.deserialize(context); - return obj; + // Run queueDelayed when all items of the queue are processed + // This is important to get the global indexing correct + // Async blocks should be processed after all sync blocks are processed + if (queue.length === 0) { + const tempQueue = queue; + queue = queueDelayed.reverse(); + queueDelayed = tempQueue; + } } -} - -makeSerializable( - FallbackDependency, - "webpack/lib/container/FallbackDependency" -); - -module.exports = FallbackDependency; - - -/***/ }), - -/***/ 33393: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ + logger.log( + `${statProcessedQueueItems} queue items processed (${statProcessedBlocks} blocks)` + ); + logger.log(`${statConnectedChunkGroups} chunk groups connected`); + logger.log( + `${statProcessedChunkGroupsForMerging} chunk groups processed for merging (${statMergedAvailableModuleSets} module sets, ${statForkedAvailableModules} forked, ${statForkedAvailableModulesCount} + ${statForkedAvailableModulesCountPlus} modules forked, ${statForkedMergedModulesCount} + ${statForkedMergedModulesCountPlus} modules merged into fork, ${statForkedResultModulesCount} resulting modules)` + ); + logger.log( + `${statChunkGroupInfoUpdated} chunk group info updated (${statChildChunkGroupsReconnected} already connected chunk groups reconnected)` + ); +}; +/** + * + * @param {Compilation} compilation the compilation + * @param {Set} blocksWithNestedBlocks flag for blocks that have nested blocks + * @param {Map} blockConnections connection for blocks + * @param {Map} chunkGroupInfoMap mapping from chunk group to available modules + */ +const connectChunkGroups = ( + compilation, + blocksWithNestedBlocks, + blockConnections, + chunkGroupInfoMap +) => { + const { chunkGraph } = compilation; + /** + * Helper function to check if all modules of a chunk are available + * + * @param {ChunkGroup} chunkGroup the chunkGroup to scan + * @param {ModuleSetPlus} availableModules the comparator set + * @returns {boolean} return true if all modules of a chunk are available + */ + const areModulesAvailable = (chunkGroup, availableModules) => { + for (const chunk of chunkGroup.chunks) { + for (const module of chunkGraph.getChunkModulesIterable(chunk)) { + if (!availableModules.has(module) && !availableModules.plus.has(module)) + return false; + } + } + return true; + }; -const ModuleDependency = __webpack_require__(80944); -const makeSerializable = __webpack_require__(26522); + // For each edge in the basic chunk graph + for (const [block, connections] of blockConnections) { + // 1. Check if connection is needed + // When none of the dependencies need to be connected + // we can skip all of them + // It's not possible to filter each item so it doesn't create inconsistent + // connections and modules can only create one version + // TODO maybe decide this per runtime + if ( + // TODO is this needed? + !blocksWithNestedBlocks.has(block) && + connections.every(({ chunkGroup, originChunkGroupInfo }) => + areModulesAvailable( + chunkGroup, + originChunkGroupInfo.resultingAvailableModules + ) + ) + ) { + continue; + } -class FallbackItemDependency extends ModuleDependency { - constructor(request) { - super(request); - } + // 2. Foreach edge + for (let i = 0; i < connections.length; i++) { + const { chunkGroup, originChunkGroupInfo } = connections[i]; - get type() { - return "fallback item"; - } + // 3. Connect block with chunk + chunkGraph.connectBlockAndChunkGroup(block, chunkGroup); - get category() { - return "esm"; + // 4. Connect chunk with parent + connectChunkGroupParentAndChild( + originChunkGroupInfo.chunkGroup, + chunkGroup + ); + } } -} - -makeSerializable( - FallbackItemDependency, - "webpack/lib/container/FallbackItemDependency" -); - -module.exports = FallbackItemDependency; - - -/***/ }), - -/***/ 95193: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra and Zackary Jackson @ScriptedAlchemy -*/ - - - -const { RawSource } = __webpack_require__(96192); -const Module = __webpack_require__(85887); -const RuntimeGlobals = __webpack_require__(49404); -const Template = __webpack_require__(92066); -const makeSerializable = __webpack_require__(26522); -const FallbackItemDependency = __webpack_require__(33393); - -/** @typedef {import("../../declarations/WebpackOptions").WebpackOptionsNormalized} WebpackOptions */ -/** @typedef {import("../Chunk")} Chunk */ -/** @typedef {import("../ChunkGraph")} ChunkGraph */ -/** @typedef {import("../ChunkGroup")} ChunkGroup */ -/** @typedef {import("../Compilation")} Compilation */ -/** @typedef {import("../Module").CodeGenerationContext} CodeGenerationContext */ -/** @typedef {import("../Module").CodeGenerationResult} CodeGenerationResult */ -/** @typedef {import("../Module").LibIdentOptions} LibIdentOptions */ -/** @typedef {import("../Module").NeedBuildContext} NeedBuildContext */ -/** @typedef {import("../RequestShortener")} RequestShortener */ -/** @typedef {import("../ResolverFactory").ResolverWithOptions} ResolverWithOptions */ -/** @typedef {import("../WebpackError")} WebpackError */ -/** @typedef {import("../util/Hash")} Hash */ -/** @typedef {import("../util/fs").InputFileSystem} InputFileSystem */ - -const TYPES = new Set(["javascript"]); -const RUNTIME_REQUIREMENTS = new Set([RuntimeGlobals.module]); +}; -class FallbackModule extends Module { - /** - * @param {string[]} requests list of requests to choose one - */ - constructor(requests) { - super("fallback-module"); - this.requests = requests; - this._identifier = `fallback ${this.requests.join(" ")}`; - } +/** + * Remove all unconnected chunk groups + * @param {Compilation} compilation the compilation + * @param {Iterable} allCreatedChunkGroups all chunk groups that where created before + */ +const cleanupUnconnectedGroups = (compilation, allCreatedChunkGroups) => { + const { chunkGraph } = compilation; - /** - * @returns {string} a unique identifier of the module - */ - identifier() { - return this._identifier; + for (const chunkGroup of allCreatedChunkGroups) { + if (chunkGroup.getNumberOfParents() === 0) { + for (const chunk of chunkGroup.chunks) { + compilation.chunks.delete(chunk); + chunkGraph.disconnectChunk(chunk); + } + chunkGraph.disconnectChunkGroup(chunkGroup); + chunkGroup.remove(); + } } +}; - /** - * @param {RequestShortener} requestShortener the request shortener - * @returns {string} a user readable identifier of the module - */ - readableIdentifier(requestShortener) { - return this._identifier; - } +/** + * This method creates the Chunk graph from the Module graph + * @param {Compilation} compilation the compilation + * @param {Map} inputEntrypointsAndModules chunk groups which are processed with the modules + * @returns {void} + */ +const buildChunkGraph = (compilation, inputEntrypointsAndModules) => { + const logger = compilation.getLogger("webpack.buildChunkGraph"); - /** - * @param {LibIdentOptions} options options - * @returns {string | null} an identifier for library inclusion - */ - libIdent(options) { - return `webpack/container/fallback/${this.requests[0]}/and ${ - this.requests.length - 1 - } more`; - } + // SHARED STATE - /** - * @param {Chunk} chunk the chunk which condition should be checked - * @param {Compilation} compilation the compilation - * @returns {boolean} true, if the chunk is ok for the module - */ - chunkCondition(chunk, { chunkGraph }) { - return chunkGraph.getNumberOfEntryModules(chunk) > 0; - } + /** @type {Map} */ + const blockConnections = new Map(); - /** - * @param {NeedBuildContext} context context info - * @param {function(WebpackError=, boolean=): void} callback callback function, returns true, if the module needs a rebuild - * @returns {void} - */ - needBuild(context, callback) { - callback(null, !this.buildInfo); - } + /** @type {Set} */ + const allCreatedChunkGroups = new Set(); - /** - * @param {WebpackOptions} options webpack options - * @param {Compilation} compilation the compilation - * @param {ResolverWithOptions} resolver the resolver - * @param {InputFileSystem} fs the file system - * @param {function(WebpackError=): void} callback callback function - * @returns {void} - */ - build(options, compilation, resolver, fs, callback) { - this.buildMeta = {}; - this.buildInfo = { - strict: true - }; + /** @type {Map} */ + const chunkGroupInfoMap = new Map(); - this.clearDependenciesAndBlocks(); - for (const request of this.requests) - this.addDependency(new FallbackItemDependency(request)); + /** @type {Set} */ + const blocksWithNestedBlocks = new Set(); - callback(); - } + // PART ONE - /** - * @param {string=} type the source type for which the size should be estimated - * @returns {number} the estimated size of the module (must be non-zero) - */ - size(type) { - return this.requests.length * 5 + 42; - } + logger.time("visitModules"); + visitModules( + logger, + compilation, + inputEntrypointsAndModules, + chunkGroupInfoMap, + blockConnections, + blocksWithNestedBlocks, + allCreatedChunkGroups + ); + logger.timeEnd("visitModules"); - /** - * @returns {Set} types available (do not mutate) - */ - getSourceTypes() { - return TYPES; - } + // PART TWO - /** - * @param {CodeGenerationContext} context context for code generation - * @returns {CodeGenerationResult} result - */ - codeGeneration({ runtimeTemplate, moduleGraph, chunkGraph }) { - const ids = this.dependencies.map(dep => - chunkGraph.getModuleId(moduleGraph.getModule(dep)) - ); - const code = Template.asString([ - `var ids = ${JSON.stringify(ids)};`, - "var error, result, i = 0;", - `var loop = ${runtimeTemplate.basicFunction("next", [ - "while(i < ids.length) {", - Template.indent([ - "try { next = __webpack_require__(ids[i++]); } catch(e) { return handleError(e); }", - "if(next) return next.then ? next.then(handleResult, handleError) : handleResult(next);" - ]), - "}", - "if(error) throw error;" - ])}`, - `var handleResult = ${runtimeTemplate.basicFunction("result", [ - "if(result) return result;", - "return loop();" - ])};`, - `var handleError = ${runtimeTemplate.basicFunction("e", [ - "error = e;", - "return loop();" - ])};`, - "module.exports = loop();" - ]); - const sources = new Map(); - sources.set("javascript", new RawSource(code)); - return { sources, runtimeRequirements: RUNTIME_REQUIREMENTS }; - } + logger.time("connectChunkGroups"); + connectChunkGroups( + compilation, + blocksWithNestedBlocks, + blockConnections, + chunkGroupInfoMap + ); + logger.timeEnd("connectChunkGroups"); - serialize(context) { - const { write } = context; - write(this.requests); - super.serialize(context); + for (const [chunkGroup, chunkGroupInfo] of chunkGroupInfoMap) { + for (const chunk of chunkGroup.chunks) + chunk.runtime = mergeRuntime(chunk.runtime, chunkGroupInfo.runtime); } - static deserialize(context) { - const { read } = context; - const obj = new FallbackModule(read()); - obj.deserialize(context); - return obj; - } -} + // Cleanup work -makeSerializable(FallbackModule, "webpack/lib/container/FallbackModule"); + logger.time("cleanup"); + cleanupUnconnectedGroups(compilation, allCreatedChunkGroups); + logger.timeEnd("cleanup"); +}; -module.exports = FallbackModule; +module.exports = buildChunkGraph; /***/ }), -/***/ 88180: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { +/***/ 30743: +/***/ (function(module) { "use strict"; /* MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra, Zackary Jackson @ScriptedAlchemy, Marais Rossouw @maraisr + Author Tobias Koppers @sokra */ -const ModuleFactory = __webpack_require__(61574); -const FallbackModule = __webpack_require__(95193); +/** @typedef {import("../Compiler")} Compiler */ -/** @typedef {import("../ModuleFactory").ModuleFactoryCreateData} ModuleFactoryCreateData */ -/** @typedef {import("../ModuleFactory").ModuleFactoryResult} ModuleFactoryResult */ -/** @typedef {import("./FallbackDependency")} FallbackDependency */ +class AddBuildDependenciesPlugin { + /** + * @param {Iterable} buildDependencies list of build dependencies + */ + constructor(buildDependencies) { + this.buildDependencies = new Set(buildDependencies); + } -module.exports = class FallbackModuleFactory extends ModuleFactory { /** - * @param {ModuleFactoryCreateData} data data object - * @param {function(Error=, ModuleFactoryResult=): void} callback callback + * Apply the plugin + * @param {Compiler} compiler the compiler instance * @returns {void} */ - create({ dependencies: [dependency] }, callback) { - const dep = /** @type {FallbackDependency} */ (dependency); - callback(null, { - module: new FallbackModule(dep.requests) - }); + apply(compiler) { + compiler.hooks.compilation.tap( + "AddBuildDependenciesPlugin", + compilation => { + compilation.buildDependencies.addAll(this.buildDependencies); + } + ); } -}; +} + +module.exports = AddBuildDependenciesPlugin; /***/ }), -/***/ 22814: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { +/***/ 19724: +/***/ (function(module) { "use strict"; /* MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra and Zackary Jackson @ScriptedAlchemy + Author Tobias Koppers @sokra */ -const isValidExternalsType = __webpack_require__(11482); -const SharePlugin = __webpack_require__(25790); -const createSchemaValidation = __webpack_require__(77695); -const ContainerPlugin = __webpack_require__(20962); -const ContainerReferencePlugin = __webpack_require__(17813); - -/** @typedef {import("../../declarations/plugins/container/ModuleFederationPlugin").ExternalsType} ExternalsType */ -/** @typedef {import("../../declarations/plugins/container/ModuleFederationPlugin").ModuleFederationPluginOptions} ModuleFederationPluginOptions */ -/** @typedef {import("../../declarations/plugins/container/ModuleFederationPlugin").Shared} Shared */ /** @typedef {import("../Compiler")} Compiler */ -const validate = createSchemaValidation( - __webpack_require__(83622), - () => __webpack_require__(2320), - { - name: "Module Federation Plugin", - baseDataPath: "options" - } -); -class ModuleFederationPlugin { +class AddManagedPathsPlugin { /** - * @param {ModuleFederationPluginOptions} options options + * @param {Iterable} managedPaths list of managed paths + * @param {Iterable} immutablePaths list of immutable paths */ - constructor(options) { - validate(options); - - this._options = options; + constructor(managedPaths, immutablePaths) { + this.managedPaths = new Set(managedPaths); + this.immutablePaths = new Set(immutablePaths); } /** @@ -72148,374 +67537,256 @@ class ModuleFederationPlugin { * @returns {void} */ apply(compiler) { - const { _options: options } = this; - const library = options.library || { type: "var", name: options.name }; - const remoteType = - options.remoteType || - (options.library && isValidExternalsType(options.library.type) - ? /** @type {ExternalsType} */ (options.library.type) - : "script"); - if ( - library && - !compiler.options.output.enabledLibraryTypes.includes(library.type) - ) { - compiler.options.output.enabledLibraryTypes.push(library.type); + for (const managedPath of this.managedPaths) { + compiler.managedPaths.add(managedPath); + } + for (const immutablePath of this.immutablePaths) { + compiler.immutablePaths.add(immutablePath); } - compiler.hooks.afterPlugins.tap("ModuleFederationPlugin", () => { - if ( - options.exposes && - (Array.isArray(options.exposes) - ? options.exposes.length > 0 - : Object.keys(options.exposes).length > 0) - ) { - new ContainerPlugin({ - name: options.name, - library, - filename: options.filename, - runtime: options.runtime, - exposes: options.exposes - }).apply(compiler); - } - if ( - options.remotes && - (Array.isArray(options.remotes) - ? options.remotes.length > 0 - : Object.keys(options.remotes).length > 0) - ) { - new ContainerReferencePlugin({ - remoteType, - remotes: options.remotes - }).apply(compiler); - } - if (options.shared) { - new SharePlugin({ - shared: options.shared, - shareScope: options.shareScope - }).apply(compiler); - } - }); } } -module.exports = ModuleFederationPlugin; +module.exports = AddManagedPathsPlugin; /***/ }), -/***/ 581: +/***/ 26277: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; /* MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra and Zackary Jackson @ScriptedAlchemy + Author Tobias Koppers @sokra */ -const { RawSource } = __webpack_require__(96192); -const Module = __webpack_require__(85887); -const RuntimeGlobals = __webpack_require__(49404); -const makeSerializable = __webpack_require__(26522); -const FallbackDependency = __webpack_require__(41061); -const RemoteToExternalDependency = __webpack_require__(44637); - -/** @typedef {import("../../declarations/WebpackOptions").WebpackOptionsNormalized} WebpackOptions */ -/** @typedef {import("../ChunkGraph")} ChunkGraph */ -/** @typedef {import("../ChunkGroup")} ChunkGroup */ -/** @typedef {import("../Compilation")} Compilation */ -/** @typedef {import("../Module").CodeGenerationContext} CodeGenerationContext */ -/** @typedef {import("../Module").CodeGenerationResult} CodeGenerationResult */ -/** @typedef {import("../Module").LibIdentOptions} LibIdentOptions */ -/** @typedef {import("../Module").NeedBuildContext} NeedBuildContext */ -/** @typedef {import("../RequestShortener")} RequestShortener */ -/** @typedef {import("../ResolverFactory").ResolverWithOptions} ResolverWithOptions */ -/** @typedef {import("../WebpackError")} WebpackError */ -/** @typedef {import("../util/Hash")} Hash */ -/** @typedef {import("../util/fs").InputFileSystem} InputFileSystem */ - -const TYPES = new Set(["remote", "share-init"]); -const RUNTIME_REQUIREMENTS = new Set([RuntimeGlobals.module]); - -class RemoteModule extends Module { - /** - * @param {string} request request string - * @param {string[]} externalRequests list of external requests to containers - * @param {string} internalRequest name of exposed module in container - * @param {string} shareScope the used share scope name - */ - constructor(request, externalRequests, internalRequest, shareScope) { - super("remote-module"); - this.request = request; - this.externalRequests = externalRequests; - this.internalRequest = internalRequest; - this.shareScope = shareScope; - this._identifier = `remote (${shareScope}) ${this.externalRequests.join( - " " - )} ${this.internalRequest}`; - } - - /** - * @returns {string} a unique identifier of the module - */ - identifier() { - return this._identifier; - } +const Cache = __webpack_require__(99453); +const ProgressPlugin = __webpack_require__(41306); - /** - * @param {RequestShortener} requestShortener the request shortener - * @returns {string} a user readable identifier of the module - */ - readableIdentifier(requestShortener) { - return `remote ${this.request}`; - } +/** @typedef {import("../Compiler")} Compiler */ - /** - * @param {LibIdentOptions} options options - * @returns {string | null} an identifier for library inclusion - */ - libIdent(options) { - return `webpack/container/remote/${this.request}`; - } +const BUILD_DEPENDENCIES_KEY = Symbol(); +class IdleFileCachePlugin { /** - * @param {NeedBuildContext} context context info - * @param {function(WebpackError=, boolean=): void} callback callback function, returns true, if the module needs a rebuild - * @returns {void} + * @param {TODO} strategy cache strategy + * @param {number} idleTimeout timeout + * @param {number} idleTimeoutForInitialStore initial timeout + * @param {number} idleTimeoutAfterLargeChanges timeout after changes */ - needBuild(context, callback) { - callback(null, !this.buildInfo); + constructor( + strategy, + idleTimeout, + idleTimeoutForInitialStore, + idleTimeoutAfterLargeChanges + ) { + this.strategy = strategy; + this.idleTimeout = idleTimeout; + this.idleTimeoutForInitialStore = idleTimeoutForInitialStore; + this.idleTimeoutAfterLargeChanges = idleTimeoutAfterLargeChanges; } /** - * @param {WebpackOptions} options webpack options - * @param {Compilation} compilation the compilation - * @param {ResolverWithOptions} resolver the resolver - * @param {InputFileSystem} fs the file system - * @param {function(WebpackError=): void} callback callback function + * Apply the plugin + * @param {Compiler} compiler the compiler instance * @returns {void} */ - build(options, compilation, resolver, fs, callback) { - this.buildMeta = {}; - this.buildInfo = { - strict: true - }; - - this.clearDependenciesAndBlocks(); - if (this.externalRequests.length === 1) { - this.addDependency( - new RemoteToExternalDependency(this.externalRequests[0]) - ); - } else { - this.addDependency(new FallbackDependency(this.externalRequests)); - } - - callback(); - } - - /** - * @param {string=} type the source type for which the size should be estimated - * @returns {number} the estimated size of the module (must be non-zero) - */ - size(type) { - return 6; - } + apply(compiler) { + let strategy = this.strategy; + const idleTimeout = this.idleTimeout; + const idleTimeoutForInitialStore = Math.min( + idleTimeout, + this.idleTimeoutForInitialStore + ); + const idleTimeoutAfterLargeChanges = this.idleTimeoutAfterLargeChanges; + const resolvedPromise = Promise.resolve(); - /** - * @returns {Set} types available (do not mutate) - */ - getSourceTypes() { - return TYPES; - } + let timeSpendInBuild = 0; + let timeSpendInStore = 0; + let avgTimeSpendInStore = 0; - /** - * @returns {string | null} absolute path which should be used for condition matching (usually the resource path) - */ - nameForCondition() { - return this.request; - } + /** @type {Map Promise>} */ + const pendingIdleTasks = new Map(); - /** - * @param {CodeGenerationContext} context context for code generation - * @returns {CodeGenerationResult} result - */ - codeGeneration({ runtimeTemplate, moduleGraph, chunkGraph }) { - const module = moduleGraph.getModule(this.dependencies[0]); - const id = module && chunkGraph.getModuleId(module); - const sources = new Map(); - sources.set("remote", new RawSource("")); - const data = new Map(); - data.set("share-init", [ - { - shareScope: this.shareScope, - initStage: 20, - init: id === undefined ? "" : `initExternal(${JSON.stringify(id)});` + compiler.cache.hooks.store.tap( + { name: "IdleFileCachePlugin", stage: Cache.STAGE_DISK }, + (identifier, etag, data) => { + pendingIdleTasks.set(identifier, () => + strategy.store(identifier, etag, data) + ); } - ]); - return { sources, data, runtimeRequirements: RUNTIME_REQUIREMENTS }; - } - - serialize(context) { - const { write } = context; - write(this.request); - write(this.externalRequests); - write(this.internalRequest); - write(this.shareScope); - super.serialize(context); - } - - static deserialize(context) { - const { read } = context; - const obj = new RemoteModule(read(), read(), read(), read()); - obj.deserialize(context); - return obj; - } -} - -makeSerializable(RemoteModule, "webpack/lib/container/RemoteModule"); - -module.exports = RemoteModule; - - -/***/ }), - -/***/ 4603: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ - - + ); -const RuntimeGlobals = __webpack_require__(49404); -const RuntimeModule = __webpack_require__(61439); -const Template = __webpack_require__(92066); + compiler.cache.hooks.get.tapPromise( + { name: "IdleFileCachePlugin", stage: Cache.STAGE_DISK }, + (identifier, etag, gotHandlers) => { + const restore = () => + strategy.restore(identifier, etag).then(cacheEntry => { + if (cacheEntry === undefined) { + gotHandlers.push((result, callback) => { + if (result !== undefined) { + pendingIdleTasks.set(identifier, () => + strategy.store(identifier, etag, result) + ); + } + callback(); + }); + } else { + return cacheEntry; + } + }); + const pendingTask = pendingIdleTasks.get(identifier); + if (pendingTask !== undefined) { + pendingIdleTasks.delete(identifier); + return pendingTask().then(restore); + } + return restore(); + } + ); -/** @typedef {import("./RemoteModule")} RemoteModule */ + compiler.cache.hooks.storeBuildDependencies.tap( + { name: "IdleFileCachePlugin", stage: Cache.STAGE_DISK }, + dependencies => { + pendingIdleTasks.set(BUILD_DEPENDENCIES_KEY, () => + strategy.storeBuildDependencies(dependencies) + ); + } + ); -class RemoteRuntimeModule extends RuntimeModule { - constructor() { - super("remotes loading"); - } + compiler.cache.hooks.shutdown.tapPromise( + { name: "IdleFileCachePlugin", stage: Cache.STAGE_DISK }, + () => { + if (idleTimer) { + clearTimeout(idleTimer); + idleTimer = undefined; + } + isIdle = false; + const reportProgress = ProgressPlugin.getReporter(compiler); + const jobs = Array.from(pendingIdleTasks.values()); + if (reportProgress) reportProgress(0, "process pending cache items"); + const promises = jobs.map(fn => fn()); + pendingIdleTasks.clear(); + promises.push(currentIdlePromise); + const promise = Promise.all(promises); + currentIdlePromise = promise.then(() => strategy.afterAllStored()); + if (reportProgress) { + currentIdlePromise = currentIdlePromise.then(() => { + reportProgress(1, `stored`); + }); + } + return currentIdlePromise.then(() => { + // Reset strategy + if (strategy.clear) strategy.clear(); + }); + } + ); - /** - * @returns {string} runtime code - */ - generate() { - const { compilation, chunkGraph } = this; - const { runtimeTemplate, moduleGraph } = compilation; - const chunkToRemotesMapping = {}; - const idToExternalAndNameMapping = {}; - for (const chunk of this.chunk.getAllAsyncChunks()) { - const modules = chunkGraph.getChunkModulesIterableBySourceType( - chunk, - "remote" - ); - if (!modules) continue; - const remotes = (chunkToRemotesMapping[chunk.id] = []); - for (const m of modules) { - const module = /** @type {RemoteModule} */ (m); - const name = module.internalRequest; - const id = chunkGraph.getModuleId(module); - const shareScope = module.shareScope; - const dep = module.dependencies[0]; - const externalModule = moduleGraph.getModule(dep); - const externalModuleId = - externalModule && chunkGraph.getModuleId(externalModule); - remotes.push(id); - idToExternalAndNameMapping[id] = [shareScope, name, externalModuleId]; + /** @type {Promise} */ + let currentIdlePromise = resolvedPromise; + let isIdle = false; + let isInitialStore = true; + const processIdleTasks = () => { + if (isIdle) { + const startTime = Date.now(); + if (pendingIdleTasks.size > 0) { + const promises = [currentIdlePromise]; + const maxTime = startTime + 100; + let maxCount = 100; + for (const [filename, factory] of pendingIdleTasks) { + pendingIdleTasks.delete(filename); + promises.push(factory()); + if (maxCount-- <= 0 || Date.now() > maxTime) break; + } + currentIdlePromise = Promise.all(promises); + currentIdlePromise.then(() => { + timeSpendInStore += Date.now() - startTime; + // Allow to exit the process between + idleTimer = setTimeout(processIdleTasks, 0); + idleTimer.unref(); + }); + return; + } + currentIdlePromise = currentIdlePromise + .then(async () => { + await strategy.afterAllStored(); + timeSpendInStore += Date.now() - startTime; + avgTimeSpendInStore = + Math.max(avgTimeSpendInStore, timeSpendInStore) * 0.9 + + timeSpendInStore * 0.1; + timeSpendInStore = 0; + timeSpendInBuild = 0; + }) + .catch(err => { + const logger = compiler.getInfrastructureLogger( + "IdleFileCachePlugin" + ); + logger.warn(`Background tasks during idle failed: ${err.message}`); + logger.debug(err.stack); + }); + isInitialStore = false; + } + }; + let idleTimer = undefined; + compiler.cache.hooks.beginIdle.tap( + { name: "IdleFileCachePlugin", stage: Cache.STAGE_DISK }, + () => { + const isLargeChange = timeSpendInBuild > avgTimeSpendInStore * 2; + if (isInitialStore && idleTimeoutForInitialStore < idleTimeout) { + compiler + .getInfrastructureLogger("IdleFileCachePlugin") + .log( + `Initial cache was generated and cache will be persisted in ${ + idleTimeoutForInitialStore / 1000 + }s.` + ); + } else if ( + isLargeChange && + idleTimeoutAfterLargeChanges < idleTimeout + ) { + compiler + .getInfrastructureLogger("IdleFileCachePlugin") + .log( + `Spend ${Math.round(timeSpendInBuild) / 1000}s in build and ${ + Math.round(avgTimeSpendInStore) / 1000 + }s in average in cache store. This is considered as large change and cache will be persisted in ${ + idleTimeoutAfterLargeChanges / 1000 + }s.` + ); + } + idleTimer = setTimeout(() => { + idleTimer = undefined; + isIdle = true; + resolvedPromise.then(processIdleTasks); + }, Math.min(isInitialStore ? idleTimeoutForInitialStore : Infinity, isLargeChange ? idleTimeoutAfterLargeChanges : Infinity, idleTimeout)); + idleTimer.unref(); } - } - return Template.asString([ - `var chunkMapping = ${JSON.stringify( - chunkToRemotesMapping, - null, - "\t" - )};`, - `var idToExternalAndNameMapping = ${JSON.stringify( - idToExternalAndNameMapping, - null, - "\t" - )};`, - `${ - RuntimeGlobals.ensureChunkHandlers - }.remotes = ${runtimeTemplate.basicFunction("chunkId, promises", [ - `if(${RuntimeGlobals.hasOwnProperty}(chunkMapping, chunkId)) {`, - Template.indent([ - `chunkMapping[chunkId].forEach(${runtimeTemplate.basicFunction("id", [ - `var getScope = ${RuntimeGlobals.currentRemoteGetScope};`, - "if(!getScope) getScope = [];", - "var data = idToExternalAndNameMapping[id];", - "if(getScope.indexOf(data) >= 0) return;", - "getScope.push(data);", - `if(data.p) return promises.push(data.p);`, - `var onError = ${runtimeTemplate.basicFunction("error", [ - 'if(!error) error = new Error("Container missing");', - 'if(typeof error.message === "string")', - Template.indent( - `error.message += '\\nwhile loading "' + data[1] + '" from ' + data[2];` - ), - `__webpack_modules__[id] = ${runtimeTemplate.basicFunction("", [ - "throw error;" - ])}`, - "data.p = 0;" - ])};`, - `var handleFunction = ${runtimeTemplate.basicFunction( - "fn, arg1, arg2, d, next, first", - [ - "try {", - Template.indent([ - "var promise = fn(arg1, arg2);", - "if(promise && promise.then) {", - Template.indent([ - `var p = promise.then(${runtimeTemplate.returningFunction( - "next(result, d)", - "result" - )}, onError);`, - `if(first) promises.push(data.p = p); else return p;` - ]), - "} else {", - Template.indent(["return next(promise, d, first);"]), - "}" - ]), - "} catch(error) {", - Template.indent(["onError(error);"]), - "}" - ] - )}`, - `var onExternal = ${runtimeTemplate.returningFunction( - `external ? handleFunction(${RuntimeGlobals.initializeSharing}, data[0], 0, external, onInitialized, first) : onError()`, - "external, _, first" - )};`, - `var onInitialized = ${runtimeTemplate.returningFunction( - `handleFunction(external.get, data[1], getScope, 0, onFactory, first)`, - "_, external, first" - )};`, - `var onFactory = ${runtimeTemplate.basicFunction("factory", [ - "data.p = 1;", - `__webpack_modules__[id] = ${runtimeTemplate.basicFunction( - "module", - ["module.exports = factory();"] - )}` - ])};`, - "handleFunction(__webpack_require__, data[2], 0, 0, onExternal, 1);" - ])});` - ]), - "}" - ])}` - ]); + ); + compiler.cache.hooks.endIdle.tap( + { name: "IdleFileCachePlugin", stage: Cache.STAGE_DISK }, + () => { + if (idleTimer) { + clearTimeout(idleTimer); + idleTimer = undefined; + } + isIdle = false; + } + ); + compiler.hooks.done.tap("IdleFileCachePlugin", stats => { + // 10% build overhead is ignored, as it's not cacheable + timeSpendInBuild *= 0.9; + timeSpendInBuild += stats.endTime - stats.startTime; + }); } } -module.exports = RemoteRuntimeModule; +module.exports = IdleFileCachePlugin; /***/ }), -/***/ 44637: +/***/ 4045: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; @@ -72526,35 +67797,62 @@ module.exports = RemoteRuntimeModule; -const ModuleDependency = __webpack_require__(80944); -const makeSerializable = __webpack_require__(26522); - -class RemoteToExternalDependency extends ModuleDependency { - constructor(request) { - super(request); - } +const Cache = __webpack_require__(99453); - get type() { - return "remote to external"; - } +/** @typedef {import("webpack-sources").Source} Source */ +/** @typedef {import("../Cache").Etag} Etag */ +/** @typedef {import("../Compiler")} Compiler */ +/** @typedef {import("../Module")} Module */ - get category() { - return "esm"; +class MemoryCachePlugin { + /** + * Apply the plugin + * @param {Compiler} compiler the compiler instance + * @returns {void} + */ + apply(compiler) { + /** @type {Map} */ + const cache = new Map(); + compiler.cache.hooks.store.tap( + { name: "MemoryCachePlugin", stage: Cache.STAGE_MEMORY }, + (identifier, etag, data) => { + cache.set(identifier, { etag, data }); + } + ); + compiler.cache.hooks.get.tap( + { name: "MemoryCachePlugin", stage: Cache.STAGE_MEMORY }, + (identifier, etag, gotHandlers) => { + const cacheEntry = cache.get(identifier); + if (cacheEntry === null) { + return null; + } else if (cacheEntry !== undefined) { + return cacheEntry.etag === etag ? cacheEntry.data : null; + } + gotHandlers.push((result, callback) => { + if (result === undefined) { + cache.set(identifier, null); + } else { + cache.set(identifier, { etag, data: result }); + } + return callback(); + }); + } + ); + compiler.cache.hooks.shutdown.tap( + { name: "MemoryCachePlugin", stage: Cache.STAGE_MEMORY }, + () => { + cache.clear(); + } + ); } } - -makeSerializable( - RemoteToExternalDependency, - "webpack/lib/container/RemoteToExternalDependency" -); - -module.exports = RemoteToExternalDependency; +module.exports = MemoryCachePlugin; /***/ }), -/***/ 56084: -/***/ (function(__unused_webpack_module, exports) { +/***/ 34854: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; /* @@ -72564,1147 +67862,1567 @@ module.exports = RemoteToExternalDependency; -/** @template T @typedef {(string | Record)[] | Record} ContainerOptionsFormat */ +const Cache = __webpack_require__(99453); -/** - * @template T - * @template N - * @param {ContainerOptionsFormat} options options passed by the user - * @param {function(string | string[], string) : N} normalizeSimple normalize a simple item - * @param {function(T, string) : N} normalizeOptions normalize a complex item - * @param {function(string, N): void} fn processing function - * @returns {void} - */ -const process = (options, normalizeSimple, normalizeOptions, fn) => { - const array = items => { - for (const item of items) { - if (typeof item === "string") { - fn(item, normalizeSimple(item, item)); - } else if (item && typeof item === "object") { - object(item); - } else { - throw new Error("Unexpected options format"); +/** @typedef {import("webpack-sources").Source} Source */ +/** @typedef {import("../Cache").Etag} Etag */ +/** @typedef {import("../Compiler")} Compiler */ +/** @typedef {import("../Module")} Module */ + +class MemoryWithGcCachePlugin { + constructor({ maxGenerations }) { + this._maxGenerations = maxGenerations; + } + /** + * Apply the plugin + * @param {Compiler} compiler the compiler instance + * @returns {void} + */ + apply(compiler) { + const maxGenerations = this._maxGenerations; + /** @type {Map} */ + const cache = new Map(); + /** @type {Map} */ + const oldCache = new Map(); + let generation = 0; + let cachePosition = 0; + const logger = compiler.getInfrastructureLogger("MemoryWithGcCachePlugin"); + compiler.hooks.afterDone.tap("MemoryWithGcCachePlugin", () => { + generation++; + let clearedEntries = 0; + let lastClearedIdentifier; + for (const [identifier, entry] of oldCache) { + if (entry.until > generation) break; + + oldCache.delete(identifier); + if (cache.get(identifier) === undefined) { + cache.delete(identifier); + clearedEntries++; + lastClearedIdentifier = identifier; + } } - } - }; - const object = obj => { - for (const [key, value] of Object.entries(obj)) { - if (typeof value === "string" || Array.isArray(value)) { - fn(key, normalizeSimple(value, key)); - } else { - fn(key, normalizeOptions(value, key)); + if (clearedEntries > 0 || oldCache.size > 0) { + logger.log( + `${cache.size - oldCache.size} active entries, ${ + oldCache.size + } recently unused cached entries${ + clearedEntries > 0 + ? `, ${clearedEntries} old unused cache entries removed e. g. ${lastClearedIdentifier}` + : "" + }` + ); } - } - }; - if (!options) { - return; - } else if (Array.isArray(options)) { - array(options); - } else if (typeof options === "object") { - object(options); - } else { - throw new Error("Unexpected options format"); + let i = (cache.size / maxGenerations) | 0; + let j = cachePosition >= cache.size ? 0 : cachePosition; + cachePosition = j + i; + for (const [identifier, entry] of cache) { + if (j !== 0) { + j--; + continue; + } + if (entry !== undefined) { + // We don't delete the cache entry, but set it to undefined instead + // This reserves the location in the data table and avoids rehashing + // when constantly adding and removing entries. + // It will be deleted when removed from oldCache. + cache.set(identifier, undefined); + oldCache.delete(identifier); + oldCache.set(identifier, { + entry, + until: generation + maxGenerations + }); + if (i-- === 0) break; + } + } + }); + compiler.cache.hooks.store.tap( + { name: "MemoryWithGcCachePlugin", stage: Cache.STAGE_MEMORY }, + (identifier, etag, data) => { + cache.set(identifier, { etag, data }); + } + ); + compiler.cache.hooks.get.tap( + { name: "MemoryWithGcCachePlugin", stage: Cache.STAGE_MEMORY }, + (identifier, etag, gotHandlers) => { + const cacheEntry = cache.get(identifier); + if (cacheEntry === null) { + return null; + } else if (cacheEntry !== undefined) { + return cacheEntry.etag === etag ? cacheEntry.data : null; + } + const oldCacheEntry = oldCache.get(identifier); + if (oldCacheEntry !== undefined) { + const cacheEntry = oldCacheEntry.entry; + if (cacheEntry === null) { + oldCache.delete(identifier); + cache.set(identifier, cacheEntry); + return null; + } else { + if (cacheEntry.etag !== etag) return null; + oldCache.delete(identifier); + cache.set(identifier, cacheEntry); + return cacheEntry.data; + } + } + gotHandlers.push((result, callback) => { + if (result === undefined) { + cache.set(identifier, null); + } else { + cache.set(identifier, { etag, data: result }); + } + return callback(); + }); + } + ); + compiler.cache.hooks.shutdown.tap( + { name: "MemoryWithGcCachePlugin", stage: Cache.STAGE_MEMORY }, + () => { + cache.clear(); + oldCache.clear(); + } + ); } -}; - -/** - * @template T - * @template R - * @param {ContainerOptionsFormat} options options passed by the user - * @param {function(string | string[], string) : R} normalizeSimple normalize a simple item - * @param {function(T, string) : R} normalizeOptions normalize a complex item - * @returns {[string, R][]} parsed options - */ -const parseOptions = (options, normalizeSimple, normalizeOptions) => { - /** @type {[string, R][]} */ - const items = []; - process(options, normalizeSimple, normalizeOptions, (key, value) => { - items.push([key, value]); - }); - return items; -}; - -/** - * @template T - * @param {string} scope scope name - * @param {ContainerOptionsFormat} options options passed by the user - * @returns {Record} options to spread or pass - */ -const scope = (scope, options) => { - /** @type {Record} */ - const obj = {}; - process( - options, - item => /** @type {string | string[] | T} */ (item), - item => /** @type {string | string[] | T} */ (item), - (key, value) => { - obj[ - key.startsWith("./") ? `${scope}${key.slice(1)}` : `${scope}/${key}` - ] = value; - } - ); - return obj; -}; - -exports.parseOptions = parseOptions; -exports.scope = scope; +} +module.exports = MemoryWithGcCachePlugin; /***/ }), -/***/ 52034: +/***/ 46810: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; /* MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra */ -const { Tracer } = __webpack_require__(92430); -const createSchemaValidation = __webpack_require__(77695); -const { dirname, mkdirpSync } = __webpack_require__(93204); +const FileSystemInfo = __webpack_require__(13679); +const ProgressPlugin = __webpack_require__(41306); +const { formatSize } = __webpack_require__(15979); +const SerializerMiddleware = __webpack_require__(37063); +const LazySet = __webpack_require__(59534); +const makeSerializable = __webpack_require__(26522); +const memoize = __webpack_require__(84297); +const { + createFileSerializer, + NOT_SERIALIZABLE +} = __webpack_require__(99551); -/** @typedef {import("../../declarations/plugins/debug/ProfilingPlugin").ProfilingPluginOptions} ProfilingPluginOptions */ +/** @typedef {import("../../declarations/WebpackOptions").SnapshotOptions} SnapshotOptions */ +/** @typedef {import("../Cache").Etag} Etag */ +/** @typedef {import("../Compiler")} Compiler */ +/** @typedef {import("../FileSystemInfo").Snapshot} Snapshot */ +/** @typedef {import("../logging/Logger").Logger} Logger */ /** @typedef {import("../util/fs").IntermediateFileSystem} IntermediateFileSystem */ -const validate = createSchemaValidation( - __webpack_require__(93129), - () => __webpack_require__(26281), - { - name: "Profiling Plugin", - baseDataPath: "options" - } -); -let inspector = undefined; - -try { - // eslint-disable-next-line node/no-unsupported-features/node-builtins - inspector = __webpack_require__(57012); -} catch (e) { - console.log("Unable to CPU profile in < node 8.0"); -} - -class Profiler { - constructor(inspector) { - this.session = undefined; - this.inspector = inspector; - this._startTime = 0; - } - - hasSession() { - return this.session !== undefined; +class PackContainer { + /** + * @param {Object} data stored data + * @param {string} version version identifier + * @param {Snapshot} buildSnapshot snapshot of all build dependencies + * @param {Set} buildDependencies list of all unresolved build dependencies captured + * @param {Map} resolveResults result of the resolved build dependencies + * @param {Snapshot} resolveBuildDependenciesSnapshot snapshot of the dependencies of the build dependencies resolving + */ + constructor( + data, + version, + buildSnapshot, + buildDependencies, + resolveResults, + resolveBuildDependenciesSnapshot + ) { + this.data = data; + this.version = version; + this.buildSnapshot = buildSnapshot; + this.buildDependencies = buildDependencies; + this.resolveResults = resolveResults; + this.resolveBuildDependenciesSnapshot = resolveBuildDependenciesSnapshot; } - startProfiling() { - if (this.inspector === undefined) { - return Promise.resolve(); - } - - try { - this.session = new inspector.Session(); - this.session.connect(); - } catch (_) { - this.session = undefined; - return Promise.resolve(); - } - - const hrtime = process.hrtime(); - this._startTime = hrtime[0] * 1000000 + Math.round(hrtime[1] / 1000); - - return Promise.all([ - this.sendCommand("Profiler.setSamplingInterval", { - interval: 100 - }), - this.sendCommand("Profiler.enable"), - this.sendCommand("Profiler.start") - ]); + serialize({ write, writeLazy }) { + write(this.version); + write(this.buildSnapshot); + write(this.buildDependencies); + write(this.resolveResults); + write(this.resolveBuildDependenciesSnapshot); + writeLazy(this.data); } - sendCommand(method, params) { - if (this.hasSession()) { - return new Promise((res, rej) => { - return this.session.post(method, params, (err, params) => { - if (err !== null) { - rej(err); - } else { - res(params); - } - }); - }); - } else { - return Promise.resolve(); - } + deserialize({ read }) { + this.version = read(); + this.buildSnapshot = read(); + this.buildDependencies = read(); + this.resolveResults = read(); + this.resolveBuildDependenciesSnapshot = read(); + this.data = read(); } +} - destroy() { - if (this.hasSession()) { - this.session.disconnect(); - } +makeSerializable( + PackContainer, + "webpack/lib/cache/PackFileCacheStrategy", + "PackContainer" +); - return Promise.resolve(); - } +const MIN_CONTENT_SIZE = 1024 * 1024; // 1 MB +const CONTENT_COUNT_TO_MERGE = 10; +const MIN_ITEMS_IN_FRESH_PACK = 100; +const MAX_ITEMS_IN_FRESH_PACK = 50000; +const MAX_TIME_IN_FRESH_PACK = 1 * 60 * 1000; // 1 min - stopProfiling() { - return this.sendCommand("Profiler.stop").then(({ profile }) => { - const hrtime = process.hrtime(); - const endTime = hrtime[0] * 1000000 + Math.round(hrtime[1] / 1000); - if (profile.startTime < this._startTime || profile.endTime > endTime) { - // In some cases timestamps mismatch and we need to adjust them - // Both process.hrtime and the inspector timestamps claim to be relative - // to a unknown point in time. But they do not guarantee that this is the - // same point in time. - const duration = profile.endTime - profile.startTime; - const ownDuration = endTime - this._startTime; - const untracked = Math.max(0, ownDuration - duration); - profile.startTime = this._startTime + untracked / 2; - profile.endTime = endTime - untracked / 2; - } - return { profile }; - }); +class PackItemInfo { + /** + * @param {string} identifier identifier of item + * @param {string | null} etag etag of item + * @param {any} value fresh value of item + */ + constructor(identifier, etag, value) { + this.identifier = identifier; + this.etag = etag; + this.location = -1; + this.lastAccess = Date.now(); + this.freshValue = value; } } -/** - * an object that wraps Tracer and Profiler with a counter - * @typedef {Object} Trace - * @property {Tracer} trace instance of Tracer - * @property {number} counter Counter - * @property {Profiler} profiler instance of Profiler - * @property {Function} end the end function - */ +class Pack { + constructor(logger, maxAge) { + /** @type {Map} */ + this.itemInfo = new Map(); + /** @type {string[]} */ + this.requests = []; + this.requestsTimeout = undefined; + /** @type {Map} */ + this.freshContent = new Map(); + /** @type {(undefined | PackContent)[]} */ + this.content = []; + this.invalid = false; + this.logger = logger; + this.maxAge = maxAge; + } -/** - * @param {IntermediateFileSystem} fs filesystem used for output - * @param {string} outputPath The location where to write the log. - * @returns {Trace} The trace object - */ -const createTrace = (fs, outputPath) => { - const trace = new Tracer({ - noStream: true - }); - const profiler = new Profiler(inspector); - if (/\/|\\/.test(outputPath)) { - const dirPath = dirname(fs, outputPath); - mkdirpSync(fs, dirPath); + _addRequest(identifier) { + this.requests.push(identifier); + if (this.requestsTimeout === undefined) { + this.requestsTimeout = setTimeout(() => { + this.requests.push(undefined); + this.requestsTimeout = undefined; + }, MAX_TIME_IN_FRESH_PACK); + if (this.requestsTimeout.unref) this.requestsTimeout.unref(); + } } - const fsStream = fs.createWriteStream(outputPath); - let counter = 0; + stopCapturingRequests() { + if (this.requestsTimeout !== undefined) { + clearTimeout(this.requestsTimeout); + this.requestsTimeout = undefined; + } + } - trace.pipe(fsStream); - // These are critical events that need to be inserted so that tools like - // chrome dev tools can load the profile. - trace.instantEvent({ - name: "TracingStartedInPage", - id: ++counter, - cat: ["disabled-by-default-devtools.timeline"], - args: { - data: { - sessionId: "-1", - page: "0xfff", - frames: [ - { - frame: "0xfff", - url: "webpack", - name: "" - } - ] + /** + * @param {string} identifier unique name for the resource + * @param {string | null} etag etag of the resource + * @returns {any} cached content + */ + get(identifier, etag) { + const info = this.itemInfo.get(identifier); + this._addRequest(identifier); + if (info === undefined) { + return undefined; + } + if (info.etag !== etag) return null; + info.lastAccess = Date.now(); + const loc = info.location; + if (loc === -1) { + return info.freshValue; + } else { + if (!this.content[loc]) { + return undefined; } + return this.content[loc].get(identifier); } - }); + } - trace.instantEvent({ - name: "TracingStartedInBrowser", - id: ++counter, - cat: ["disabled-by-default-devtools.timeline"], - args: { - data: { - sessionId: "-1" + /** + * @param {string} identifier unique name for the resource + * @param {string | null} etag etag of the resource + * @param {any} data cached content + * @returns {void} + */ + set(identifier, etag, data) { + if (!this.invalid) { + this.invalid = true; + this.logger.log(`Pack got invalid because of write to: ${identifier}`); + } + const info = this.itemInfo.get(identifier); + if (info === undefined) { + const newInfo = new PackItemInfo(identifier, etag, data); + this.itemInfo.set(identifier, newInfo); + this._addRequest(identifier); + this.freshContent.set(identifier, newInfo); + } else { + const loc = info.location; + if (loc >= 0) { + this._addRequest(identifier); + this.freshContent.set(identifier, info); + const content = this.content[loc]; + content.delete(identifier); + if (content.items.size === 0) { + this.content[loc] = undefined; + this.logger.debug("Pack %d got empty and is removed", loc); + } } + info.freshValue = data; + info.lastAccess = Date.now(); + info.etag = etag; + info.location = -1; } - }); + } - return { - trace, - counter, - profiler, - end: callback => { - // Wait until the write stream finishes. - fsStream.on("close", () => { - callback(); - }); - // Tear down the readable trace stream. - trace.push(null); + getContentStats() { + let count = 0; + let size = 0; + for (const content of this.content) { + if (content !== undefined) { + count++; + const s = content.getSize(); + if (s > 0) { + size += s; + } + } } - }; -}; - -const pluginName = "ProfilingPlugin"; + return { count, size }; + } -class ProfilingPlugin { /** - * @param {ProfilingPluginOptions=} options options object + * @returns {number} new location of data entries */ - constructor(options = {}) { - validate(options); - this.outputPath = options.outputPath || "events.json"; + _findLocation() { + let i; + for (i = 0; i < this.content.length && this.content[i] !== undefined; i++); + return i; } - apply(compiler) { - const tracer = createTrace( - compiler.intermediateFileSystem, - this.outputPath - ); - tracer.profiler.startProfiling(); - - // Compiler Hooks - Object.keys(compiler.hooks).forEach(hookName => { - const hook = compiler.hooks[hookName]; - if (hook) { - hook.intercept(makeInterceptorFor("Compiler", tracer)(hookName)); + _gcAndUpdateLocation(items, usedItems, newLoc) { + let count = 0; + let lastGC; + const now = Date.now(); + for (const identifier of items) { + const info = this.itemInfo.get(identifier); + if (now - info.lastAccess > this.maxAge) { + this.itemInfo.delete(identifier); + items.delete(identifier); + usedItems.delete(identifier); + count++; + lastGC = identifier; + } else { + info.location = newLoc; } - }); + } + if (count > 0) { + this.logger.log( + "Garbage Collected %d old items at pack %d (%d items remaining) e. g. %s", + count, + newLoc, + items.size, + lastGC + ); + } + } - Object.keys(compiler.resolverFactory.hooks).forEach(hookName => { - const hook = compiler.resolverFactory.hooks[hookName]; - if (hook) { - hook.intercept(makeInterceptorFor("Resolver", tracer)(hookName)); + _persistFreshContent() { + const itemsCount = this.freshContent.size; + if (itemsCount > 0) { + const packCount = Math.ceil(itemsCount / MAX_ITEMS_IN_FRESH_PACK); + const itemsPerPack = Math.ceil(itemsCount / packCount); + const packs = []; + let i = 0; + let ignoreNextTimeTick = false; + const createNextPack = () => { + const loc = this._findLocation(); + this.content[loc] = null; // reserve + const pack = { + /** @type {Set} */ + items: new Set(), + /** @type {Map} */ + map: new Map(), + loc + }; + packs.push(pack); + return pack; + }; + let pack = createNextPack(); + if (this.requestsTimeout !== undefined) + clearTimeout(this.requestsTimeout); + for (const identifier of this.requests) { + if (identifier === undefined) { + if (ignoreNextTimeTick) { + ignoreNextTimeTick = false; + } else if (pack.items.size >= MIN_ITEMS_IN_FRESH_PACK) { + i = 0; + pack = createNextPack(); + } + continue; + } + const info = this.freshContent.get(identifier); + if (info === undefined) continue; + pack.items.add(identifier); + pack.map.set(identifier, info.freshValue); + info.location = pack.loc; + info.freshValue = undefined; + this.freshContent.delete(identifier); + if (++i > itemsPerPack) { + i = 0; + pack = createNextPack(); + ignoreNextTimeTick = true; + } } - }); - - compiler.hooks.compilation.tap( - pluginName, - (compilation, { normalModuleFactory, contextModuleFactory }) => { - interceptAllHooksFor(compilation, tracer, "Compilation"); - interceptAllHooksFor( - normalModuleFactory, - tracer, - "Normal Module Factory" - ); - interceptAllHooksFor( - contextModuleFactory, - tracer, - "Context Module Factory" + this.requests.length = 0; + for (const pack of packs) { + this.content[pack.loc] = new PackContent( + pack.items, + new Set(pack.items), + new PackContentItems(pack.map) ); - interceptAllParserHooks(normalModuleFactory, tracer); - interceptAllJavascriptModulesPluginHooks(compilation, tracer); - } - ); - - // We need to write out the CPU profile when we are all done. - compiler.hooks.done.tapAsync( - { - name: pluginName, - stage: Infinity - }, - (stats, callback) => { - tracer.profiler.stopProfiling().then(parsedResults => { - if (parsedResults === undefined) { - tracer.profiler.destroy(); - tracer.trace.flush(); - tracer.end(callback); - return; - } - - const cpuStartTime = parsedResults.profile.startTime; - const cpuEndTime = parsedResults.profile.endTime; - - tracer.trace.completeEvent({ - name: "TaskQueueManager::ProcessTaskFromWorkQueue", - id: ++tracer.counter, - cat: ["toplevel"], - ts: cpuStartTime, - args: { - src_file: "../../ipc/ipc_moji_bootstrap.cc", - src_func: "Accept" - } - }); - - tracer.trace.completeEvent({ - name: "EvaluateScript", - id: ++tracer.counter, - cat: ["devtools.timeline"], - ts: cpuStartTime, - dur: cpuEndTime - cpuStartTime, - args: { - data: { - url: "webpack", - lineNumber: 1, - columnNumber: 1, - frame: "0xFFF" - } - } - }); - - tracer.trace.instantEvent({ - name: "CpuProfile", - id: ++tracer.counter, - cat: ["disabled-by-default-devtools.timeline"], - ts: cpuEndTime, - args: { - data: { - cpuProfile: parsedResults.profile - } - } - }); - - tracer.profiler.destroy(); - tracer.trace.flush(); - tracer.end(callback); - }); } - ); + this.logger.log( + `${itemsCount} fresh items in cache put into pack ${ + packs.length > 1 + ? packs + .map(pack => `${pack.loc} (${pack.items.size} items)`) + .join(", ") + : packs[0].loc + }` + ); + } } -} -const interceptAllHooksFor = (instance, tracer, logLabel) => { - if (Reflect.has(instance, "hooks")) { - Object.keys(instance.hooks).forEach(hookName => { - const hook = instance.hooks[hookName]; - if (hook && !hook._fakeHook) { - hook.intercept(makeInterceptorFor(logLabel, tracer)(hookName)); + /** + * Merges small content files to a single content file + */ + _optimizeSmallContent() { + // 1. Find all small content files + // Treat unused content files separately to avoid + // a merge-split cycle + /** @type {number[]} */ + const smallUsedContents = []; + /** @type {number} */ + let smallUsedContentSize = 0; + /** @type {number[]} */ + const smallUnusedContents = []; + /** @type {number} */ + let smallUnusedContentSize = 0; + for (let i = 0; i < this.content.length; i++) { + const content = this.content[i]; + if (content === undefined) continue; + if (content.outdated) continue; + const size = content.getSize(); + if (size < 0 || size > MIN_CONTENT_SIZE) continue; + if (content.used.size > 0) { + smallUsedContents.push(i); + smallUsedContentSize += size; + } else { + smallUnusedContents.push(i); + smallUnusedContentSize += size; } - }); - } -}; - -const interceptAllParserHooks = (moduleFactory, tracer) => { - const moduleTypes = [ - "javascript/auto", - "javascript/dynamic", - "javascript/esm", - "json", - "webassembly/async", - "webassembly/sync" - ]; - - moduleTypes.forEach(moduleType => { - moduleFactory.hooks.parser - .for(moduleType) - .tap("ProfilingPlugin", (parser, parserOpts) => { - interceptAllHooksFor(parser, tracer, "Parser"); - }); - }); -}; - -const interceptAllJavascriptModulesPluginHooks = (compilation, tracer) => { - interceptAllHooksFor( - { - hooks: - __webpack_require__(76767).getCompilationHooks( - compilation - ) - }, - tracer, - "JavascriptModulesPlugin" - ); -}; - -const makeInterceptorFor = (instance, tracer) => hookName => ({ - register: ({ name, type, context, fn }) => { - const newFn = makeNewProfiledTapFn(hookName, tracer, { - name, - type, - fn - }); - return { - name, - type, - context, - fn: newFn - }; - } -}); + } -// TODO improve typing -/** @typedef {(...args: TODO[]) => void | Promise} PluginFunction */ + // 2. Check if minimum number is reached + let mergedIndices; + if ( + smallUsedContents.length >= CONTENT_COUNT_TO_MERGE || + smallUsedContentSize > MIN_CONTENT_SIZE + ) { + mergedIndices = smallUsedContents; + } else if ( + smallUnusedContents.length >= CONTENT_COUNT_TO_MERGE || + smallUnusedContentSize > MIN_CONTENT_SIZE + ) { + mergedIndices = smallUnusedContents; + } else return; -/** - * @param {string} hookName Name of the hook to profile. - * @param {Trace} tracer The trace object. - * @param {object} options Options for the profiled fn. - * @param {string} options.name Plugin name - * @param {string} options.type Plugin type (sync | async | promise) - * @param {PluginFunction} options.fn Plugin function - * @returns {PluginFunction} Chainable hooked function. - */ -const makeNewProfiledTapFn = (hookName, tracer, { name, type, fn }) => { - const defaultCategory = ["blink.user_timing"]; + const mergedContent = []; - switch (type) { - case "promise": - return (...args) => { - const id = ++tracer.counter; - tracer.trace.begin({ - name, - id, - cat: defaultCategory - }); - const promise = /** @type {Promise<*>} */ (fn(...args)); - return promise.then(r => { - tracer.trace.end({ - name, - id, - cat: defaultCategory - }); - return r; - }); - }; - case "async": - return (...args) => { - const id = ++tracer.counter; - tracer.trace.begin({ - name, - id, - cat: defaultCategory - }); - const callback = args.pop(); - fn(...args, (...r) => { - tracer.trace.end({ - name, - id, - cat: defaultCategory - }); - callback(...r); - }); - }; - case "sync": - return (...args) => { - const id = ++tracer.counter; - // Do not instrument ourself due to the CPU - // profile needing to be the last event in the trace. - if (name === pluginName) { - return fn(...args); - } + // 3. Remove old content entries + for (const i of mergedIndices) { + mergedContent.push(this.content[i]); + this.content[i] = undefined; + } - tracer.trace.begin({ - name, - id, - cat: defaultCategory - }); - let r; - try { - r = fn(...args); - } catch (error) { - tracer.trace.end({ - name, - id, - cat: defaultCategory - }); - throw error; + // 4. Determine merged items + /** @type {Set} */ + const mergedItems = new Set(); + /** @type {Set} */ + const mergedUsedItems = new Set(); + /** @type {(function(Map): Promise)[]} */ + const addToMergedMap = []; + for (const content of mergedContent) { + for (const identifier of content.items) { + mergedItems.add(identifier); + } + for (const identifier of content.used) { + mergedUsedItems.add(identifier); + } + addToMergedMap.push(async map => { + // unpack existing content + // after that values are accessible in .content + await content.unpack( + "it should be merged with other small pack contents" + ); + for (const [identifier, value] of content.content) { + map.set(identifier, value); } - tracer.trace.end({ - name, - id, - cat: defaultCategory - }); - return r; - }; - default: - break; + }); + } + + // 5. GC and update location of merged items + const newLoc = this._findLocation(); + this._gcAndUpdateLocation(mergedItems, mergedUsedItems, newLoc); + + // 6. If not empty, store content somewhere + if (mergedItems.size > 0) { + this.content[newLoc] = new PackContent( + mergedItems, + mergedUsedItems, + memoize(async () => { + /** @type {Map} */ + const map = new Map(); + await Promise.all(addToMergedMap.map(fn => fn(map))); + return new PackContentItems(map); + }) + ); + this.logger.log( + "Merged %d small files with %d cache items into pack %d", + mergedContent.length, + mergedItems.size, + newLoc + ); + } } -}; -module.exports = ProfilingPlugin; -module.exports.Profiler = Profiler; + /** + * Split large content files with used and unused items + * into two parts to separate used from unused items + */ + _optimizeUnusedContent() { + // 1. Find a large content file with used and unused items + for (let i = 0; i < this.content.length; i++) { + const content = this.content[i]; + if (content === undefined) continue; + const size = content.getSize(); + if (size < MIN_CONTENT_SIZE) continue; + const used = content.used.size; + const total = content.items.size; + if (used > 0 && used < total) { + // 2. Remove this content + this.content[i] = undefined; + // 3. Determine items for the used content file + const usedItems = new Set(content.used); + const newLoc = this._findLocation(); + this._gcAndUpdateLocation(usedItems, usedItems, newLoc); -/***/ }), + // 4. Create content file for used items + if (usedItems.size > 0) { + this.content[newLoc] = new PackContent( + usedItems, + new Set(usedItems), + async () => { + await content.unpack( + "it should be splitted into used and unused items" + ); + const map = new Map(); + for (const identifier of usedItems) { + map.set(identifier, content.content.get(identifier)); + } + return new PackContentItems(map); + } + ); + } -/***/ 76309: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + // 5. Determine items for the unused content file + const unusedItems = new Set(content.items); + const usedOfUnusedItems = new Set(); + for (const identifier of usedItems) { + unusedItems.delete(identifier); + } + const newUnusedLoc = this._findLocation(); + this._gcAndUpdateLocation(unusedItems, usedOfUnusedItems, newUnusedLoc); -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ + // 6. Create content file for unused items + if (unusedItems.size > 0) { + this.content[newUnusedLoc] = new PackContent( + unusedItems, + usedOfUnusedItems, + async () => { + await content.unpack( + "it should be splitted into used and unused items" + ); + const map = new Map(); + for (const identifier of unusedItems) { + map.set(identifier, content.content.get(identifier)); + } + return new PackContentItems(map); + } + ); + } + this.logger.log( + "Split pack %d into pack %d with %d used items and pack %d with %d unused items", + i, + newLoc, + usedItems.size, + newUnusedLoc, + unusedItems.size + ); + // optimizing only one of them is good enough and + // reduces the amount of serialization needed + return; + } + } + } -const RuntimeGlobals = __webpack_require__(49404); -const makeSerializable = __webpack_require__(26522); -const NullDependency = __webpack_require__(65845); + /** + * Find the content with the oldest item and run GC on that. + * Only runs for one content to avoid large invalidation. + */ + _gcOldestContent() { + /** @type {PackItemInfo} */ + let oldest = undefined; + for (const info of this.itemInfo.values()) { + if (oldest === undefined || info.lastAccess < oldest.lastAccess) { + oldest = info; + } + } + if (Date.now() - oldest.lastAccess > this.maxAge) { + const loc = oldest.location; + if (loc < 0) return; + const content = this.content[loc]; + const items = new Set(content.items); + const usedItems = new Set(content.used); + this._gcAndUpdateLocation(items, usedItems, loc); -/** @typedef {import("webpack-sources").ReplaceSource} ReplaceSource */ -/** @typedef {import("../Dependency")} Dependency */ -/** @typedef {import("../DependencyTemplate").DependencyTemplateContext} DependencyTemplateContext */ + this.content[loc] = + items.size > 0 + ? new PackContent(items, usedItems, async () => { + await content.unpack( + "it contains old items that should be garbage collected" + ); + const map = new Map(); + for (const identifier of items) { + map.set(identifier, content.content.get(identifier)); + } + return new PackContentItems(map); + }) + : undefined; + } + } -/** @type {Record} */ -const DEFINITIONS = { - f: { - definition: "var __WEBPACK_AMD_DEFINE_RESULT__;", - content: `!(__WEBPACK_AMD_DEFINE_RESULT__ = (#).call(exports, __webpack_require__, exports, module), - __WEBPACK_AMD_DEFINE_RESULT__ !== undefined && (module.exports = __WEBPACK_AMD_DEFINE_RESULT__))`, - requests: [ - RuntimeGlobals.require, - RuntimeGlobals.exports, - RuntimeGlobals.module - ] - }, - o: { - definition: "", - content: "!(module.exports = #)", - requests: [RuntimeGlobals.module] - }, - of: { - definition: - "var __WEBPACK_AMD_DEFINE_FACTORY__, __WEBPACK_AMD_DEFINE_RESULT__;", - content: `!(__WEBPACK_AMD_DEFINE_FACTORY__ = (#), - __WEBPACK_AMD_DEFINE_RESULT__ = (typeof __WEBPACK_AMD_DEFINE_FACTORY__ === 'function' ? - (__WEBPACK_AMD_DEFINE_FACTORY__.call(exports, __webpack_require__, exports, module)) : - __WEBPACK_AMD_DEFINE_FACTORY__), - __WEBPACK_AMD_DEFINE_RESULT__ !== undefined && (module.exports = __WEBPACK_AMD_DEFINE_RESULT__))`, - requests: [ - RuntimeGlobals.require, - RuntimeGlobals.exports, - RuntimeGlobals.module - ] - }, - af: { - definition: - "var __WEBPACK_AMD_DEFINE_ARRAY__, __WEBPACK_AMD_DEFINE_RESULT__;", - content: `!(__WEBPACK_AMD_DEFINE_ARRAY__ = #, __WEBPACK_AMD_DEFINE_RESULT__ = (#).apply(exports, __WEBPACK_AMD_DEFINE_ARRAY__), - __WEBPACK_AMD_DEFINE_RESULT__ !== undefined && (module.exports = __WEBPACK_AMD_DEFINE_RESULT__))`, - requests: [RuntimeGlobals.exports, RuntimeGlobals.module] - }, - ao: { - definition: "", - content: "!(#, module.exports = #)", - requests: [RuntimeGlobals.module] - }, - aof: { - definition: - "var __WEBPACK_AMD_DEFINE_FACTORY__, __WEBPACK_AMD_DEFINE_ARRAY__, __WEBPACK_AMD_DEFINE_RESULT__;", - content: `!(__WEBPACK_AMD_DEFINE_ARRAY__ = #, __WEBPACK_AMD_DEFINE_FACTORY__ = (#), - __WEBPACK_AMD_DEFINE_RESULT__ = (typeof __WEBPACK_AMD_DEFINE_FACTORY__ === 'function' ? - (__WEBPACK_AMD_DEFINE_FACTORY__.apply(exports, __WEBPACK_AMD_DEFINE_ARRAY__)) : __WEBPACK_AMD_DEFINE_FACTORY__), - __WEBPACK_AMD_DEFINE_RESULT__ !== undefined && (module.exports = __WEBPACK_AMD_DEFINE_RESULT__))`, - requests: [RuntimeGlobals.exports, RuntimeGlobals.module] - }, - lf: { - definition: "var XXX, XXXmodule;", - content: - "!(XXXmodule = { id: YYY, exports: {}, loaded: false }, XXX = (#).call(XXXmodule.exports, __webpack_require__, XXXmodule.exports, XXXmodule), XXXmodule.loaded = true, XXX === undefined && (XXX = XXXmodule.exports))", - requests: [RuntimeGlobals.require, RuntimeGlobals.module] - }, - lo: { - definition: "var XXX;", - content: "!(XXX = #)", - requests: [] - }, - lof: { - definition: "var XXX, XXXfactory, XXXmodule;", - content: - "!(XXXfactory = (#), (typeof XXXfactory === 'function' ? ((XXXmodule = { id: YYY, exports: {}, loaded: false }), (XXX = XXXfactory.call(XXXmodule.exports, __webpack_require__, XXXmodule.exports, XXXmodule)), (XXXmodule.loaded = true), XXX === undefined && (XXX = XXXmodule.exports)) : XXX = XXXfactory))", - requests: [RuntimeGlobals.require, RuntimeGlobals.module] - }, - laf: { - definition: "var __WEBPACK_AMD_DEFINE_ARRAY__, XXX, XXXexports;", - content: - "!(__WEBPACK_AMD_DEFINE_ARRAY__ = #, XXX = (#).apply(XXXexports = {}, __WEBPACK_AMD_DEFINE_ARRAY__), XXX === undefined && (XXX = XXXexports))", - requests: [] - }, - lao: { - definition: "var XXX;", - content: "!(#, XXX = #)", - requests: [] - }, - laof: { - definition: "var XXXarray, XXXfactory, XXXexports, XXX;", - content: `!(XXXarray = #, XXXfactory = (#), - (typeof XXXfactory === 'function' ? - ((XXX = XXXfactory.apply(XXXexports = {}, XXXarray)), XXX === undefined && (XXX = XXXexports)) : - (XXX = XXXfactory) - ))`, - requests: [] + serialize({ write, writeSeparate }) { + this._persistFreshContent(); + this._optimizeSmallContent(); + this._optimizeUnusedContent(); + this._gcOldestContent(); + for (const identifier of this.itemInfo.keys()) { + write(identifier); + } + write(null); // null as marker of the end of keys + for (const info of this.itemInfo.values()) { + write(info.etag); + } + for (const info of this.itemInfo.values()) { + write(info.lastAccess); + } + for (let i = 0; i < this.content.length; i++) { + const content = this.content[i]; + if (content !== undefined) { + write(content.items); + content.writeLazy(lazy => writeSeparate(lazy, { name: `${i}` })); + } else { + write(undefined); // undefined marks an empty content slot + } + } + write(null); // null as marker of the end of items } -}; -class AMDDefineDependency extends NullDependency { - constructor(range, arrayRange, functionRange, objectRange, namedModule) { - super(); - this.range = range; - this.arrayRange = arrayRange; - this.functionRange = functionRange; - this.objectRange = objectRange; - this.namedModule = namedModule; - this.localModule = null; + deserialize({ read, logger }) { + this.logger = logger; + { + const items = []; + let item = read(); + while (item !== null) { + items.push(item); + item = read(); + } + this.itemInfo.clear(); + const infoItems = items.map(identifier => { + const info = new PackItemInfo(identifier, undefined, undefined); + this.itemInfo.set(identifier, info); + return info; + }); + for (const info of infoItems) { + info.etag = read(); + } + for (const info of infoItems) { + info.lastAccess = read(); + } + } + this.content.length = 0; + let items = read(); + while (items !== null) { + if (items === undefined) { + this.content.push(items); + } else { + const idx = this.content.length; + const lazy = read(); + this.content.push( + new PackContent( + items, + new Set(), + lazy, + logger, + `${this.content.length}` + ) + ); + for (const identifier of items) { + this.itemInfo.get(identifier).location = idx; + } + } + items = read(); + } } +} - get type() { - return "amd define"; +makeSerializable(Pack, "webpack/lib/cache/PackFileCacheStrategy", "Pack"); + +class PackContentItems { + /** + * @param {Map} map items + */ + constructor(map) { + this.map = map; } - serialize(context) { - const { write } = context; - write(this.range); - write(this.arrayRange); - write(this.functionRange); - write(this.objectRange); - write(this.namedModule); - write(this.localModule); - super.serialize(context); + serialize({ write, snapshot, rollback, logger, profile }) { + if (profile) { + write(false); + for (const [key, value] of this.map) { + const s = snapshot(); + try { + write(key); + const start = process.hrtime(); + write(value); + const durationHr = process.hrtime(start); + const duration = durationHr[0] * 1000 + durationHr[1] / 1e6; + if (duration > 1) { + if (duration > 500) + logger.error(`Serialization of '${key}': ${duration} ms`); + else if (duration > 50) + logger.warn(`Serialization of '${key}': ${duration} ms`); + else if (duration > 10) + logger.info(`Serialization of '${key}': ${duration} ms`); + else if (duration > 5) + logger.log(`Serialization of '${key}': ${duration} ms`); + else logger.debug(`Serialization of '${key}': ${duration} ms`); + } + } catch (e) { + rollback(s); + if (e === NOT_SERIALIZABLE) continue; + logger.warn( + `Skipped not serializable cache item '${key}': ${e.message}` + ); + logger.debug(e.stack); + } + } + write(null); + return; + } + // Try to serialize all at once + const s = snapshot(); + try { + write(true); + write(this.map); + } catch (e) { + rollback(s); + + // Try to serialize each item on it's own + write(false); + for (const [key, value] of this.map) { + const s = snapshot(); + try { + write(key); + write(value); + } catch (e) { + rollback(s); + if (e === NOT_SERIALIZABLE) continue; + logger.warn( + `Skipped not serializable cache item '${key}': ${e.message}` + ); + logger.debug(e.stack); + } + } + write(null); + } } - deserialize(context) { - const { read } = context; - this.range = read(); - this.arrayRange = read(); - this.functionRange = read(); - this.objectRange = read(); - this.namedModule = read(); - this.localModule = read(); - super.deserialize(context); + deserialize({ read, logger, profile }) { + if (read()) { + this.map = read(); + } else if (profile) { + const map = new Map(); + let key = read(); + while (key !== null) { + const start = process.hrtime(); + const value = read(); + const durationHr = process.hrtime(start); + const duration = durationHr[0] * 1000 + durationHr[1] / 1e6; + if (duration > 1) { + if (duration > 100) + logger.error(`Deserialization of '${key}': ${duration} ms`); + else if (duration > 20) + logger.warn(`Deserialization of '${key}': ${duration} ms`); + else if (duration > 5) + logger.info(`Deserialization of '${key}': ${duration} ms`); + else if (duration > 2) + logger.log(`Deserialization of '${key}': ${duration} ms`); + else logger.debug(`Deserialization of '${key}': ${duration} ms`); + } + map.set(key, value); + key = read(); + } + this.map = map; + } else { + const map = new Map(); + let key = read(); + while (key !== null) { + map.set(key, read()); + key = read(); + } + this.map = map; + } } } makeSerializable( - AMDDefineDependency, - "webpack/lib/dependencies/AMDDefineDependency" + PackContentItems, + "webpack/lib/cache/PackFileCacheStrategy", + "PackContentItems" ); -AMDDefineDependency.Template = class AMDDefineDependencyTemplate extends ( - NullDependency.Template -) { +class PackContent { + /* + This class can be in these states: + | this.lazy | this.content | this.outdated | state + A1 | undefined | Map | false | fresh content + A2 | undefined | Map | true | (will not happen) + B1 | lazy () => {} | undefined | false | not deserialized + B2 | lazy () => {} | undefined | true | not deserialized, but some items has been removed + C1 | lazy* () => {} | Map | false | deserialized + C2 | lazy* () => {} | Map | true | deserialized, and some items has been removed + + this.used is a subset of this.items. + this.items is a subset of this.content.keys() resp. this.lazy().map.keys() + When this.outdated === false, this.items === this.content.keys() resp. this.lazy().map.keys() + When this.outdated === true, this.items should be used to recreated this.lazy/this.content. + When this.lazy and this.content is set, they contain the same data. + this.get must only be called with a valid item from this.items. + In state C this.lazy is unMemoized + */ + /** - * @param {Dependency} dependency the dependency for which the template should be applied - * @param {ReplaceSource} source the current replace source which can be modified - * @param {DependencyTemplateContext} templateContext the context object - * @returns {void} + * @param {Set} items keys + * @param {Set} usedItems used keys + * @param {PackContentItems | function(): Promise} dataOrFn sync or async content + * @param {Logger=} logger logger for logging + * @param {string=} lazyName name of dataOrFn for logging */ - apply(dependency, source, { runtimeRequirements }) { - const dep = /** @type {AMDDefineDependency} */ (dependency); - const branch = this.branch(dep); - const { definition, content, requests } = DEFINITIONS[branch]; - for (const req of requests) { - runtimeRequirements.add(req); - } - this.replace(dep, source, definition, content); - } - - localModuleVar(dependency) { - return ( - dependency.localModule && - dependency.localModule.used && - dependency.localModule.variableName() - ); + constructor(items, usedItems, dataOrFn, logger, lazyName) { + this.items = items; + /** @type {function(): Promise | PackContentItems} */ + this.lazy = typeof dataOrFn === "function" ? dataOrFn : undefined; + /** @type {Map} */ + this.content = typeof dataOrFn === "function" ? undefined : dataOrFn.map; + this.outdated = false; + this.used = usedItems; + this.logger = logger; + this.lazyName = lazyName; } - branch(dependency) { - const localModuleVar = this.localModuleVar(dependency) ? "l" : ""; - const arrayRange = dependency.arrayRange ? "a" : ""; - const objectRange = dependency.objectRange ? "o" : ""; - const functionRange = dependency.functionRange ? "f" : ""; - return localModuleVar + arrayRange + objectRange + functionRange; - } + get(identifier) { + this.used.add(identifier); + if (this.content) { + return this.content.get(identifier); + } - replace(dependency, source, definition, text) { - const localModuleVar = this.localModuleVar(dependency); - if (localModuleVar) { - text = text.replace(/XXX/g, localModuleVar.replace(/\$/g, "$$$$")); - definition = definition.replace( - /XXX/g, - localModuleVar.replace(/\$/g, "$$$$") + // We are in state B + const { lazyName } = this; + let timeMessage; + if (lazyName) { + // only log once + this.lazyName = undefined; + timeMessage = `restore cache content ${lazyName} (${formatSize( + this.getSize() + )})`; + this.logger.log( + `starting to restore cache content ${lazyName} (${formatSize( + this.getSize() + )}) because of request to: ${identifier}` ); + this.logger.time(timeMessage); } - - if (dependency.namedModule) { - text = text.replace(/YYY/g, JSON.stringify(dependency.namedModule)); + const value = this.lazy(); + if ("then" in value) { + return value.then(data => { + const map = data.map; + if (timeMessage) { + this.logger.timeEnd(timeMessage); + } + // Move to state C + this.content = map; + this.lazy = SerializerMiddleware.unMemoizeLazy(this.lazy); + return map.get(identifier); + }); + } else { + const map = value.map; + if (timeMessage) { + this.logger.timeEnd(timeMessage); + } + // Move to state C + this.content = map; + this.lazy = SerializerMiddleware.unMemoizeLazy(this.lazy); + return map.get(identifier); } + } - const texts = text.split("#"); - - if (definition) source.insert(0, definition); - - let current = dependency.range[0]; - if (dependency.arrayRange) { - source.replace(current, dependency.arrayRange[0] - 1, texts.shift()); - current = dependency.arrayRange[1]; - } + /** + * @param {string} reason explanation why unpack is necessary + * @returns {void | Promise} maybe a promise if lazy + */ + unpack(reason) { + if (this.content) return; - if (dependency.objectRange) { - source.replace(current, dependency.objectRange[0] - 1, texts.shift()); - current = dependency.objectRange[1]; - } else if (dependency.functionRange) { - source.replace(current, dependency.functionRange[0] - 1, texts.shift()); - current = dependency.functionRange[1]; + // Move from state B to C + if (this.lazy) { + const { lazyName } = this; + let timeMessage; + if (lazyName) { + // only log once + this.lazyName = undefined; + timeMessage = `unpack cache content ${lazyName} (${formatSize( + this.getSize() + )})`; + this.logger.log( + `starting to unpack cache content ${lazyName} (${formatSize( + this.getSize() + )}) because ${reason}` + ); + this.logger.time(timeMessage); + } + const value = this.lazy(); + if ("then" in value) { + return value.then(data => { + if (timeMessage) { + this.logger.timeEnd(timeMessage); + } + this.content = data.map; + }); + } else { + if (timeMessage) { + this.logger.timeEnd(timeMessage); + } + this.content = value.map; + } } - source.replace(current, dependency.range[1] - 1, texts.shift()); - if (texts.length > 0) throw new Error("Implementation error"); } -}; - -module.exports = AMDDefineDependency; - - -/***/ }), - -/***/ 78237: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ - - - -const RuntimeGlobals = __webpack_require__(49404); -const AMDDefineDependency = __webpack_require__(76309); -const AMDRequireArrayDependency = __webpack_require__(98233); -const AMDRequireContextDependency = __webpack_require__(60958); -const AMDRequireItemDependency = __webpack_require__(90377); -const ConstDependency = __webpack_require__(60864); -const ContextDependencyHelpers = __webpack_require__(7114); -const DynamicExports = __webpack_require__(87370); -const LocalModuleDependency = __webpack_require__(67494); -const { addLocalModule, getLocalModule } = __webpack_require__(6311); - -const isBoundFunctionExpression = expr => { - if (expr.type !== "CallExpression") return false; - if (expr.callee.type !== "MemberExpression") return false; - if (expr.callee.computed) return false; - if (expr.callee.object.type !== "FunctionExpression") return false; - if (expr.callee.property.type !== "Identifier") return false; - if (expr.callee.property.name !== "bind") return false; - return true; -}; - -const isUnboundFunctionExpression = expr => { - if (expr.type === "FunctionExpression") return true; - if (expr.type === "ArrowFunctionExpression") return true; - return false; -}; -const isCallable = expr => { - if (isUnboundFunctionExpression(expr)) return true; - if (isBoundFunctionExpression(expr)) return true; - return false; -}; - -class AMDDefineDependencyParserPlugin { - constructor(options) { - this.options = options; + /** + * @returns {number} size of the content or -1 if not known + */ + getSize() { + if (!this.lazy) return -1; + const options = /** @type {any} */ (this.lazy).options; + if (!options) return -1; + const size = options.size; + if (typeof size !== "number") return -1; + return size; } - apply(parser) { - parser.hooks.call - .for("define") - .tap( - "AMDDefineDependencyParserPlugin", - this.processCallDefine.bind(this, parser) - ); + delete(identifier) { + this.items.delete(identifier); + this.used.delete(identifier); + this.outdated = true; } - processArray(parser, expr, param, identifiers, namedModule) { - if (param.isArray()) { - param.items.forEach((param, idx) => { - if ( - param.isString() && - ["require", "module", "exports"].includes(param.string) - ) - identifiers[idx] = param.string; - const result = this.processItem(parser, expr, param, namedModule); - if (result === undefined) { - this.processContext(parser, expr, param); - } - }); - return true; - } else if (param.isConstArray()) { - const deps = []; - param.array.forEach((request, idx) => { - let dep; - let localModule; - if (request === "require") { - identifiers[idx] = request; - dep = "__webpack_require__"; - } else if (["exports", "module"].includes(request)) { - identifiers[idx] = request; - dep = request; - } else if ((localModule = getLocalModule(parser.state, request))) { - localModule.flagUsed(); - dep = new LocalModuleDependency(localModule, undefined, false); - dep.loc = expr.loc; - parser.state.module.addPresentationalDependency(dep); - } else { - dep = this.newRequireItemDependency(request); - dep.loc = expr.loc; - dep.optional = !!parser.scope.inTry; - parser.state.current.addDependency(dep); - } - deps.push(dep); - }); - const dep = this.newRequireArrayDependency(deps, param.range); - dep.loc = expr.loc; - dep.optional = !!parser.scope.inTry; - parser.state.module.addPresentationalDependency(dep); - return true; + /** + * @template T + * @param {function(any): function(): Promise | PackContentItems} write write function + * @returns {void} + */ + writeLazy(write) { + if (!this.outdated && this.lazy) { + // State B1 or C1 + // this.lazy is still the valid deserialized version + write(this.lazy); + return; } - } - processItem(parser, expr, param, namedModule) { - if (param.isConditional()) { - param.options.forEach(param => { - const result = this.processItem(parser, expr, param); - if (result === undefined) { - this.processContext(parser, expr, param); - } - }); - return true; - } else if (param.isString()) { - let dep, localModule; - if (param.string === "require") { - dep = new ConstDependency("__webpack_require__", param.range, [ - RuntimeGlobals.require - ]); - } else if (param.string === "exports") { - dep = new ConstDependency("exports", param.range, [ - RuntimeGlobals.exports - ]); - } else if (param.string === "module") { - dep = new ConstDependency("module", param.range, [ - RuntimeGlobals.module - ]); - } else if ( - (localModule = getLocalModule(parser.state, param.string, namedModule)) - ) { - localModule.flagUsed(); - dep = new LocalModuleDependency(localModule, param.range, false); - } else { - dep = this.newRequireItemDependency(param.string, param.range); - dep.optional = !!parser.scope.inTry; - parser.state.current.addDependency(dep); - return true; + if (!this.outdated && this.content) { + // State A1 + const map = new Map(this.content); + // Move to state C1 + this.lazy = SerializerMiddleware.unMemoizeLazy( + write(() => new PackContentItems(map)) + ); + return; + } + if (this.content) { + // State A2 or C2 + /** @type {Map} */ + const map = new Map(); + for (const item of this.items) { + map.set(item, this.content.get(item)); } - dep.loc = expr.loc; - parser.state.module.addPresentationalDependency(dep); - return true; + // Move to state C1 + this.outdated = false; + this.content = map; + this.lazy = SerializerMiddleware.unMemoizeLazy( + write(() => new PackContentItems(map)) + ); + return; + } + // State B2 + const { lazyName } = this; + let timeMessage; + if (lazyName) { + // only log once + this.lazyName = undefined; + timeMessage = `unpack cache content ${lazyName} (${formatSize( + this.getSize() + )})`; + this.logger.log( + `starting to unpack cache content ${lazyName} (${formatSize( + this.getSize() + )}) because it's outdated and need to be serialized` + ); + this.logger.time(timeMessage); + } + const value = this.lazy(); + this.outdated = false; + if ("then" in value) { + // Move to state B1 + this.lazy = write(() => + value.then(data => { + if (timeMessage) { + this.logger.timeEnd(timeMessage); + } + const oldMap = data.map; + /** @type {Map} */ + const map = new Map(); + for (const item of this.items) { + map.set(item, oldMap.get(item)); + } + // Move to state C1 (or maybe C2) + this.content = map; + this.lazy = SerializerMiddleware.unMemoizeLazy(this.lazy); + + return new PackContentItems(map); + }) + ); + } else { + // Move to state C1 + if (timeMessage) { + this.logger.timeEnd(timeMessage); + } + const oldMap = value.map; + /** @type {Map} */ + const map = new Map(); + for (const item of this.items) { + map.set(item, oldMap.get(item)); + } + this.content = map; + this.lazy = write(() => new PackContentItems(map)); } } - processContext(parser, expr, param) { - const dep = ContextDependencyHelpers.create( - AMDRequireContextDependency, - param.range, - param, - expr, - this.options, - { - category: "amd" - }, - parser - ); - if (!dep) return; - dep.loc = expr.loc; - dep.optional = !!parser.scope.inTry; - parser.state.current.addDependency(dep); - return true; +} + +const allowCollectingMemory = buf => { + const wasted = buf.buffer.byteLength - buf.byteLength; + if (wasted > 8192 && (wasted > 1048576 || wasted > buf.byteLength)) { + return Buffer.from(buf); + } + return buf; +}; + +class PackFileCacheStrategy { + /** + * @param {Object} options options + * @param {Compiler} options.compiler the compiler + * @param {IntermediateFileSystem} options.fs the filesystem + * @param {string} options.context the context directory + * @param {string} options.cacheLocation the location of the cache data + * @param {string} options.version version identifier + * @param {Logger} options.logger a logger + * @param {SnapshotOptions} options.snapshot options regarding snapshotting + * @param {number} options.maxAge max age of cache items + * @param {boolean} options.profile track and log detailed timing information for individual cache items + * @param {boolean} options.allowCollectingMemory allow to collect unused memory created during deserialization + * @param {false | "gzip" | "brotli"} options.compression compression used + */ + constructor({ + compiler, + fs, + context, + cacheLocation, + version, + logger, + snapshot, + maxAge, + profile, + allowCollectingMemory, + compression + }) { + this.fileSerializer = createFileSerializer( + fs, + compiler.options.output.hashFunction + ); + this.fileSystemInfo = new FileSystemInfo(fs, { + managedPaths: snapshot.managedPaths, + immutablePaths: snapshot.immutablePaths, + logger: logger.getChildLogger("webpack.FileSystemInfo"), + hashFunction: compiler.options.output.hashFunction + }); + this.compiler = compiler; + this.context = context; + this.cacheLocation = cacheLocation; + this.version = version; + this.logger = logger; + this.maxAge = maxAge; + this.profile = profile; + this.allowCollectingMemory = allowCollectingMemory; + this.compression = compression; + this._extension = + compression === "brotli" + ? ".pack.br" + : compression === "gzip" + ? ".pack.gz" + : ".pack"; + this.snapshot = snapshot; + /** @type {Set} */ + this.buildDependencies = new Set(); + /** @type {LazySet} */ + this.newBuildDependencies = new LazySet(); + /** @type {Snapshot} */ + this.resolveBuildDependenciesSnapshot = undefined; + /** @type {Map} */ + this.resolveResults = undefined; + /** @type {Snapshot} */ + this.buildSnapshot = undefined; + /** @type {Promise} */ + this.packPromise = this._openPack(); + this.storePromise = Promise.resolve(); + } + + _getPack() { + if (this.packPromise === undefined) { + this.packPromise = this.storePromise.then(() => this._openPack()); + } + return this.packPromise; } - processCallDefine(parser, expr) { - let array, fn, obj, namedModule; - switch (expr.arguments.length) { - case 1: - if (isCallable(expr.arguments[0])) { - // define(f() {…}) - fn = expr.arguments[0]; - } else if (expr.arguments[0].type === "ObjectExpression") { - // define({…}) - obj = expr.arguments[0]; - } else { - // define(expr) - // unclear if function or object - obj = fn = expr.arguments[0]; - } - break; - case 2: - if (expr.arguments[0].type === "Literal") { - namedModule = expr.arguments[0].value; - // define("…", …) - if (isCallable(expr.arguments[1])) { - // define("…", f() {…}) - fn = expr.arguments[1]; - } else if (expr.arguments[1].type === "ObjectExpression") { - // define("…", {…}) - obj = expr.arguments[1]; - } else { - // define("…", expr) - // unclear if function or object - obj = fn = expr.arguments[1]; - } + /** + * @returns {Promise} the pack + */ + _openPack() { + const { logger, profile, cacheLocation, version } = this; + /** @type {Snapshot} */ + let buildSnapshot; + /** @type {Set} */ + let buildDependencies; + /** @type {Set} */ + let newBuildDependencies; + /** @type {Snapshot} */ + let resolveBuildDependenciesSnapshot; + /** @type {Map} */ + let resolveResults; + logger.time("restore cache container"); + return this.fileSerializer + .deserialize(null, { + filename: `${cacheLocation}/index${this._extension}`, + extension: `${this._extension}`, + logger, + profile, + retainedBuffer: this.allowCollectingMemory + ? allowCollectingMemory + : undefined + }) + .catch(err => { + if (err.code !== "ENOENT") { + logger.warn( + `Restoring pack failed from ${cacheLocation}${this._extension}: ${err}` + ); + logger.debug(err.stack); } else { - array = expr.arguments[0]; - if (isCallable(expr.arguments[1])) { - // define([…], f() {}) - fn = expr.arguments[1]; - } else if (expr.arguments[1].type === "ObjectExpression") { - // define([…], {…}) - obj = expr.arguments[1]; - } else { - // define([…], expr) - // unclear if function or object - obj = fn = expr.arguments[1]; - } + logger.debug( + `No pack exists at ${cacheLocation}${this._extension}: ${err}` + ); } - break; - case 3: - // define("…", […], f() {…}) - namedModule = expr.arguments[0].value; - array = expr.arguments[1]; - if (isCallable(expr.arguments[2])) { - // define("…", […], f() {}) - fn = expr.arguments[2]; - } else if (expr.arguments[2].type === "ObjectExpression") { - // define("…", […], {…}) - obj = expr.arguments[2]; - } else { - // define("…", […], expr) - // unclear if function or object - obj = fn = expr.arguments[2]; + return undefined; + }) + .then(packContainer => { + logger.timeEnd("restore cache container"); + if (!packContainer) return undefined; + if (!(packContainer instanceof PackContainer)) { + logger.warn( + `Restored pack from ${cacheLocation}${this._extension}, but contained content is unexpected.`, + packContainer + ); + return undefined; } - break; - default: - return; - } - DynamicExports.bailout(parser.state); - let fnParams = null; - let fnParamsOffset = 0; - if (fn) { - if (isUnboundFunctionExpression(fn)) { - fnParams = fn.params; - } else if (isBoundFunctionExpression(fn)) { - fnParams = fn.callee.object.params; - fnParamsOffset = fn.arguments.length - 1; - if (fnParamsOffset < 0) { - fnParamsOffset = 0; + if (packContainer.version !== version) { + logger.log( + `Restored pack from ${cacheLocation}${this._extension}, but version doesn't match.` + ); + return undefined; } - } - } - let fnRenames = new Map(); - if (array) { - const identifiers = {}; - const param = parser.evaluateExpression(array); - const result = this.processArray( - parser, - expr, - param, - identifiers, - namedModule - ); - if (!result) return; - if (fnParams) { - fnParams = fnParams.slice(fnParamsOffset).filter((param, idx) => { - if (identifiers[idx]) { - fnRenames.set(param.name, parser.getVariableInfo(identifiers[idx])); - return false; - } - return true; - }); - } - } else { - const identifiers = ["require", "exports", "module"]; - if (fnParams) { - fnParams = fnParams.slice(fnParamsOffset).filter((param, idx) => { - if (identifiers[idx]) { - fnRenames.set(param.name, parser.getVariableInfo(identifiers[idx])); - return false; - } - return true; - }); - } - } - let inTry; - if (fn && isUnboundFunctionExpression(fn)) { - inTry = parser.scope.inTry; - parser.inScope(fnParams, () => { - for (const [name, varInfo] of fnRenames) { - parser.setVariable(name, varInfo); + logger.time("check build dependencies"); + return Promise.all([ + new Promise((resolve, reject) => { + this.fileSystemInfo.checkSnapshotValid( + packContainer.buildSnapshot, + (err, valid) => { + if (err) { + logger.log( + `Restored pack from ${cacheLocation}${this._extension}, but checking snapshot of build dependencies errored: ${err}.` + ); + logger.debug(err.stack); + return resolve(false); + } + if (!valid) { + logger.log( + `Restored pack from ${cacheLocation}${this._extension}, but build dependencies have changed.` + ); + return resolve(false); + } + buildSnapshot = packContainer.buildSnapshot; + return resolve(true); + } + ); + }), + new Promise((resolve, reject) => { + this.fileSystemInfo.checkSnapshotValid( + packContainer.resolveBuildDependenciesSnapshot, + (err, valid) => { + if (err) { + logger.log( + `Restored pack from ${cacheLocation}${this._extension}, but checking snapshot of resolving of build dependencies errored: ${err}.` + ); + logger.debug(err.stack); + return resolve(false); + } + if (valid) { + resolveBuildDependenciesSnapshot = + packContainer.resolveBuildDependenciesSnapshot; + buildDependencies = packContainer.buildDependencies; + resolveResults = packContainer.resolveResults; + return resolve(true); + } + logger.log( + "resolving of build dependencies is invalid, will re-resolve build dependencies" + ); + this.fileSystemInfo.checkResolveResultsValid( + packContainer.resolveResults, + (err, valid) => { + if (err) { + logger.log( + `Restored pack from ${cacheLocation}${this._extension}, but resolving of build dependencies errored: ${err}.` + ); + logger.debug(err.stack); + return resolve(false); + } + if (valid) { + newBuildDependencies = packContainer.buildDependencies; + resolveResults = packContainer.resolveResults; + return resolve(true); + } + logger.log( + `Restored pack from ${cacheLocation}${this._extension}, but build dependencies resolve to different locations.` + ); + return resolve(false); + } + ); + } + ); + }) + ]) + .catch(err => { + logger.timeEnd("check build dependencies"); + throw err; + }) + .then(([buildSnapshotValid, resolveValid]) => { + logger.timeEnd("check build dependencies"); + if (buildSnapshotValid && resolveValid) { + logger.time("restore cache content metadata"); + const d = packContainer.data(); + logger.timeEnd("restore cache content metadata"); + return d; + } + return undefined; + }); + }) + .then(pack => { + if (pack) { + pack.maxAge = this.maxAge; + this.buildSnapshot = buildSnapshot; + if (buildDependencies) this.buildDependencies = buildDependencies; + if (newBuildDependencies) + this.newBuildDependencies.addAll(newBuildDependencies); + this.resolveResults = resolveResults; + this.resolveBuildDependenciesSnapshot = + resolveBuildDependenciesSnapshot; + return pack; } - parser.scope.inTry = inTry; - if (fn.body.type === "BlockStatement") { - parser.detectMode(fn.body.body); - const prev = parser.prevStatement; - parser.preWalkStatement(fn.body); - parser.prevStatement = prev; - parser.walkStatement(fn.body); - } else { - parser.walkExpression(fn.body); + return new Pack(logger, this.maxAge); + }) + .catch(err => { + this.logger.warn( + `Restoring pack from ${cacheLocation}${this._extension} failed: ${err}` + ); + this.logger.debug(err.stack); + return new Pack(logger, this.maxAge); + }); + } + + /** + * @param {string} identifier unique name for the resource + * @param {Etag | null} etag etag of the resource + * @param {any} data cached content + * @returns {Promise} promise + */ + store(identifier, etag, data) { + return this._getPack().then(pack => { + pack.set(identifier, etag === null ? null : etag.toString(), data); + }); + } + + /** + * @param {string} identifier unique name for the resource + * @param {Etag | null} etag etag of the resource + * @returns {Promise} promise to the cached content + */ + restore(identifier, etag) { + return this._getPack() + .then(pack => + pack.get(identifier, etag === null ? null : etag.toString()) + ) + .catch(err => { + if (err && err.code !== "ENOENT") { + this.logger.warn( + `Restoring failed for ${identifier} from pack: ${err}` + ); + this.logger.debug(err.stack); } }); - } else if (fn && isBoundFunctionExpression(fn)) { - inTry = parser.scope.inTry; - parser.inScope( - fn.callee.object.params.filter( - i => !["require", "module", "exports"].includes(i.name) - ), - () => { - for (const [name, varInfo] of fnRenames) { - parser.setVariable(name, varInfo); - } - parser.scope.inTry = inTry; - if (fn.callee.object.body.type === "BlockStatement") { - parser.detectMode(fn.callee.object.body.body); - const prev = parser.prevStatement; - parser.preWalkStatement(fn.callee.object.body); - parser.prevStatement = prev; - parser.walkStatement(fn.callee.object.body); - } else { - parser.walkExpression(fn.callee.object.body); + } + + storeBuildDependencies(dependencies) { + this.newBuildDependencies.addAll(dependencies); + } + + afterAllStored() { + const packPromise = this.packPromise; + if (packPromise === undefined) return Promise.resolve(); + const reportProgress = ProgressPlugin.getReporter(this.compiler); + return (this.storePromise = packPromise + .then(pack => { + pack.stopCapturingRequests(); + if (!pack.invalid) return; + this.packPromise = undefined; + this.logger.log(`Storing pack...`); + let promise; + const newBuildDependencies = new Set(); + for (const dep of this.newBuildDependencies) { + if (!this.buildDependencies.has(dep)) { + newBuildDependencies.add(dep); } } - ); - if (fn.arguments) { - parser.walkExpressions(fn.arguments); - } - } else if (fn || obj) { - parser.walkExpression(fn || obj); - } + if (newBuildDependencies.size > 0 || !this.buildSnapshot) { + if (reportProgress) reportProgress(0.5, "resolve build dependencies"); + this.logger.debug( + `Capturing build dependencies... (${Array.from( + newBuildDependencies + ).join(", ")})` + ); + promise = new Promise((resolve, reject) => { + this.logger.time("resolve build dependencies"); + this.fileSystemInfo.resolveBuildDependencies( + this.context, + newBuildDependencies, + (err, result) => { + this.logger.timeEnd("resolve build dependencies"); + if (err) return reject(err); - const dep = this.newDefineDependency( - expr.range, - array ? array.range : null, - fn ? fn.range : null, - obj ? obj.range : null, - namedModule ? namedModule : null - ); - dep.loc = expr.loc; - if (namedModule) { - dep.localModule = addLocalModule(parser.state, namedModule); - } - parser.state.module.addPresentationalDependency(dep); - return true; + this.logger.time("snapshot build dependencies"); + const { + files, + directories, + missing, + resolveResults, + resolveDependencies + } = result; + if (this.resolveResults) { + for (const [key, value] of resolveResults) { + this.resolveResults.set(key, value); + } + } else { + this.resolveResults = resolveResults; + } + if (reportProgress) { + reportProgress( + 0.6, + "snapshot build dependencies", + "resolving" + ); + } + this.fileSystemInfo.createSnapshot( + undefined, + resolveDependencies.files, + resolveDependencies.directories, + resolveDependencies.missing, + this.snapshot.resolveBuildDependencies, + (err, snapshot) => { + if (err) { + this.logger.timeEnd("snapshot build dependencies"); + return reject(err); + } + if (!snapshot) { + this.logger.timeEnd("snapshot build dependencies"); + return reject( + new Error("Unable to snapshot resolve dependencies") + ); + } + if (this.resolveBuildDependenciesSnapshot) { + this.resolveBuildDependenciesSnapshot = + this.fileSystemInfo.mergeSnapshots( + this.resolveBuildDependenciesSnapshot, + snapshot + ); + } else { + this.resolveBuildDependenciesSnapshot = snapshot; + } + if (reportProgress) { + reportProgress( + 0.7, + "snapshot build dependencies", + "modules" + ); + } + this.fileSystemInfo.createSnapshot( + undefined, + files, + directories, + missing, + this.snapshot.buildDependencies, + (err, snapshot) => { + this.logger.timeEnd("snapshot build dependencies"); + if (err) return reject(err); + if (!snapshot) { + return reject( + new Error("Unable to snapshot build dependencies") + ); + } + this.logger.debug("Captured build dependencies"); + + if (this.buildSnapshot) { + this.buildSnapshot = + this.fileSystemInfo.mergeSnapshots( + this.buildSnapshot, + snapshot + ); + } else { + this.buildSnapshot = snapshot; + } + + resolve(); + } + ); + } + ); + } + ); + }); + } else { + promise = Promise.resolve(); + } + return promise.then(() => { + if (reportProgress) reportProgress(0.8, "serialize pack"); + this.logger.time(`store pack`); + const updatedBuildDependencies = new Set(this.buildDependencies); + for (const dep of newBuildDependencies) { + updatedBuildDependencies.add(dep); + } + const content = new PackContainer( + pack, + this.version, + this.buildSnapshot, + updatedBuildDependencies, + this.resolveResults, + this.resolveBuildDependenciesSnapshot + ); + return this.fileSerializer + .serialize(content, { + filename: `${this.cacheLocation}/index${this._extension}`, + extension: `${this._extension}`, + logger: this.logger, + profile: this.profile + }) + .then(() => { + for (const dep of newBuildDependencies) { + this.buildDependencies.add(dep); + } + this.newBuildDependencies.clear(); + this.logger.timeEnd(`store pack`); + const stats = pack.getContentStats(); + this.logger.log( + "Stored pack (%d items, %d files, %d MiB)", + pack.itemInfo.size, + stats.count, + Math.round(stats.size / 1024 / 1024) + ); + }) + .catch(err => { + this.logger.timeEnd(`store pack`); + this.logger.warn(`Caching failed for pack: ${err}`); + this.logger.debug(err.stack); + }); + }); + }) + .catch(err => { + this.logger.warn(`Caching failed for pack: ${err}`); + this.logger.debug(err.stack); + })); } - newDefineDependency( - range, - arrayRange, - functionRange, - objectRange, - namedModule - ) { - return new AMDDefineDependency( - range, - arrayRange, - functionRange, - objectRange, - namedModule - ); - } - newRequireArrayDependency(depsArray, range) { - return new AMDRequireArrayDependency(depsArray, range); - } - newRequireItemDependency(request, range) { - return new AMDRequireItemDependency(request, range); + clear() { + this.fileSystemInfo.clear(); + this.buildDependencies.clear(); + this.newBuildDependencies.clear(); + this.resolveBuildDependenciesSnapshot = undefined; + this.resolveResults = undefined; + this.buildSnapshot = undefined; + this.packPromise = undefined; } } -module.exports = AMDDefineDependencyParserPlugin; + +module.exports = PackFileCacheStrategy; /***/ }), -/***/ 82916: +/***/ 11740: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; @@ -73715,220 +69433,297 @@ module.exports = AMDDefineDependencyParserPlugin; -const RuntimeGlobals = __webpack_require__(49404); -const { - approve, - evaluateToIdentifier, - evaluateToString, - toConstantDependency -} = __webpack_require__(28723); - -const AMDDefineDependency = __webpack_require__(76309); -const AMDDefineDependencyParserPlugin = __webpack_require__(78237); -const AMDRequireArrayDependency = __webpack_require__(98233); -const AMDRequireContextDependency = __webpack_require__(60958); -const AMDRequireDependenciesBlockParserPlugin = __webpack_require__(78012); -const AMDRequireDependency = __webpack_require__(11311); -const AMDRequireItemDependency = __webpack_require__(90377); -const { - AMDDefineRuntimeModule, - AMDOptionsRuntimeModule -} = __webpack_require__(35469); -const ConstDependency = __webpack_require__(60864); -const LocalModuleDependency = __webpack_require__(67494); -const UnsupportedDependency = __webpack_require__(41381); +const LazySet = __webpack_require__(59534); +const makeSerializable = __webpack_require__(26522); -/** @typedef {import("../../declarations/WebpackOptions").ModuleOptionsNormalized} ModuleOptions */ +/** @typedef {import("enhanced-resolve/lib/Resolver")} Resolver */ +/** @typedef {import("../CacheFacade").ItemCacheFacade} ItemCacheFacade */ /** @typedef {import("../Compiler")} Compiler */ +/** @typedef {import("../FileSystemInfo")} FileSystemInfo */ +/** @typedef {import("../FileSystemInfo").Snapshot} Snapshot */ -class AMDPlugin { - /** - * @param {Record} amdOptions the AMD options - */ - constructor(amdOptions) { - this.amdOptions = amdOptions; +class CacheEntry { + constructor(result, snapshot) { + this.result = result; + this.snapshot = snapshot; + } + + serialize({ write }) { + write(this.result); + write(this.snapshot); + } + + deserialize({ read }) { + this.result = read(); + this.snapshot = read(); + } +} + +makeSerializable(CacheEntry, "webpack/lib/cache/ResolverCachePlugin"); + +/** + * @template T + * @param {Set | LazySet} set set to add items to + * @param {Set | LazySet} otherSet set to add items from + * @returns {void} + */ +const addAllToSet = (set, otherSet) => { + if (set instanceof LazySet) { + set.addAll(otherSet); + } else { + for (const item of otherSet) { + set.add(item); + } + } +}; + +/** + * @param {Object} object an object + * @param {boolean} excludeContext if true, context is not included in string + * @returns {string} stringified version + */ +const objectToString = (object, excludeContext) => { + let str = ""; + for (const key in object) { + if (excludeContext && key === "context") continue; + const value = object[key]; + if (typeof value === "object" && value !== null) { + str += `|${key}=[${objectToString(value, false)}|]`; + } else { + str += `|${key}=|${value}`; + } } + return str; +}; +class ResolverCachePlugin { /** * Apply the plugin * @param {Compiler} compiler the compiler instance * @returns {void} */ apply(compiler) { - const amdOptions = this.amdOptions; - compiler.hooks.compilation.tap( - "AMDPlugin", - (compilation, { contextModuleFactory, normalModuleFactory }) => { - compilation.dependencyTemplates.set( - AMDRequireDependency, - new AMDRequireDependency.Template() - ); - - compilation.dependencyFactories.set( - AMDRequireItemDependency, - normalModuleFactory - ); - compilation.dependencyTemplates.set( - AMDRequireItemDependency, - new AMDRequireItemDependency.Template() - ); - - compilation.dependencyTemplates.set( - AMDRequireArrayDependency, - new AMDRequireArrayDependency.Template() - ); - - compilation.dependencyFactories.set( - AMDRequireContextDependency, - contextModuleFactory - ); - compilation.dependencyTemplates.set( - AMDRequireContextDependency, - new AMDRequireContextDependency.Template() - ); - - compilation.dependencyTemplates.set( - AMDDefineDependency, - new AMDDefineDependency.Template() - ); - - compilation.dependencyTemplates.set( - UnsupportedDependency, - new UnsupportedDependency.Template() - ); - - compilation.dependencyTemplates.set( - LocalModuleDependency, - new LocalModuleDependency.Template() - ); - - compilation.hooks.runtimeRequirementInModule - .for(RuntimeGlobals.amdDefine) - .tap("AMDPlugin", (module, set) => { - set.add(RuntimeGlobals.require); - }); - - compilation.hooks.runtimeRequirementInModule - .for(RuntimeGlobals.amdOptions) - .tap("AMDPlugin", (module, set) => { - set.add(RuntimeGlobals.requireScope); - }); - - compilation.hooks.runtimeRequirementInTree - .for(RuntimeGlobals.amdDefine) - .tap("AMDPlugin", (chunk, set) => { - compilation.addRuntimeModule(chunk, new AMDDefineRuntimeModule()); - }); - - compilation.hooks.runtimeRequirementInTree - .for(RuntimeGlobals.amdOptions) - .tap("AMDPlugin", (chunk, set) => { - compilation.addRuntimeModule( - chunk, - new AMDOptionsRuntimeModule(amdOptions) - ); - }); - - const handler = (parser, parserOptions) => { - if (parserOptions.amd !== undefined && !parserOptions.amd) return; - - const tapOptionsHooks = (optionExpr, rootName, getMembers) => { - parser.hooks.expression - .for(optionExpr) - .tap( - "AMDPlugin", - toConstantDependency(parser, RuntimeGlobals.amdOptions, [ - RuntimeGlobals.amdOptions - ]) - ); - parser.hooks.evaluateIdentifier - .for(optionExpr) - .tap( - "AMDPlugin", - evaluateToIdentifier(optionExpr, rootName, getMembers, true) - ); - parser.hooks.evaluateTypeof - .for(optionExpr) - .tap("AMDPlugin", evaluateToString("object")); - parser.hooks.typeof - .for(optionExpr) - .tap( - "AMDPlugin", - toConstantDependency(parser, JSON.stringify("object")) - ); - }; - - new AMDRequireDependenciesBlockParserPlugin(parserOptions).apply( - parser + const cache = compiler.getCache("ResolverCachePlugin"); + /** @type {FileSystemInfo} */ + let fileSystemInfo; + let snapshotOptions; + let realResolves = 0; + let cachedResolves = 0; + let cacheInvalidResolves = 0; + let concurrentResolves = 0; + compiler.hooks.thisCompilation.tap("ResolverCachePlugin", compilation => { + snapshotOptions = compilation.options.snapshot.resolve; + fileSystemInfo = compilation.fileSystemInfo; + compilation.hooks.finishModules.tap("ResolverCachePlugin", () => { + if (realResolves + cachedResolves > 0) { + const logger = compilation.getLogger("webpack.ResolverCachePlugin"); + logger.log( + `${Math.round( + (100 * realResolves) / (realResolves + cachedResolves) + )}% really resolved (${realResolves} real resolves with ${cacheInvalidResolves} cached but invalid, ${cachedResolves} cached valid, ${concurrentResolves} concurrent)` ); - new AMDDefineDependencyParserPlugin(parserOptions).apply(parser); - - tapOptionsHooks("define.amd", "define", () => "amd"); - tapOptionsHooks("require.amd", "require", () => ["amd"]); - tapOptionsHooks( - "__webpack_amd_options__", - "__webpack_amd_options__", - () => [] + realResolves = 0; + cachedResolves = 0; + cacheInvalidResolves = 0; + concurrentResolves = 0; + } + }); + }); + /** + * @param {ItemCacheFacade} itemCache cache + * @param {Resolver} resolver the resolver + * @param {Object} resolveContext context for resolving meta info + * @param {Object} request the request info object + * @param {function(Error=, Object=): void} callback callback function + * @returns {void} + */ + const doRealResolve = ( + itemCache, + resolver, + resolveContext, + request, + callback + ) => { + realResolves++; + const newRequest = { + _ResolverCachePluginCacheMiss: true, + ...request + }; + const newResolveContext = { + ...resolveContext, + stack: new Set(), + missingDependencies: new LazySet(), + fileDependencies: new LazySet(), + contextDependencies: new LazySet() + }; + const propagate = key => { + if (resolveContext[key]) { + addAllToSet(resolveContext[key], newResolveContext[key]); + } + }; + const resolveTime = Date.now(); + resolver.doResolve( + resolver.hooks.resolve, + newRequest, + "Cache miss", + newResolveContext, + (err, result) => { + propagate("fileDependencies"); + propagate("contextDependencies"); + propagate("missingDependencies"); + if (err) return callback(err); + const fileDependencies = newResolveContext.fileDependencies; + const contextDependencies = newResolveContext.contextDependencies; + const missingDependencies = newResolveContext.missingDependencies; + fileSystemInfo.createSnapshot( + resolveTime, + fileDependencies, + contextDependencies, + missingDependencies, + snapshotOptions, + (err, snapshot) => { + if (err) return callback(err); + if (!snapshot) { + if (result) return callback(null, result); + return callback(); + } + itemCache.store(new CacheEntry(result, snapshot), storeErr => { + if (storeErr) return callback(storeErr); + if (result) return callback(null, result); + callback(); + }); + } ); + } + ); + }; + compiler.resolverFactory.hooks.resolver.intercept({ + factory(type, hook) { + /** @type {Map} */ + const activeRequests = new Map(); + hook.tap( + "ResolverCachePlugin", + /** + * @param {Resolver} resolver the resolver + * @param {Object} options resolve options + * @param {Object} userOptions resolve options passed by the user + * @returns {void} + */ + (resolver, options, userOptions) => { + if (options.cache !== true) return; + const optionsIdent = objectToString(userOptions, false); + const cacheWithContext = + options.cacheWithContext !== undefined + ? options.cacheWithContext + : false; + resolver.hooks.resolve.tapAsync( + { + name: "ResolverCachePlugin", + stage: -100 + }, + (request, resolveContext, callback) => { + if (request._ResolverCachePluginCacheMiss || !fileSystemInfo) { + return callback(); + } + const identifier = `${type}${optionsIdent}${objectToString( + request, + !cacheWithContext + )}`; + const activeRequest = activeRequests.get(identifier); + if (activeRequest) { + activeRequest.push(callback); + return; + } + const itemCache = cache.getItemCache(identifier, null); + let callbacks; + const done = (err, result) => { + if (callbacks === undefined) { + callback(err, result); + callbacks = false; + } else { + for (const callback of callbacks) { + callback(err, result); + } + activeRequests.delete(identifier); + callbacks = false; + } + }; + /** + * @param {Error=} err error if any + * @param {CacheEntry=} cacheEntry cache entry + * @returns {void} + */ + const processCacheResult = (err, cacheEntry) => { + if (err) return done(err); - parser.hooks.expression.for("define").tap("AMDPlugin", expr => { - const dep = new ConstDependency( - RuntimeGlobals.amdDefine, - expr.range, - [RuntimeGlobals.amdDefine] - ); - dep.loc = expr.loc; - parser.state.module.addPresentationalDependency(dep); - return true; - }); - parser.hooks.typeof - .for("define") - .tap( - "AMDPlugin", - toConstantDependency(parser, JSON.stringify("function")) - ); - parser.hooks.evaluateTypeof - .for("define") - .tap("AMDPlugin", evaluateToString("function")); - parser.hooks.canRename.for("define").tap("AMDPlugin", approve); - parser.hooks.rename.for("define").tap("AMDPlugin", expr => { - const dep = new ConstDependency( - RuntimeGlobals.amdDefine, - expr.range, - [RuntimeGlobals.amdDefine] - ); - dep.loc = expr.loc; - parser.state.module.addPresentationalDependency(dep); - return false; - }); - parser.hooks.typeof - .for("require") - .tap( - "AMDPlugin", - toConstantDependency(parser, JSON.stringify("function")) + if (cacheEntry) { + const { snapshot, result } = cacheEntry; + fileSystemInfo.checkSnapshotValid( + snapshot, + (err, valid) => { + if (err || !valid) { + cacheInvalidResolves++; + return doRealResolve( + itemCache, + resolver, + resolveContext, + request, + done + ); + } + cachedResolves++; + if (resolveContext.missingDependencies) { + addAllToSet( + resolveContext.missingDependencies, + snapshot.getMissingIterable() + ); + } + if (resolveContext.fileDependencies) { + addAllToSet( + resolveContext.fileDependencies, + snapshot.getFileIterable() + ); + } + if (resolveContext.contextDependencies) { + addAllToSet( + resolveContext.contextDependencies, + snapshot.getContextIterable() + ); + } + done(null, result); + } + ); + } else { + doRealResolve( + itemCache, + resolver, + resolveContext, + request, + done + ); + } + }; + itemCache.get(processCacheResult); + if (callbacks === undefined) { + callbacks = [callback]; + activeRequests.set(identifier, callbacks); + } + } ); - parser.hooks.evaluateTypeof - .for("require") - .tap("AMDPlugin", evaluateToString("function")); - }; - - normalModuleFactory.hooks.parser - .for("javascript/auto") - .tap("AMDPlugin", handler); - normalModuleFactory.hooks.parser - .for("javascript/dynamic") - .tap("AMDPlugin", handler); + } + ); + return hook; } - ); + }); } } -module.exports = AMDPlugin; +module.exports = ResolverCachePlugin; /***/ }), -/***/ 98233: +/***/ 12339: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; @@ -73939,104 +69734,168 @@ module.exports = AMDPlugin; -const DependencyTemplate = __webpack_require__(17600); -const makeSerializable = __webpack_require__(26522); -const NullDependency = __webpack_require__(65845); +const createHash = __webpack_require__(24123); -/** @typedef {import("webpack-sources").ReplaceSource} ReplaceSource */ -/** @typedef {import("../Dependency")} Dependency */ -/** @typedef {import("../DependencyTemplate").DependencyTemplateContext} DependencyTemplateContext */ +/** @typedef {import("../util/Hash")} Hash */ +/** @typedef {typeof import("../util/Hash")} HashConstructor */ -class AMDRequireArrayDependency extends NullDependency { - constructor(depsArray, range) { - super(); +/** + * @typedef {Object} HashableObject + * @property {function(Hash): void} updateHash + */ - this.depsArray = depsArray; - this.range = range; +class LazyHashedEtag { + /** + * @param {HashableObject} obj object with updateHash method + * @param {string | HashConstructor} hashFunction the hash function to use + */ + constructor(obj, hashFunction = "md4") { + this._obj = obj; + this._hash = undefined; + this._hashFunction = hashFunction; } - get type() { - return "amd require array"; + /** + * @returns {string} hash of object + */ + toString() { + if (this._hash === undefined) { + const hash = createHash(this._hashFunction); + this._obj.updateHash(hash); + this._hash = /** @type {string} */ (hash.digest("base64")); + } + return this._hash; } +} - get category() { - return "amd"; +/** @type {Map>} */ +const mapStrings = new Map(); + +/** @type {WeakMap>} */ +const mapObjects = new WeakMap(); + +/** + * @param {HashableObject} obj object with updateHash method + * @param {string | HashConstructor} hashFunction the hash function to use + * @returns {LazyHashedEtag} etag + */ +const getter = (obj, hashFunction = "md4") => { + let innerMap; + if (typeof hashFunction === "string") { + innerMap = mapStrings.get(hashFunction); + if (innerMap === undefined) { + const newHash = new LazyHashedEtag(obj, hashFunction); + innerMap = new WeakMap(); + innerMap.set(obj, newHash); + mapStrings.set(hashFunction, innerMap); + return newHash; + } + } else { + innerMap = mapObjects.get(hashFunction); + if (innerMap === undefined) { + const newHash = new LazyHashedEtag(obj, hashFunction); + innerMap = new WeakMap(); + innerMap.set(obj, newHash); + mapObjects.set(hashFunction, innerMap); + return newHash; + } } + const hash = innerMap.get(obj); + if (hash !== undefined) return hash; + const newHash = new LazyHashedEtag(obj, hashFunction); + innerMap.set(obj, newHash); + return newHash; +}; - serialize(context) { - const { write } = context; +module.exports = getter; - write(this.depsArray); - write(this.range); - super.serialize(context); - } +/***/ }), - deserialize(context) { - const { read } = context; +/***/ 53885: +/***/ (function(module) { - this.depsArray = read(); - this.range = read(); +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ - super.deserialize(context); - } -} -makeSerializable( - AMDRequireArrayDependency, - "webpack/lib/dependencies/AMDRequireArrayDependency" -); -AMDRequireArrayDependency.Template = class AMDRequireArrayDependencyTemplate extends ( - DependencyTemplate -) { +/** @typedef {import("../Cache").Etag} Etag */ + +class MergedEtag { /** - * @param {Dependency} dependency the dependency for which the template should be applied - * @param {ReplaceSource} source the current replace source which can be modified - * @param {DependencyTemplateContext} templateContext the context object - * @returns {void} + * @param {Etag} a first + * @param {Etag} b second */ - apply(dependency, source, templateContext) { - const dep = /** @type {AMDRequireArrayDependency} */ (dependency); - const content = this.getContent(dep, templateContext); - source.replace(dep.range[0], dep.range[1] - 1, content); + constructor(a, b) { + this.a = a; + this.b = b; } - getContent(dep, templateContext) { - const requires = dep.depsArray.map(dependency => { - return this.contentForDependency(dependency, templateContext); - }); - return `[${requires.join(", ")}]`; + toString() { + return `${this.a.toString()}|${this.b.toString()}`; } +} - contentForDependency( - dep, - { runtimeTemplate, moduleGraph, chunkGraph, runtimeRequirements } - ) { - if (typeof dep === "string") { - return dep; - } +const dualObjectMap = new WeakMap(); +const objectStringMap = new WeakMap(); - if (dep.localModule) { - return dep.localModule.variableName(); +/** + * @param {Etag} a first + * @param {Etag} b second + * @returns {Etag} result + */ +const mergeEtags = (a, b) => { + if (typeof a === "string") { + if (typeof b === "string") { + return `${a}|${b}`; } else { - return runtimeTemplate.moduleExports({ - module: moduleGraph.getModule(dep), - chunkGraph, - request: dep.request, - runtimeRequirements - }); + const temp = b; + b = a; + a = temp; + } + } else { + if (typeof b !== "string") { + // both a and b are objects + let map = dualObjectMap.get(a); + if (map === undefined) { + dualObjectMap.set(a, (map = new WeakMap())); + } + const mergedEtag = map.get(b); + if (mergedEtag === undefined) { + const newMergedEtag = new MergedEtag(a, b); + map.set(b, newMergedEtag); + return newMergedEtag; + } else { + return mergedEtag; + } } } + // a is object, b is string + let map = objectStringMap.get(a); + if (map === undefined) { + objectStringMap.set(a, (map = new Map())); + } + const mergedEtag = map.get(b); + if (mergedEtag === undefined) { + const newMergedEtag = new MergedEtag(a, b); + map.set(b, newMergedEtag); + return newMergedEtag; + } else { + return mergedEtag; + } }; -module.exports = AMDRequireArrayDependency; +module.exports = mergeEtags; /***/ }), -/***/ 60958: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { +/***/ 26040: +/***/ (function(__unused_webpack_module, exports, __webpack_require__) { "use strict"; /* @@ -74046,827 +69905,2162 @@ module.exports = AMDRequireArrayDependency; -const makeSerializable = __webpack_require__(26522); -const ContextDependency = __webpack_require__(67840); +const path = __webpack_require__(85622); +const webpackSchema = __webpack_require__(1863); -class AMDRequireContextDependency extends ContextDependency { - constructor(options, range, valueRange) { - super(options); +// TODO add originPath to PathItem for better errors +/** + * @typedef {Object} PathItem + * @property {any} schema the part of the schema + * @property {string} path the path in the config + */ - this.range = range; - this.valueRange = valueRange; - } +/** @typedef {"unknown-argument" | "unexpected-non-array-in-path" | "unexpected-non-object-in-path" | "multiple-values-unexpected" | "invalid-value"} ProblemType */ - get type() { - return "amd require context"; - } +/** + * @typedef {Object} Problem + * @property {ProblemType} type + * @property {string} path + * @property {string} argument + * @property {any=} value + * @property {number=} index + * @property {string=} expected + */ - get category() { - return "amd"; - } +/** + * @typedef {Object} LocalProblem + * @property {ProblemType} type + * @property {string} path + * @property {string=} expected + */ - serialize(context) { - const { write } = context; +/** + * @typedef {Object} ArgumentConfig + * @property {string} description + * @property {string} path + * @property {boolean} multiple + * @property {"enum"|"string"|"path"|"number"|"boolean"|"RegExp"|"reset"} type + * @property {any[]=} values + */ - write(this.range); - write(this.valueRange); +/** + * @typedef {Object} Argument + * @property {string} description + * @property {"string"|"number"|"boolean"} simpleType + * @property {boolean} multiple + * @property {ArgumentConfig[]} configs + */ - super.serialize(context); - } +/** + * @param {any=} schema a json schema to create arguments for (by default webpack schema is used) + * @returns {Record} object of arguments + */ +const getArguments = (schema = webpackSchema) => { + /** @type {Record} */ + const flags = {}; - deserialize(context) { - const { read } = context; + const pathToArgumentName = input => { + return input + .replace(/\./g, "-") + .replace(/\[\]/g, "") + .replace( + /(\p{Uppercase_Letter}+|\p{Lowercase_Letter}|\d)(\p{Uppercase_Letter}+)/gu, + "$1-$2" + ) + .replace(/-?[^\p{Uppercase_Letter}\p{Lowercase_Letter}\d]+/gu, "-") + .toLowerCase(); + }; - this.range = read(); - this.valueRange = read(); + const getSchemaPart = path => { + const newPath = path.split("/"); - super.deserialize(context); - } -} + let schemaPart = schema; -makeSerializable( - AMDRequireContextDependency, - "webpack/lib/dependencies/AMDRequireContextDependency" -); + for (let i = 1; i < newPath.length; i++) { + const inner = schemaPart[newPath[i]]; -AMDRequireContextDependency.Template = __webpack_require__(18259); + if (!inner) { + break; + } -module.exports = AMDRequireContextDependency; + schemaPart = inner; + } + return schemaPart; + }; -/***/ }), + /** + * + * @param {PathItem[]} path path in the schema + * @returns {string | undefined} description + */ + const getDescription = path => { + for (const { schema } of path) { + if (schema.cli && schema.cli.helper) continue; + if (schema.description) return schema.description; + } + }; -/***/ 69675: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + /** + * + * @param {any} schemaPart schema + * @returns {Pick} partial argument config + */ + const schemaToArgumentConfig = schemaPart => { + if (schemaPart.enum) { + return { + type: "enum", + values: schemaPart.enum + }; + } + switch (schemaPart.type) { + case "number": + return { + type: "number" + }; + case "string": + return { + type: schemaPart.absolutePath ? "path" : "string" + }; + case "boolean": + return { + type: "boolean" + }; + } + if (schemaPart.instanceof === "RegExp") { + return { + type: "RegExp" + }; + } + return undefined; + }; -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ + /** + * @param {PathItem[]} path path in the schema + * @returns {void} + */ + const addResetFlag = path => { + const schemaPath = path[0].path; + const name = pathToArgumentName(`${schemaPath}.reset`); + const description = getDescription(path); + flags[name] = { + configs: [ + { + type: "reset", + multiple: false, + description: `Clear all items provided in '${schemaPath}' configuration. ${description}`, + path: schemaPath + } + ], + description: undefined, + simpleType: undefined, + multiple: undefined + }; + }; + /** + * @param {PathItem[]} path full path in schema + * @param {boolean} multiple inside of an array + * @returns {number} number of arguments added + */ + const addFlag = (path, multiple) => { + const argConfigBase = schemaToArgumentConfig(path[0].schema); + if (!argConfigBase) return 0; + const name = pathToArgumentName(path[0].path); + /** @type {ArgumentConfig} */ + const argConfig = { + ...argConfigBase, + multiple, + description: getDescription(path), + path: path[0].path + }; -const AsyncDependenciesBlock = __webpack_require__(11315); -const makeSerializable = __webpack_require__(26522); + if (!flags[name]) { + flags[name] = { + configs: [], + description: undefined, + simpleType: undefined, + multiple: undefined + }; + } -class AMDRequireDependenciesBlock extends AsyncDependenciesBlock { - constructor(loc, request) { - super(null, loc, request); - } -} + if ( + flags[name].configs.some( + item => JSON.stringify(item) === JSON.stringify(argConfig) + ) + ) { + return 0; + } + + if ( + flags[name].configs.some( + item => item.type === argConfig.type && item.multiple !== multiple + ) + ) { + if (multiple) { + throw new Error( + `Conflicting schema for ${path[0].path} with ${argConfig.type} type (array type must be before single item type)` + ); + } + return 0; + } + + flags[name].configs.push(argConfig); + + return 1; + }; + + // TODO support `not` and `if/then/else` + // TODO support `const`, but we don't use it on our schema + /** + * + * @param {object} schemaPart the current schema + * @param {string} schemaPath the current path in the schema + * @param {{schema: object, path: string}[]} path all previous visited schemaParts + * @param {string | null} inArray if inside of an array, the path to the array + * @returns {number} added arguments + */ + const traverse = (schemaPart, schemaPath = "", path = [], inArray = null) => { + while (schemaPart.$ref) { + schemaPart = getSchemaPart(schemaPart.$ref); + } + + const repetitions = path.filter(({ schema }) => schema === schemaPart); + if ( + repetitions.length >= 2 || + repetitions.some(({ path }) => path === schemaPath) + ) { + return 0; + } + + if (schemaPart.cli && schemaPart.cli.exclude) return 0; + + const fullPath = [{ schema: schemaPart, path: schemaPath }, ...path]; + + let addedArguments = 0; + + addedArguments += addFlag(fullPath, !!inArray); + + if (schemaPart.type === "object") { + if (schemaPart.properties) { + for (const property of Object.keys(schemaPart.properties)) { + addedArguments += traverse( + schemaPart.properties[property], + schemaPath ? `${schemaPath}.${property}` : property, + fullPath, + inArray + ); + } + } + + return addedArguments; + } + + if (schemaPart.type === "array") { + if (inArray) { + return 0; + } + if (Array.isArray(schemaPart.items)) { + let i = 0; + for (const item of schemaPart.items) { + addedArguments += traverse( + item, + `${schemaPath}.${i}`, + fullPath, + schemaPath + ); + } -makeSerializable( - AMDRequireDependenciesBlock, - "webpack/lib/dependencies/AMDRequireDependenciesBlock" -); + return addedArguments; + } -module.exports = AMDRequireDependenciesBlock; + addedArguments += traverse( + schemaPart.items, + `${schemaPath}[]`, + fullPath, + schemaPath + ); + if (addedArguments > 0) { + addResetFlag(fullPath); + addedArguments++; + } -/***/ }), + return addedArguments; + } -/***/ 78012: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + const maybeOf = schemaPart.oneOf || schemaPart.anyOf || schemaPart.allOf; -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ + if (maybeOf) { + const items = maybeOf; + for (let i = 0; i < items.length; i++) { + addedArguments += traverse(items[i], schemaPath, fullPath, inArray); + } + return addedArguments; + } -const RuntimeGlobals = __webpack_require__(49404); -const UnsupportedFeatureWarning = __webpack_require__(9532); -const AMDRequireArrayDependency = __webpack_require__(98233); -const AMDRequireContextDependency = __webpack_require__(60958); -const AMDRequireDependenciesBlock = __webpack_require__(69675); -const AMDRequireDependency = __webpack_require__(11311); -const AMDRequireItemDependency = __webpack_require__(90377); -const ConstDependency = __webpack_require__(60864); -const ContextDependencyHelpers = __webpack_require__(7114); -const LocalModuleDependency = __webpack_require__(67494); -const { getLocalModule } = __webpack_require__(6311); -const UnsupportedDependency = __webpack_require__(41381); -const getFunctionExpression = __webpack_require__(70108); + return addedArguments; + }; -class AMDRequireDependenciesBlockParserPlugin { - constructor(options) { - this.options = options; - } + traverse(schema); - processFunctionArgument(parser, expression) { - let bindThis = true; - const fnData = getFunctionExpression(expression); - if (fnData) { - parser.inScope( - fnData.fn.params.filter(i => { - return !["require", "module", "exports"].includes(i.name); - }), - () => { - if (fnData.fn.body.type === "BlockStatement") { - parser.walkStatement(fnData.fn.body); - } else { - parser.walkExpression(fnData.fn.body); - } - } - ); - parser.walkExpressions(fnData.expressions); - if (fnData.needThis === false) { - bindThis = false; + // Summarize flags + for (const name of Object.keys(flags)) { + const argument = flags[name]; + argument.description = argument.configs.reduce((desc, { description }) => { + if (!desc) return description; + if (!description) return desc; + if (desc.includes(description)) return desc; + return `${desc} ${description}`; + }, /** @type {string | undefined} */ (undefined)); + argument.simpleType = argument.configs.reduce((t, argConfig) => { + /** @type {"string" | "number" | "boolean"} */ + let type = "string"; + switch (argConfig.type) { + case "number": + type = "number"; + break; + case "reset": + case "boolean": + type = "boolean"; + break; + case "enum": + if (argConfig.values.every(v => typeof v === "boolean")) + type = "boolean"; + if (argConfig.values.every(v => typeof v === "number")) + type = "number"; + break; } - } else { - parser.walkExpression(expression); - } - return bindThis; + if (t === undefined) return type; + return t === type ? t : "string"; + }, /** @type {"string" | "number" | "boolean" | undefined} */ (undefined)); + argument.multiple = argument.configs.some(c => c.multiple); } - apply(parser) { - parser.hooks.call - .for("require") - .tap( - "AMDRequireDependenciesBlockParserPlugin", - this.processCallRequire.bind(this, parser) - ); - } + return flags; +}; - processArray(parser, expr, param) { - if (param.isArray()) { - for (const p of param.items) { - const result = this.processItem(parser, expr, p); - if (result === undefined) { - this.processContext(parser, expr, p); +const cliAddedItems = new WeakMap(); + +/** + * @param {any} config configuration + * @param {string} schemaPath path in the config + * @param {number | undefined} index index of value when multiple values are provided, otherwise undefined + * @returns {{ problem?: LocalProblem, object?: any, property?: string | number, value?: any }} problem or object with property and value + */ +const getObjectAndProperty = (config, schemaPath, index = 0) => { + if (!schemaPath) return { value: config }; + const parts = schemaPath.split("."); + let property = parts.pop(); + let current = config; + let i = 0; + for (const part of parts) { + const isArray = part.endsWith("[]"); + const name = isArray ? part.slice(0, -2) : part; + let value = current[name]; + if (isArray) { + if (value === undefined) { + value = {}; + current[name] = [...Array.from({ length: index }), value]; + cliAddedItems.set(current[name], index + 1); + } else if (!Array.isArray(value)) { + return { + problem: { + type: "unexpected-non-array-in-path", + path: parts.slice(0, i).join(".") + } + }; + } else { + let addedItems = cliAddedItems.get(value) || 0; + while (addedItems <= index) { + value.push(undefined); + addedItems++; } - } - return true; - } else if (param.isConstArray()) { - const deps = []; - for (const request of param.array) { - let dep, localModule; - if (request === "require") { - dep = "__webpack_require__"; - } else if (["exports", "module"].includes(request)) { - dep = request; - } else if ((localModule = getLocalModule(parser.state, request))) { - localModule.flagUsed(); - dep = new LocalModuleDependency(localModule, undefined, false); - dep.loc = expr.loc; - parser.state.module.addPresentationalDependency(dep); - } else { - dep = this.newRequireItemDependency(request); - dep.loc = expr.loc; - dep.optional = !!parser.scope.inTry; - parser.state.current.addDependency(dep); + cliAddedItems.set(value, addedItems); + const x = value.length - addedItems + index; + if (value[x] === undefined) { + value[x] = {}; + } else if (value[x] === null || typeof value[x] !== "object") { + return { + problem: { + type: "unexpected-non-object-in-path", + path: parts.slice(0, i).join(".") + } + }; } - deps.push(dep); + value = value[x]; + } + } else { + if (value === undefined) { + value = current[name] = {}; + } else if (value === null || typeof value !== "object") { + return { + problem: { + type: "unexpected-non-object-in-path", + path: parts.slice(0, i).join(".") + } + }; } - const dep = this.newRequireArrayDependency(deps, param.range); - dep.loc = expr.loc; - dep.optional = !!parser.scope.inTry; - parser.state.module.addPresentationalDependency(dep); - return true; } + current = value; + i++; } - processItem(parser, expr, param) { - if (param.isConditional()) { - for (const p of param.options) { - const result = this.processItem(parser, expr, p); - if (result === undefined) { - this.processContext(parser, expr, p); - } + let value = current[property]; + if (property.endsWith("[]")) { + const name = property.slice(0, -2); + const value = current[name]; + if (value === undefined) { + current[name] = [...Array.from({ length: index }), undefined]; + cliAddedItems.set(current[name], index + 1); + return { object: current[name], property: index, value: undefined }; + } else if (!Array.isArray(value)) { + current[name] = [value, ...Array.from({ length: index }), undefined]; + cliAddedItems.set(current[name], index + 1); + return { object: current[name], property: index + 1, value: undefined }; + } else { + let addedItems = cliAddedItems.get(value) || 0; + while (addedItems <= index) { + value.push(undefined); + addedItems++; } - return true; - } else if (param.isString()) { - let dep, localModule; - if (param.string === "require") { - dep = new ConstDependency("__webpack_require__", param.string, [ - RuntimeGlobals.require - ]); - } else if (param.string === "module") { - dep = new ConstDependency( - parser.state.module.buildInfo.moduleArgument, - param.range, - [RuntimeGlobals.module] - ); - } else if (param.string === "exports") { - dep = new ConstDependency( - parser.state.module.buildInfo.exportsArgument, - param.range, - [RuntimeGlobals.exports] - ); - } else if ((localModule = getLocalModule(parser.state, param.string))) { - localModule.flagUsed(); - dep = new LocalModuleDependency(localModule, param.range, false); - } else { - dep = this.newRequireItemDependency(param.string, param.range); - dep.loc = expr.loc; - dep.optional = !!parser.scope.inTry; - parser.state.current.addDependency(dep); - return true; + cliAddedItems.set(value, addedItems); + const x = value.length - addedItems + index; + if (value[x] === undefined) { + value[x] = {}; + } else if (value[x] === null || typeof value[x] !== "object") { + return { + problem: { + type: "unexpected-non-object-in-path", + path: schemaPath + } + }; } - dep.loc = expr.loc; - parser.state.module.addPresentationalDependency(dep); - return true; + return { + object: value, + property: x, + value: value[x] + }; } } - processContext(parser, expr, param) { - const dep = ContextDependencyHelpers.create( - AMDRequireContextDependency, - param.range, - param, - expr, - this.options, - { - category: "amd" - }, - parser - ); - if (!dep) return; - dep.loc = expr.loc; - dep.optional = !!parser.scope.inTry; - parser.state.current.addDependency(dep); - return true; - } + return { object: current, property, value }; +}; - processArrayForRequestString(param) { - if (param.isArray()) { - const result = param.items.map(item => - this.processItemForRequestString(item) - ); - if (result.every(Boolean)) return result.join(" "); - } else if (param.isConstArray()) { - return param.array.join(" "); - } - } +/** + * @param {any} config configuration + * @param {string} schemaPath path in the config + * @param {any} value parsed value + * @param {number | undefined} index index of value when multiple values are provided, otherwise undefined + * @returns {LocalProblem | null} problem or null for success + */ +const setValue = (config, schemaPath, value, index) => { + const { problem, object, property } = getObjectAndProperty( + config, + schemaPath, + index + ); + if (problem) return problem; + object[property] = value; + return null; +}; - processItemForRequestString(param) { - if (param.isConditional()) { - const result = param.options.map(item => - this.processItemForRequestString(item) - ); - if (result.every(Boolean)) return result.join("|"); - } else if (param.isString()) { - return param.string; - } +/** + * @param {ArgumentConfig} argConfig processing instructions + * @param {any} config configuration + * @param {any} value the value + * @param {number | undefined} index the index if multiple values provided + * @returns {LocalProblem | null} a problem if any + */ +const processArgumentConfig = (argConfig, config, value, index) => { + if (index !== undefined && !argConfig.multiple) { + return { + type: "multiple-values-unexpected", + path: argConfig.path + }; } + const parsed = parseValueForArgumentConfig(argConfig, value); + if (parsed === undefined) { + return { + type: "invalid-value", + path: argConfig.path, + expected: getExpectedValue(argConfig) + }; + } + const problem = setValue(config, argConfig.path, parsed, index); + if (problem) return problem; + return null; +}; - processCallRequire(parser, expr) { - let param; - let depBlock; - let dep; - let result; - - const old = parser.state.current; - - if (expr.arguments.length >= 1) { - param = parser.evaluateExpression(expr.arguments[0]); - depBlock = this.newRequireDependenciesBlock( - expr.loc, - this.processArrayForRequestString(param) - ); - dep = this.newRequireDependency( - expr.range, - param.range, - expr.arguments.length > 1 ? expr.arguments[1].range : null, - expr.arguments.length > 2 ? expr.arguments[2].range : null - ); - dep.loc = expr.loc; - depBlock.addDependency(dep); +/** + * @param {ArgumentConfig} argConfig processing instructions + * @returns {string | undefined} expected message + */ +const getExpectedValue = argConfig => { + switch (argConfig.type) { + default: + return argConfig.type; + case "boolean": + return "true | false"; + case "RegExp": + return "regular expression (example: /ab?c*/)"; + case "enum": + return argConfig.values.map(v => `${v}`).join(" | "); + case "reset": + return "true (will reset the previous value to an empty array)"; + } +}; - parser.state.current = depBlock; - } +/** + * @param {ArgumentConfig} argConfig processing instructions + * @param {any} value the value + * @returns {any | undefined} parsed value + */ +const parseValueForArgumentConfig = (argConfig, value) => { + switch (argConfig.type) { + case "string": + if (typeof value === "string") { + return value; + } + break; + case "path": + if (typeof value === "string") { + return path.resolve(value); + } + break; + case "number": + if (typeof value === "number") return value; + if (typeof value === "string" && /^[+-]?\d*(\.\d*)[eE]\d+$/) { + const n = +value; + if (!isNaN(n)) return n; + } + break; + case "boolean": + if (typeof value === "boolean") return value; + if (value === "true") return true; + if (value === "false") return false; + break; + case "RegExp": + if (value instanceof RegExp) return value; + if (typeof value === "string") { + // cspell:word yugi + const match = /^\/(.*)\/([yugi]*)$/.exec(value); + if (match && !/[^\\]\//.test(match[1])) + return new RegExp(match[1], match[2]); + } + break; + case "enum": + if (argConfig.values.includes(value)) return value; + for (const item of argConfig.values) { + if (`${item}` === value) return item; + } + break; + case "reset": + if (value === true) return []; + break; + } +}; - if (expr.arguments.length === 1) { - parser.inScope([], () => { - result = this.processArray(parser, expr, param); +/** + * @param {Record} args object of arguments + * @param {any} config configuration + * @param {Record} values object with values + * @returns {Problem[] | null} problems or null for success + */ +const processArguments = (args, config, values) => { + /** @type {Problem[]} */ + const problems = []; + for (const key of Object.keys(values)) { + const arg = args[key]; + if (!arg) { + problems.push({ + type: "unknown-argument", + path: "", + argument: key }); - parser.state.current = old; - if (!result) return; - parser.state.current.addBlock(depBlock); - return true; + continue; } - - if (expr.arguments.length === 2 || expr.arguments.length === 3) { - try { - parser.inScope([], () => { - result = this.processArray(parser, expr, param); - }); - if (!result) { - const dep = new UnsupportedDependency("unsupported", expr.range); - old.addPresentationalDependency(dep); - if (parser.state.module) { - parser.state.module.addError( - new UnsupportedFeatureWarning( - "Cannot statically analyse 'require(…, …)' in line " + - expr.loc.start.line, - expr.loc - ) - ); - } - depBlock = null; - return true; - } - dep.functionBindThis = this.processFunctionArgument( - parser, - expr.arguments[1] - ); - if (expr.arguments.length === 3) { - dep.errorCallbackBindThis = this.processFunctionArgument( - parser, - expr.arguments[2] - ); + const processValue = (value, i) => { + const currentProblems = []; + for (const argConfig of arg.configs) { + const problem = processArgumentConfig(argConfig, config, value, i); + if (!problem) { + return; } - } finally { - parser.state.current = old; - if (depBlock) parser.state.current.addBlock(depBlock); + currentProblems.push({ + ...problem, + argument: key, + value: value, + index: i + }); } - return true; + problems.push(...currentProblems); + }; + let value = values[key]; + if (Array.isArray(value)) { + for (let i = 0; i < value.length; i++) { + processValue(value[i], i); + } + } else { + processValue(value, undefined); } } + if (problems.length === 0) return null; + return problems; +}; - newRequireDependenciesBlock(loc, request) { - return new AMDRequireDependenciesBlock(loc, request); - } - newRequireDependency( - outerRange, - arrayRange, - functionRange, - errorCallbackRange - ) { - return new AMDRequireDependency( - outerRange, - arrayRange, - functionRange, - errorCallbackRange - ); - } - newRequireItemDependency(request, range) { - return new AMDRequireItemDependency(request, range); - } - newRequireArrayDependency(depsArray, range) { - return new AMDRequireArrayDependency(depsArray, range); - } -} -module.exports = AMDRequireDependenciesBlockParserPlugin; +exports.getArguments = getArguments; +exports.processArguments = processArguments; /***/ }), -/***/ 11311: +/***/ 82852: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; /* MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra + Author Sergey Melyukov @smelukov */ -const RuntimeGlobals = __webpack_require__(49404); -const makeSerializable = __webpack_require__(26522); -const NullDependency = __webpack_require__(65845); +const browserslist = __webpack_require__(3561); +const path = __webpack_require__(85622); -/** @typedef {import("webpack-sources").ReplaceSource} ReplaceSource */ -/** @typedef {import("../AsyncDependenciesBlock")} AsyncDependenciesBlock */ -/** @typedef {import("../Dependency")} Dependency */ -/** @typedef {import("../DependencyTemplate").DependencyTemplateContext} DependencyTemplateContext */ +/** @typedef {import("./target").ApiTargetProperties} ApiTargetProperties */ +/** @typedef {import("./target").EcmaTargetProperties} EcmaTargetProperties */ +/** @typedef {import("./target").PlatformTargetProperties} PlatformTargetProperties */ -class AMDRequireDependency extends NullDependency { - constructor(outerRange, arrayRange, functionRange, errorCallbackRange) { - super(); +// [[C:]/path/to/config][:env] +const inputRx = /^(?:((?:[A-Z]:)?[/\\].*?))?(?::(.+?))?$/i; - this.outerRange = outerRange; - this.arrayRange = arrayRange; - this.functionRange = functionRange; - this.errorCallbackRange = errorCallbackRange; - this.functionBindThis = false; - this.errorCallbackBindThis = false; - } +/** + * @typedef {Object} BrowserslistHandlerConfig + * @property {string=} configPath + * @property {string=} env + * @property {string=} query + */ - get category() { - return "amd"; +/** + * @param {string} input input string + * @param {string} context the context directory + * @returns {BrowserslistHandlerConfig} config + */ +const parse = (input, context) => { + if (!input) { + return {}; } - serialize(context) { - const { write } = context; + if (path.isAbsolute(input)) { + const [, configPath, env] = inputRx.exec(input) || []; + return { configPath, env }; + } - write(this.outerRange); - write(this.arrayRange); - write(this.functionRange); - write(this.errorCallbackRange); - write(this.functionBindThis); - write(this.errorCallbackBindThis); + const config = browserslist.findConfig(context); - super.serialize(context); + if (config && Object.keys(config).includes(input)) { + return { env: input }; } - deserialize(context) { - const { read } = context; + return { query: input }; +}; - this.outerRange = read(); - this.arrayRange = read(); - this.functionRange = read(); - this.errorCallbackRange = read(); - this.functionBindThis = read(); - this.errorCallbackBindThis = read(); +/** + * @param {string} input input string + * @param {string} context the context directory + * @returns {string[] | undefined} selected browsers + */ +const load = (input, context) => { + const { configPath, env, query } = parse(input, context); - super.deserialize(context); - } -} + // if a query is specified, then use it, else + // if a path to a config is specified then load it, else + // find a nearest config + const config = query + ? query + : configPath + ? browserslist.loadConfig({ + config: configPath, + env + }) + : browserslist.loadConfig({ path: context, env }); -makeSerializable( - AMDRequireDependency, - "webpack/lib/dependencies/AMDRequireDependency" -); + if (!config) return null; + return browserslist(config); +}; -AMDRequireDependency.Template = class AMDRequireDependencyTemplate extends ( - NullDependency.Template -) { +/** + * @param {string[]} browsers supported browsers list + * @returns {EcmaTargetProperties & PlatformTargetProperties & ApiTargetProperties} target properties + */ +const resolve = browsers => { /** - * @param {Dependency} dependency the dependency for which the template should be applied - * @param {ReplaceSource} source the current replace source which can be modified - * @param {DependencyTemplateContext} templateContext the context object - * @returns {void} + * Checks all against a version number + * @param {Record} versions first supported version + * @returns {boolean} true if supports */ - apply( - dependency, - source, - { runtimeTemplate, moduleGraph, chunkGraph, runtimeRequirements } - ) { - const dep = /** @type {AMDRequireDependency} */ (dependency); - const depBlock = /** @type {AsyncDependenciesBlock} */ ( - moduleGraph.getParentBlock(dep) - ); - const promise = runtimeTemplate.blockPromise({ - chunkGraph, - block: depBlock, - message: "AMD require", - runtimeRequirements + const rawChecker = versions => { + return browsers.every(v => { + const [name, parsedVersion] = v.split(" "); + if (!name) return false; + const requiredVersion = versions[name]; + if (!requiredVersion) return false; + const [parsedMajor, parserMinor] = + // safari TP supports all features for normal safari + parsedVersion === "TP" + ? [Infinity, Infinity] + : parsedVersion.split("."); + if (typeof requiredVersion === "number") { + return +parsedMajor >= requiredVersion; + } + return requiredVersion[0] === +parsedMajor + ? +parserMinor >= requiredVersion[1] + : +parsedMajor > requiredVersion[0]; }); + }; + const anyNode = browsers.some(b => /^node /.test(b)); + const anyBrowser = browsers.some(b => /^(?!node)/.test(b)); + const browserProperty = !anyBrowser ? false : anyNode ? null : true; + const nodeProperty = !anyNode ? false : anyBrowser ? null : true; + // Internet Explorer Mobile, Blackberry browser and Opera Mini are very old browsers, they do not support new features + const es6DynamicImport = rawChecker({ + chrome: 63, + and_chr: 63, + edge: 79, + firefox: 67, + and_ff: 67, + // ie: Not supported + opera: 50, + op_mob: 46, + safari: [11, 1], + ios_saf: [11, 3], + samsung: [8, 2], + android: 63, + and_qq: [10, 4], + // baidu: Not supported + // and_uc: Not supported + // kaios: Not supported + // Since Node.js 13.14.0 no warning about usage, but it was added 8.5.0 with some limitations and it was improved in 12.0.0 and 13.2.0 + node: [13, 14] + }); - // has array range but no function range - if (dep.arrayRange && !dep.functionRange) { - const startBlock = `${promise}.then(function() {`; - const endBlock = `;})['catch'](${RuntimeGlobals.uncaughtErrorHandler})`; - runtimeRequirements.add(RuntimeGlobals.uncaughtErrorHandler); + return { + const: rawChecker({ + chrome: 49, + and_chr: 49, + edge: 12, + // Prior to Firefox 13, const is implemented, but re-assignment is not failing. + // Prior to Firefox 46, a TypeError was thrown on redeclaration instead of a SyntaxError. + firefox: 36, + and_ff: 36, + // Not supported in for-in and for-of loops + // ie: Not supported + opera: 36, + op_mob: 36, + safari: [10, 0], + ios_saf: [10, 0], + // Before 5.0 supported correctly in strict mode, otherwise supported without block scope + samsung: [5, 0], + android: 37, + and_qq: [10, 4], + // Supported correctly in strict mode, otherwise supported without block scope + // baidu: Not supported + and_uc: [12, 12], + kaios: [2, 5], + node: [6, 0] + }), + arrowFunction: rawChecker({ + chrome: 45, + and_chr: 45, + edge: 12, + // The initial implementation of arrow functions in Firefox made them automatically strict. This has been changed as of Firefox 24. The use of 'use strict'; is now required. + // Prior to Firefox 39, a line terminator (\\n) was incorrectly allowed after arrow function arguments. This has been fixed to conform to the ES2015 specification and code like () \\n => {} will now throw a SyntaxError in this and later versions. + firefox: 39, + and_ff: 39, + // ie: Not supported, + opera: 32, + op_mob: 32, + safari: 10, + ios_saf: 10, + samsung: [5, 0], + android: 45, + and_qq: [10, 4], + baidu: [7, 12], + and_uc: [12, 12], + kaios: [2, 5], + node: [6, 0] + }), + forOf: rawChecker({ + chrome: 38, + and_chr: 38, + edge: 12, + // Prior to Firefox 51, using the for...of loop construct with the const keyword threw a SyntaxError ("missing = in const declaration"). + firefox: 51, + and_ff: 51, + // ie: Not supported, + opera: 25, + op_mob: 25, + safari: 7, + ios_saf: 7, + samsung: [3, 0], + android: 38, + // and_qq: Unknown support + // baidu: Unknown support + // and_uc: Unknown support + // kaios: Unknown support + node: [0, 12] + }), + destructuring: rawChecker({ + chrome: 49, + and_chr: 49, + edge: 14, + firefox: 41, + and_ff: 41, + // ie: Not supported, + opera: 36, + op_mob: 36, + safari: 8, + ios_saf: 8, + samsung: [5, 0], + android: 49, + // and_qq: Unknown support + // baidu: Unknown support + // and_uc: Unknown support + // kaios: Unknown support + node: [6, 0] + }), + bigIntLiteral: rawChecker({ + chrome: 67, + and_chr: 67, + edge: 79, + firefox: 68, + and_ff: 68, + // ie: Not supported, + opera: 54, + op_mob: 48, + safari: 14, + ios_saf: 14, + samsung: [9, 2], + android: 67, + // and_qq: Not supported + // baidu: Not supported + // and_uc: Not supported + // kaios: Not supported + node: [10, 4] + }), + // Support syntax `import` and `export` and no limitations and bugs on Node.js + // Not include `export * as namespace` + module: rawChecker({ + chrome: 61, + and_chr: 61, + edge: 16, + firefox: 60, + and_ff: 60, + // ie: Not supported, + opera: 48, + op_mob: 45, + safari: [10, 1], + ios_saf: [10, 3], + samsung: [8, 0], + android: 61, + and_qq: [10, 4], + // baidu: Not supported + // and_uc: Not supported + // kaios: Not supported + // Since Node.js 13.14.0 no warning about usage, but it was added 8.5.0 with some limitations and it was improved in 12.0.0 and 13.2.0 + node: [13, 14] + }), + dynamicImport: es6DynamicImport, + dynamicImportInWorker: es6DynamicImport && !anyNode, + // browserslist does not have info about globalThis + // so this is based on mdn-browser-compat-data + globalThis: rawChecker({ + chrome: 71, + and_chr: 71, + edge: 79, + firefox: 65, + and_ff: 65, + // ie: Not supported, + opera: 58, + op_mob: 50, + safari: [12, 1], + ios_saf: [12, 2], + samsung: [10, 1], + android: 71, + // and_qq: Unknown support + // baidu: Unknown support + // and_uc: Unknown support + // kaios: Unknown support + node: [12, 0] + }), - source.replace(dep.outerRange[0], dep.arrayRange[0] - 1, startBlock); + browser: browserProperty, + electron: false, + node: nodeProperty, + nwjs: false, + web: browserProperty, + webworker: false, - source.replace(dep.arrayRange[1], dep.outerRange[1] - 1, endBlock); + document: browserProperty, + fetchWasm: browserProperty, + global: nodeProperty, + importScripts: false, + importScriptsInWorker: true, + nodeBuiltins: nodeProperty, + require: nodeProperty + }; +}; - return; - } +module.exports = { + resolve, + load +}; - // has function range but no array range - if (dep.functionRange && !dep.arrayRange) { - const startBlock = `${promise}.then((`; - const endBlock = `).bind(exports, __webpack_require__, exports, module))['catch'](${RuntimeGlobals.uncaughtErrorHandler})`; - runtimeRequirements.add(RuntimeGlobals.uncaughtErrorHandler); - source.replace(dep.outerRange[0], dep.functionRange[0] - 1, startBlock); +/***/ }), - source.replace(dep.functionRange[1], dep.outerRange[1] - 1, endBlock); +/***/ 27057: +/***/ (function(__unused_webpack_module, exports, __webpack_require__) { - return; +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ + + + +const fs = __webpack_require__(35747); +const path = __webpack_require__(85622); +const Template = __webpack_require__(92066); +const { cleverMerge } = __webpack_require__(11217); +const { + getTargetsProperties, + getTargetProperties, + getDefaultTarget +} = __webpack_require__(23451); + +/** @typedef {import("../../declarations/WebpackOptions").CacheOptionsNormalized} CacheOptions */ +/** @typedef {import("../../declarations/WebpackOptions").EntryDescription} EntryDescription */ +/** @typedef {import("../../declarations/WebpackOptions").EntryNormalized} Entry */ +/** @typedef {import("../../declarations/WebpackOptions").Experiments} Experiments */ +/** @typedef {import("../../declarations/WebpackOptions").ExperimentsNormalized} ExperimentsNormalized */ +/** @typedef {import("../../declarations/WebpackOptions").ExternalsPresets} ExternalsPresets */ +/** @typedef {import("../../declarations/WebpackOptions").ExternalsType} ExternalsType */ +/** @typedef {import("../../declarations/WebpackOptions").InfrastructureLogging} InfrastructureLogging */ +/** @typedef {import("../../declarations/WebpackOptions").JavascriptParserOptions} JavascriptParserOptions */ +/** @typedef {import("../../declarations/WebpackOptions").Library} Library */ +/** @typedef {import("../../declarations/WebpackOptions").LibraryName} LibraryName */ +/** @typedef {import("../../declarations/WebpackOptions").LibraryOptions} LibraryOptions */ +/** @typedef {import("../../declarations/WebpackOptions").Loader} Loader */ +/** @typedef {import("../../declarations/WebpackOptions").Mode} Mode */ +/** @typedef {import("../../declarations/WebpackOptions").ModuleOptionsNormalized} ModuleOptions */ +/** @typedef {import("../../declarations/WebpackOptions").Node} WebpackNode */ +/** @typedef {import("../../declarations/WebpackOptions").Optimization} Optimization */ +/** @typedef {import("../../declarations/WebpackOptions").OutputNormalized} Output */ +/** @typedef {import("../../declarations/WebpackOptions").Performance} Performance */ +/** @typedef {import("../../declarations/WebpackOptions").ResolveOptions} ResolveOptions */ +/** @typedef {import("../../declarations/WebpackOptions").RuleSetRules} RuleSetRules */ +/** @typedef {import("../../declarations/WebpackOptions").SnapshotOptions} SnapshotOptions */ +/** @typedef {import("../../declarations/WebpackOptions").Target} Target */ +/** @typedef {import("../../declarations/WebpackOptions").WebpackOptionsNormalized} WebpackOptions */ +/** @typedef {import("./target").TargetProperties} TargetProperties */ + +const NODE_MODULES_REGEXP = /[\\/]node_modules[\\/]/i; + +/** + * Sets a constant default value when undefined + * @template T + * @template {keyof T} P + * @param {T} obj an object + * @param {P} prop a property of this object + * @param {T[P]} value a default value of the property + * @returns {void} + */ +const D = (obj, prop, value) => { + if (obj[prop] === undefined) { + obj[prop] = value; + } +}; + +/** + * Sets a dynamic default value when undefined, by calling the factory function + * @template T + * @template {keyof T} P + * @param {T} obj an object + * @param {P} prop a property of this object + * @param {function(): T[P]} factory a default value factory for the property + * @returns {void} + */ +const F = (obj, prop, factory) => { + if (obj[prop] === undefined) { + obj[prop] = factory(); + } +}; + +/** + * Sets a dynamic default value when undefined, by calling the factory function. + * factory must return an array or undefined + * When the current value is already an array an contains "..." it's replaced with + * the result of the factory function + * @template T + * @template {keyof T} P + * @param {T} obj an object + * @param {P} prop a property of this object + * @param {function(): T[P]} factory a default value factory for the property + * @returns {void} + */ +const A = (obj, prop, factory) => { + const value = obj[prop]; + if (value === undefined) { + obj[prop] = factory(); + } else if (Array.isArray(value)) { + /** @type {any[]} */ + let newArray = undefined; + for (let i = 0; i < value.length; i++) { + const item = value[i]; + if (item === "...") { + if (newArray === undefined) { + newArray = value.slice(0, i); + obj[prop] = /** @type {T[P]} */ (/** @type {unknown} */ (newArray)); + } + const items = /** @type {any[]} */ (/** @type {unknown} */ (factory())); + if (items !== undefined) { + for (const item of items) { + newArray.push(item); + } + } + } else if (newArray !== undefined) { + newArray.push(item); + } } + } +}; - // has array range, function range, and errorCallbackRange - if (dep.arrayRange && dep.functionRange && dep.errorCallbackRange) { - const startBlock = `${promise}.then(function() { `; - const errorRangeBlock = `}${ - dep.functionBindThis ? ".bind(this)" : "" - })['catch'](`; - const endBlock = `${dep.errorCallbackBindThis ? ".bind(this)" : ""})`; - - source.replace(dep.outerRange[0], dep.arrayRange[0] - 1, startBlock); +/** + * @param {WebpackOptions} options options to be modified + * @returns {void} + */ +const applyWebpackOptionsBaseDefaults = options => { + F(options, "context", () => process.cwd()); + applyInfrastructureLoggingDefaults(options.infrastructureLogging); +}; - source.insert(dep.arrayRange[0], "var __WEBPACK_AMD_REQUIRE_ARRAY__ = "); +/** + * @param {WebpackOptions} options options to be modified + * @returns {void} + */ +const applyWebpackOptionsDefaults = options => { + F(options, "context", () => process.cwd()); + F(options, "target", () => { + return getDefaultTarget(options.context); + }); - source.replace(dep.arrayRange[1], dep.functionRange[0] - 1, "; ("); + const { mode, name, target } = options; - source.insert( - dep.functionRange[1], - ").apply(null, __WEBPACK_AMD_REQUIRE_ARRAY__);" - ); + let targetProperties = + target === false + ? /** @type {false} */ (false) + : typeof target === "string" + ? getTargetProperties(target, options.context) + : getTargetsProperties(target, options.context); - source.replace( - dep.functionRange[1], - dep.errorCallbackRange[0] - 1, - errorRangeBlock - ); + const development = mode === "development"; + const production = mode === "production" || !mode; - source.replace( - dep.errorCallbackRange[1], - dep.outerRange[1] - 1, - endBlock + if (typeof options.entry !== "function") { + for (const key of Object.keys(options.entry)) { + F( + options.entry[key], + "import", + () => /** @type {[string]} */ (["./src"]) ); - - return; } + } - // has array range, function range, but no errorCallbackRange - if (dep.arrayRange && dep.functionRange) { - const startBlock = `${promise}.then(function() { `; - const endBlock = `}${ - dep.functionBindThis ? ".bind(this)" : "" - })['catch'](${RuntimeGlobals.uncaughtErrorHandler})`; - runtimeRequirements.add(RuntimeGlobals.uncaughtErrorHandler); + F(options, "devtool", () => (development ? "eval" : false)); + D(options, "watch", false); + D(options, "profile", false); + D(options, "parallelism", 100); + D(options, "recordsInputPath", false); + D(options, "recordsOutputPath", false); - source.replace(dep.outerRange[0], dep.arrayRange[0] - 1, startBlock); + applyExperimentsDefaults(options.experiments, { production, development }); - source.insert(dep.arrayRange[0], "var __WEBPACK_AMD_REQUIRE_ARRAY__ = "); + const futureDefaults = options.experiments.futureDefaults; - source.replace(dep.arrayRange[1], dep.functionRange[0] - 1, "; ("); + F(options, "cache", () => + development ? { type: /** @type {"memory"} */ ("memory") } : false + ); + applyCacheDefaults(options.cache, { + name: name || "default", + mode: mode || "production", + development, + cacheUnaffected: options.experiments.cacheUnaffected + }); + const cache = !!options.cache; - source.insert( - dep.functionRange[1], - ").apply(null, __WEBPACK_AMD_REQUIRE_ARRAY__);" - ); + applySnapshotDefaults(options.snapshot, { + production, + futureDefaults + }); - source.replace(dep.functionRange[1], dep.outerRange[1] - 1, endBlock); - } - } -}; + applyModuleDefaults(options.module, { + cache, + syncWebAssembly: options.experiments.syncWebAssembly, + asyncWebAssembly: options.experiments.asyncWebAssembly, + futureDefaults + }); -module.exports = AMDRequireDependency; + applyOutputDefaults(options.output, { + context: options.context, + targetProperties, + isAffectedByBrowserslist: + target === undefined || + (typeof target === "string" && target.startsWith("browserslist")) || + (Array.isArray(target) && + target.some(target => target.startsWith("browserslist"))), + outputModule: options.experiments.outputModule, + development, + entry: options.entry, + module: options.module, + futureDefaults + }); + applyExternalsPresetsDefaults(options.externalsPresets, { + targetProperties, + buildHttp: !!options.experiments.buildHttp + }); -/***/ }), + applyLoaderDefaults(options.loader, { targetProperties }); -/***/ 90377: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + F(options, "externalsType", () => { + const validExternalTypes = __webpack_require__(1863).definitions.ExternalsType.enum; + return options.output.library && + validExternalTypes.includes(options.output.library.type) + ? /** @type {ExternalsType} */ (options.output.library.type) + : options.output.module + ? "module" + : "var"; + }); -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ + applyNodeDefaults(options.node, { + futureDefaults: options.experiments.futureDefaults, + targetProperties + }); + F(options, "performance", () => + production && + targetProperties && + (targetProperties.browser || targetProperties.browser === null) + ? {} + : false + ); + applyPerformanceDefaults(options.performance, { + production + }); + applyOptimizationDefaults(options.optimization, { + development, + production, + records: !!(options.recordsInputPath || options.recordsOutputPath) + }); -const makeSerializable = __webpack_require__(26522); -const ModuleDependency = __webpack_require__(80944); -const ModuleDependencyTemplateAsRequireId = __webpack_require__(77802); + options.resolve = cleverMerge( + getResolveDefaults({ + cache, + context: options.context, + targetProperties, + mode: options.mode + }), + options.resolve + ); -class AMDRequireItemDependency extends ModuleDependency { - constructor(request, range) { - super(request); + options.resolveLoader = cleverMerge( + getResolveLoaderDefaults({ cache }), + options.resolveLoader + ); +}; - this.range = range; - } +/** + * @param {ExperimentsNormalized} experiments options + * @param {Object} options options + * @param {boolean} options.production is production + * @param {boolean} options.development is development mode + * @returns {void} + */ +const applyExperimentsDefaults = (experiments, { production, development }) => { + D(experiments, "futureDefaults", false); + D(experiments, "backCompat", !experiments.futureDefaults); + D(experiments, "topLevelAwait", experiments.futureDefaults); + D(experiments, "syncWebAssembly", false); + D(experiments, "asyncWebAssembly", experiments.futureDefaults); + D(experiments, "outputModule", false); + D(experiments, "layers", false); + D(experiments, "lazyCompilation", undefined); + D(experiments, "buildHttp", undefined); + D(experiments, "cacheUnaffected", experiments.futureDefaults); - get type() { - return "amd require"; + if (typeof experiments.buildHttp === "object") { + D(experiments.buildHttp, "frozen", production); + D(experiments.buildHttp, "upgrade", false); } +}; - get category() { - return "amd"; +/** + * @param {CacheOptions} cache options + * @param {Object} options options + * @param {string} options.name name + * @param {string} options.mode mode + * @param {boolean} options.development is development mode + * @param {boolean} options.cacheUnaffected the cacheUnaffected experiment is enabled + * @returns {void} + */ +const applyCacheDefaults = ( + cache, + { name, mode, development, cacheUnaffected } +) => { + if (cache === false) return; + switch (cache.type) { + case "filesystem": + F(cache, "name", () => name + "-" + mode); + D(cache, "version", ""); + F(cache, "cacheDirectory", () => { + const cwd = process.cwd(); + let dir = cwd; + for (;;) { + try { + if (fs.statSync(path.join(dir, "package.json")).isFile()) break; + // eslint-disable-next-line no-empty + } catch (e) {} + const parent = path.dirname(dir); + if (dir === parent) { + dir = undefined; + break; + } + dir = parent; + } + if (!dir) { + return path.resolve(cwd, ".cache/webpack"); + } else if (process.versions.pnp === "1") { + return path.resolve(dir, ".pnp/.cache/webpack"); + } else if (process.versions.pnp === "3") { + return path.resolve(dir, ".yarn/.cache/webpack"); + } else { + return path.resolve(dir, "node_modules/.cache/webpack"); + } + }); + F(cache, "cacheLocation", () => + path.resolve(cache.cacheDirectory, cache.name) + ); + D(cache, "hashAlgorithm", "md4"); + D(cache, "store", "pack"); + D(cache, "compression", false); + D(cache, "profile", false); + D(cache, "idleTimeout", 60000); + D(cache, "idleTimeoutForInitialStore", 5000); + D(cache, "idleTimeoutAfterLargeChanges", 1000); + D(cache, "maxMemoryGenerations", development ? 5 : Infinity); + D(cache, "maxAge", 1000 * 60 * 60 * 24 * 60); // 1 month + D(cache, "allowCollectingMemory", development); + D(cache, "memoryCacheUnaffected", development && cacheUnaffected); + D(cache.buildDependencies, "defaultWebpack", [ + path.resolve(__dirname, "..") + path.sep + ]); + break; + case "memory": + D(cache, "maxGenerations", Infinity); + D(cache, "cacheUnaffected", development && cacheUnaffected); + break; } -} - -makeSerializable( - AMDRequireItemDependency, - "webpack/lib/dependencies/AMDRequireItemDependency" -); - -AMDRequireItemDependency.Template = ModuleDependencyTemplateAsRequireId; - -module.exports = AMDRequireItemDependency; - +}; -/***/ }), +/** + * @param {SnapshotOptions} snapshot options + * @param {Object} options options + * @param {boolean} options.production is production + * @param {boolean} options.futureDefaults is future defaults enabled + * @returns {void} + */ +const applySnapshotDefaults = (snapshot, { production, futureDefaults }) => { + if (futureDefaults) { + F(snapshot, "managedPaths", () => + process.versions.pnp === "3" + ? [ + /^(.+?(?:[\\/]\.yarn[\\/]unplugged[\\/][^\\/]+)?[\\/]node_modules[\\/])/ + ] + : [/^(.+?[\\/]node_modules[\\/])/] + ); + F(snapshot, "immutablePaths", () => + process.versions.pnp === "3" + ? [/^(.+?[\\/]cache[\\/][^\\/]+\.zip[\\/]node_modules[\\/])/] + : [] + ); + } else { + A(snapshot, "managedPaths", () => { + if (process.versions.pnp === "3") { + const match = + /^(.+?)[\\/]cache[\\/]watchpack-npm-[^\\/]+\.zip[\\/]node_modules[\\/]/.exec( + /*require.resolve*/(29149) + ); + if (match) { + return [path.resolve(match[1], "unplugged")]; + } + } else { + const match = /^(.+?[\\/]node_modules[\\/])/.exec( + // eslint-disable-next-line node/no-extraneous-require + /*require.resolve*/(29149) + ); + if (match) { + return [match[1]]; + } + } + return []; + }); + A(snapshot, "immutablePaths", () => { + if (process.versions.pnp === "1") { + const match = + /^(.+?[\\/]v4)[\\/]npm-watchpack-[^\\/]+-[\da-f]{40}[\\/]node_modules[\\/]/.exec( + /*require.resolve*/(29149) + ); + if (match) { + return [match[1]]; + } + } else if (process.versions.pnp === "3") { + const match = + /^(.+?)[\\/]watchpack-npm-[^\\/]+\.zip[\\/]node_modules[\\/]/.exec( + /*require.resolve*/(29149) + ); + if (match) { + return [match[1]]; + } + } + return []; + }); + } + F(snapshot, "resolveBuildDependencies", () => ({ + timestamp: true, + hash: true + })); + F(snapshot, "buildDependencies", () => ({ timestamp: true, hash: true })); + F(snapshot, "module", () => + production ? { timestamp: true, hash: true } : { timestamp: true } + ); + F(snapshot, "resolve", () => + production ? { timestamp: true, hash: true } : { timestamp: true } + ); +}; -/***/ 35469: -/***/ (function(__unused_webpack_module, exports, __webpack_require__) { +/** + * @param {JavascriptParserOptions} parserOptions parser options + * @param {Object} options options + * @param {boolean} options.futureDefaults is future defaults enabled + * @returns {void} + */ +const applyJavascriptParserOptionsDefaults = ( + parserOptions, + { futureDefaults } +) => { + D(parserOptions, "unknownContextRequest", "."); + D(parserOptions, "unknownContextRegExp", false); + D(parserOptions, "unknownContextRecursive", true); + D(parserOptions, "unknownContextCritical", true); + D(parserOptions, "exprContextRequest", "."); + D(parserOptions, "exprContextRegExp", false); + D(parserOptions, "exprContextRecursive", true); + D(parserOptions, "exprContextCritical", true); + D(parserOptions, "wrappedContextRegExp", /.*/); + D(parserOptions, "wrappedContextRecursive", true); + D(parserOptions, "wrappedContextCritical", false); + D(parserOptions, "strictThisContextOnImports", false); + if (futureDefaults) D(parserOptions, "exportsPresence", "error"); +}; -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php -*/ +/** + * @param {ModuleOptions} module options + * @param {Object} options options + * @param {boolean} options.cache is caching enabled + * @param {boolean} options.syncWebAssembly is syncWebAssembly enabled + * @param {boolean} options.asyncWebAssembly is asyncWebAssembly enabled + * @param {boolean} options.futureDefaults is future defaults enabled + * @returns {void} + */ +const applyModuleDefaults = ( + module, + { cache, syncWebAssembly, asyncWebAssembly, futureDefaults } +) => { + if (cache) { + D(module, "unsafeCache", module => { + const name = module.nameForCondition(); + return name && NODE_MODULES_REGEXP.test(name); + }); + } else { + D(module, "unsafeCache", false); + } + F(module.parser, "asset", () => ({})); + F(module.parser.asset, "dataUrlCondition", () => ({})); + if (typeof module.parser.asset.dataUrlCondition === "object") { + D(module.parser.asset.dataUrlCondition, "maxSize", 8096); + } + F(module.parser, "javascript", () => ({})); + applyJavascriptParserOptionsDefaults(module.parser.javascript, { + futureDefaults + }); -const RuntimeGlobals = __webpack_require__(49404); -const RuntimeModule = __webpack_require__(61439); -const Template = __webpack_require__(92066); + A(module, "defaultRules", () => { + const esm = { + type: "javascript/esm", + resolve: { + byDependency: { + esm: { + fullySpecified: true + } + } + } + }; + const commonjs = { + type: "javascript/dynamic" + }; + /** @type {RuleSetRules} */ + const rules = [ + { + mimetype: "application/node", + type: "javascript/auto" + }, + { + test: /\.json$/i, + type: "json" + }, + { + mimetype: "application/json", + type: "json" + }, + { + test: /\.mjs$/i, + ...esm + }, + { + test: /\.js$/i, + descriptionData: { + type: "module" + }, + ...esm + }, + { + test: /\.cjs$/i, + ...commonjs + }, + { + test: /\.js$/i, + descriptionData: { + type: "commonjs" + }, + ...commonjs + }, + { + mimetype: { + or: ["text/javascript", "application/javascript"] + }, + ...esm + } + ]; + if (asyncWebAssembly) { + const wasm = { + type: "webassembly/async", + rules: [ + { + descriptionData: { + type: "module" + }, + resolve: { + fullySpecified: true + } + } + ] + }; + rules.push({ + test: /\.wasm$/i, + ...wasm + }); + rules.push({ + mimetype: "application/wasm", + ...wasm + }); + } else if (syncWebAssembly) { + const wasm = { + type: "webassembly/sync", + rules: [ + { + descriptionData: { + type: "module" + }, + resolve: { + fullySpecified: true + } + } + ] + }; + rules.push({ + test: /\.wasm$/i, + ...wasm + }); + rules.push({ + mimetype: "application/wasm", + ...wasm + }); + } + rules.push( + { + dependency: "url", + oneOf: [ + { + scheme: /^data$/, + type: "asset/inline" + }, + { + type: "asset/resource" + } + ] + }, + { + assert: { type: "json" }, + type: "json" + } + ); + return rules; + }); +}; -class AMDDefineRuntimeModule extends RuntimeModule { - constructor() { - super("amd define"); +/** + * @param {Output} output options + * @param {Object} options options + * @param {string} options.context context + * @param {TargetProperties | false} options.targetProperties target properties + * @param {boolean} options.isAffectedByBrowserslist is affected by browserslist + * @param {boolean} options.outputModule is outputModule experiment enabled + * @param {boolean} options.development is development mode + * @param {Entry} options.entry entry option + * @param {ModuleOptions} options.module module option + * @param {boolean} options.futureDefaults is future defaults enabled + * @returns {void} + */ +const applyOutputDefaults = ( + output, + { + context, + targetProperties: tp, + isAffectedByBrowserslist, + outputModule, + development, + entry, + module, + futureDefaults } - +) => { /** - * @returns {string} runtime code + * @param {Library=} library the library option + * @returns {string} a readable library name */ - generate() { - return Template.asString([ - `${RuntimeGlobals.amdDefine} = function () {`, - Template.indent("throw new Error('define cannot be used indirect');"), - "};" - ]); - } -} + const getLibraryName = library => { + const libraryName = + typeof library === "object" && + library && + !Array.isArray(library) && + "type" in library + ? library.name + : /** @type {LibraryName=} */ (library); + if (Array.isArray(libraryName)) { + return libraryName.join("."); + } else if (typeof libraryName === "object") { + return getLibraryName(libraryName.root); + } else if (typeof libraryName === "string") { + return libraryName; + } + return ""; + }; -class AMDOptionsRuntimeModule extends RuntimeModule { - /** - * @param {Record} options the AMD options - */ - constructor(options) { - super("amd options"); - this.options = options; - } + F(output, "uniqueName", () => { + const libraryName = getLibraryName(output.library); + if (libraryName) return libraryName; + const pkgPath = path.resolve(context, "package.json"); + try { + const packageInfo = JSON.parse(fs.readFileSync(pkgPath, "utf-8")); + return packageInfo.name || ""; + } catch (e) { + if (e.code !== "ENOENT") { + e.message += `\nwhile determining default 'output.uniqueName' from 'name' in ${pkgPath}`; + throw e; + } + return ""; + } + }); - /** - * @returns {string} runtime code - */ - generate() { - return Template.asString([ - `${RuntimeGlobals.amdOptions} = ${JSON.stringify(this.options)};` - ]); + F(output, "module", () => !!outputModule); + D(output, "filename", output.module ? "[name].mjs" : "[name].js"); + F(output, "iife", () => !output.module); + D(output, "importFunctionName", "import"); + D(output, "importMetaName", "import.meta"); + F(output, "chunkFilename", () => { + const filename = output.filename; + if (typeof filename !== "function") { + const hasName = filename.includes("[name]"); + const hasId = filename.includes("[id]"); + const hasChunkHash = filename.includes("[chunkhash]"); + const hasContentHash = filename.includes("[contenthash]"); + // Anything changing depending on chunk is fine + if (hasChunkHash || hasContentHash || hasName || hasId) return filename; + // Otherwise prefix "[id]." in front of the basename to make it changing + return filename.replace(/(^|\/)([^/]*(?:\?|$))/, "$1[id].$2"); + } + return output.module ? "[id].mjs" : "[id].js"; + }); + D(output, "assetModuleFilename", "[hash][ext][query]"); + D(output, "webassemblyModuleFilename", "[hash].module.wasm"); + D(output, "compareBeforeEmit", true); + D(output, "charset", true); + F(output, "hotUpdateGlobal", () => + Template.toIdentifier( + "webpackHotUpdate" + Template.toIdentifier(output.uniqueName) + ) + ); + F(output, "chunkLoadingGlobal", () => + Template.toIdentifier( + "webpackChunk" + Template.toIdentifier(output.uniqueName) + ) + ); + F(output, "globalObject", () => { + if (tp) { + if (tp.global) return "global"; + if (tp.globalThis) return "globalThis"; + } + return "self"; + }); + F(output, "chunkFormat", () => { + if (tp) { + const helpMessage = isAffectedByBrowserslist + ? "Make sure that your 'browserslist' includes only platforms that support these features or select an appropriate 'target' to allow selecting a chunk format by default. Alternatively specify the 'output.chunkFormat' directly." + : "Select an appropriate 'target' to allow selecting one by default, or specify the 'output.chunkFormat' directly."; + if (output.module) { + if (tp.dynamicImport) return "module"; + if (tp.document) return "array-push"; + throw new Error( + "For the selected environment is no default ESM chunk format available:\n" + + "ESM exports can be chosen when 'import()' is available.\n" + + "JSONP Array push can be chosen when 'document' is available.\n" + + helpMessage + ); + } else { + if (tp.document) return "array-push"; + if (tp.require) return "commonjs"; + if (tp.nodeBuiltins) return "commonjs"; + if (tp.importScripts) return "array-push"; + throw new Error( + "For the selected environment is no default script chunk format available:\n" + + "JSONP Array push can be chosen when 'document' or 'importScripts' is available.\n" + + "CommonJs exports can be chosen when 'require' or node builtins are available.\n" + + helpMessage + ); + } + } + throw new Error( + "Chunk format can't be selected by default when no target is specified" + ); + }); + D(output, "asyncChunks", true); + F(output, "chunkLoading", () => { + if (tp) { + switch (output.chunkFormat) { + case "array-push": + if (tp.document) return "jsonp"; + if (tp.importScripts) return "import-scripts"; + break; + case "commonjs": + if (tp.require) return "require"; + if (tp.nodeBuiltins) return "async-node"; + break; + case "module": + if (tp.dynamicImport) return "import"; + break; + } + if ( + tp.require === null || + tp.nodeBuiltins === null || + tp.document === null || + tp.importScripts === null + ) { + return "universal"; + } + } + return false; + }); + F(output, "workerChunkLoading", () => { + if (tp) { + switch (output.chunkFormat) { + case "array-push": + if (tp.importScriptsInWorker) return "import-scripts"; + break; + case "commonjs": + if (tp.require) return "require"; + if (tp.nodeBuiltins) return "async-node"; + break; + case "module": + if (tp.dynamicImportInWorker) return "import"; + break; + } + if ( + tp.require === null || + tp.nodeBuiltins === null || + tp.importScriptsInWorker === null + ) { + return "universal"; + } + } + return false; + }); + F(output, "wasmLoading", () => { + if (tp) { + if (tp.fetchWasm) return "fetch"; + if (tp.nodeBuiltins) + return output.module ? "async-node-module" : "async-node"; + if (tp.nodeBuiltins === null || tp.fetchWasm === null) { + return "universal"; + } + } + return false; + }); + F(output, "workerWasmLoading", () => output.wasmLoading); + F(output, "devtoolNamespace", () => output.uniqueName); + if (output.library) { + F(output.library, "type", () => (output.module ? "module" : "var")); } -} - -exports.AMDDefineRuntimeModule = AMDDefineRuntimeModule; -exports.AMDOptionsRuntimeModule = AMDOptionsRuntimeModule; - - -/***/ }), - -/***/ 64177: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Florent Cailhol @ooflorent -*/ - - - -const DependencyTemplate = __webpack_require__(17600); -const InitFragment = __webpack_require__(51739); -const makeSerializable = __webpack_require__(26522); -const NullDependency = __webpack_require__(65845); - -/** @typedef {import("webpack-sources").ReplaceSource} ReplaceSource */ -/** @typedef {import("../ChunkGraph")} ChunkGraph */ -/** @typedef {import("../Dependency")} Dependency */ -/** @typedef {import("../Dependency").UpdateHashContext} UpdateHashContext */ -/** @typedef {import("../DependencyTemplate").DependencyTemplateContext} DependencyTemplateContext */ -/** @typedef {import("../DependencyTemplates")} DependencyTemplates */ -/** @typedef {import("../ModuleGraph")} ModuleGraph */ -/** @typedef {import("../RuntimeTemplate")} RuntimeTemplate */ -/** @typedef {import("../util/Hash")} Hash */ + F(output, "path", () => path.join(process.cwd(), "dist")); + F(output, "pathinfo", () => development); + D(output, "sourceMapFilename", "[file].map[query]"); + D( + output, + "hotUpdateChunkFilename", + `[id].[fullhash].hot-update.${output.module ? "mjs" : "js"}` + ); + D(output, "hotUpdateMainFilename", "[runtime].[fullhash].hot-update.json"); + D(output, "crossOriginLoading", false); + F(output, "scriptType", () => (output.module ? "module" : false)); + D( + output, + "publicPath", + (tp && (tp.document || tp.importScripts)) || output.scriptType === "module" + ? "auto" + : "" + ); + D(output, "chunkLoadTimeout", 120000); + D(output, "hashFunction", futureDefaults ? "xxhash64" : "md4"); + D(output, "hashDigest", "hex"); + D(output, "hashDigestLength", 20); + D(output, "strictModuleExceptionHandling", false); -class CachedConstDependency extends NullDependency { - constructor(expression, range, identifier) { - super(); + const optimistic = v => v || v === undefined; + F( + output.environment, + "arrowFunction", + () => tp && optimistic(tp.arrowFunction) + ); + F(output.environment, "const", () => tp && optimistic(tp.const)); + F( + output.environment, + "destructuring", + () => tp && optimistic(tp.destructuring) + ); + F(output.environment, "forOf", () => tp && optimistic(tp.forOf)); + F(output.environment, "bigIntLiteral", () => tp && tp.bigIntLiteral); + F(output.environment, "dynamicImport", () => tp && tp.dynamicImport); + F(output.environment, "module", () => tp && tp.module); - this.expression = expression; - this.range = range; - this.identifier = identifier; - this._hashUpdate = undefined; + const { trustedTypes } = output; + if (trustedTypes) { + F( + trustedTypes, + "policyName", + () => + output.uniqueName.replace(/[^a-zA-Z0-9\-#=_/@.%]+/g, "_") || "webpack" + ); } /** - * Update the hash - * @param {Hash} hash hash to be updated - * @param {UpdateHashContext} context context + * @param {function(EntryDescription): void} fn iterator * @returns {void} */ - updateHash(hash, context) { - if (this._hashUpdate === undefined) - this._hashUpdate = "" + this.identifier + this.range + this.expression; - hash.update(this._hashUpdate); - } - - serialize(context) { - const { write } = context; - - write(this.expression); - write(this.range); - write(this.identifier); - - super.serialize(context); - } - - deserialize(context) { - const { read } = context; + const forEachEntry = fn => { + for (const name of Object.keys(entry)) { + fn(entry[name]); + } + }; + A(output, "enabledLibraryTypes", () => { + const enabledLibraryTypes = []; + if (output.library) { + enabledLibraryTypes.push(output.library.type); + } + forEachEntry(desc => { + if (desc.library) { + enabledLibraryTypes.push(desc.library.type); + } + }); + return enabledLibraryTypes; + }); - this.expression = read(); - this.range = read(); - this.identifier = read(); + A(output, "enabledChunkLoadingTypes", () => { + const enabledChunkLoadingTypes = new Set(); + if (output.chunkLoading) { + enabledChunkLoadingTypes.add(output.chunkLoading); + } + if (output.workerChunkLoading) { + enabledChunkLoadingTypes.add(output.workerChunkLoading); + } + forEachEntry(desc => { + if (desc.chunkLoading) { + enabledChunkLoadingTypes.add(desc.chunkLoading); + } + }); + return Array.from(enabledChunkLoadingTypes); + }); - super.deserialize(context); - } -} + A(output, "enabledWasmLoadingTypes", () => { + const enabledWasmLoadingTypes = new Set(); + if (output.wasmLoading) { + enabledWasmLoadingTypes.add(output.wasmLoading); + } + if (output.workerWasmLoading) { + enabledWasmLoadingTypes.add(output.workerWasmLoading); + } + forEachEntry(desc => { + if (desc.wasmLoading) { + enabledWasmLoadingTypes.add(desc.wasmLoading); + } + }); + return Array.from(enabledWasmLoadingTypes); + }); +}; -makeSerializable( - CachedConstDependency, - "webpack/lib/dependencies/CachedConstDependency" -); +/** + * @param {ExternalsPresets} externalsPresets options + * @param {Object} options options + * @param {TargetProperties | false} options.targetProperties target properties + * @param {boolean} options.buildHttp buildHttp experiment enabled + * @returns {void} + */ +const applyExternalsPresetsDefaults = ( + externalsPresets, + { targetProperties, buildHttp } +) => { + D( + externalsPresets, + "web", + !buildHttp && targetProperties && targetProperties.web + ); + D(externalsPresets, "node", targetProperties && targetProperties.node); + D(externalsPresets, "nwjs", targetProperties && targetProperties.nwjs); + D( + externalsPresets, + "electron", + targetProperties && targetProperties.electron + ); + D( + externalsPresets, + "electronMain", + targetProperties && + targetProperties.electron && + targetProperties.electronMain + ); + D( + externalsPresets, + "electronPreload", + targetProperties && + targetProperties.electron && + targetProperties.electronPreload + ); + D( + externalsPresets, + "electronRenderer", + targetProperties && + targetProperties.electron && + targetProperties.electronRenderer + ); +}; -CachedConstDependency.Template = class CachedConstDependencyTemplate extends ( - DependencyTemplate -) { - /** - * @param {Dependency} dependency the dependency for which the template should be applied - * @param {ReplaceSource} source the current replace source which can be modified - * @param {DependencyTemplateContext} templateContext the context object - * @returns {void} - */ - apply( - dependency, - source, - { runtimeTemplate, dependencyTemplates, initFragments } - ) { - const dep = /** @type {CachedConstDependency} */ (dependency); +/** + * @param {Loader} loader options + * @param {Object} options options + * @param {TargetProperties | false} options.targetProperties target properties + * @returns {void} + */ +const applyLoaderDefaults = (loader, { targetProperties }) => { + F(loader, "target", () => { + if (targetProperties) { + if (targetProperties.electron) { + if (targetProperties.electronMain) return "electron-main"; + if (targetProperties.electronPreload) return "electron-preload"; + if (targetProperties.electronRenderer) return "electron-renderer"; + return "electron"; + } + if (targetProperties.nwjs) return "nwjs"; + if (targetProperties.node) return "node"; + if (targetProperties.web) return "web"; + } + }); +}; - initFragments.push( - new InitFragment( - `var ${dep.identifier} = ${dep.expression};\n`, - InitFragment.STAGE_CONSTANTS, - 0, - `const ${dep.identifier}` - ) - ); +/** + * @param {WebpackNode} node options + * @param {Object} options options + * @param {TargetProperties | false} options.targetProperties target properties + * @param {boolean} options.futureDefaults is future defaults enabled + * @returns {void} + */ +const applyNodeDefaults = (node, { futureDefaults, targetProperties }) => { + if (node === false) return; - if (typeof dep.range === "number") { - source.insert(dep.range, dep.identifier); + F(node, "global", () => { + if (targetProperties && targetProperties.global) return false; + // TODO webpack 6 should always default to false + return futureDefaults ? "warn" : true; + }); + F(node, "__filename", () => { + if (targetProperties && targetProperties.node) return "eval-only"; + // TODO webpack 6 should always default to false + return futureDefaults ? "warn-mock" : "mock"; + }); + F(node, "__dirname", () => { + if (targetProperties && targetProperties.node) return "eval-only"; + // TODO webpack 6 should always default to false + return futureDefaults ? "warn-mock" : "mock"; + }); +}; - return; - } +/** + * @param {Performance} performance options + * @param {Object} options options + * @param {boolean} options.production is production + * @returns {void} + */ +const applyPerformanceDefaults = (performance, { production }) => { + if (performance === false) return; + D(performance, "maxAssetSize", 250000); + D(performance, "maxEntrypointSize", 250000); + F(performance, "hints", () => (production ? "warning" : false)); +}; - source.replace(dep.range[0], dep.range[1] - 1, dep.identifier); +/** + * @param {Optimization} optimization options + * @param {Object} options options + * @param {boolean} options.production is production + * @param {boolean} options.development is development + * @param {boolean} options.records using records + * @returns {void} + */ +const applyOptimizationDefaults = ( + optimization, + { production, development, records } +) => { + D(optimization, "removeAvailableModules", false); + D(optimization, "removeEmptyChunks", true); + D(optimization, "mergeDuplicateChunks", true); + D(optimization, "flagIncludedChunks", production); + F(optimization, "moduleIds", () => { + if (production) return "deterministic"; + if (development) return "named"; + return "natural"; + }); + F(optimization, "chunkIds", () => { + if (production) return "deterministic"; + if (development) return "named"; + return "natural"; + }); + F(optimization, "sideEffects", () => (production ? true : "flag")); + D(optimization, "providedExports", true); + D(optimization, "usedExports", production); + D(optimization, "innerGraph", production); + D(optimization, "mangleExports", production); + D(optimization, "concatenateModules", production); + D(optimization, "runtimeChunk", false); + D(optimization, "emitOnErrors", !production); + D(optimization, "checkWasmTypes", production); + D(optimization, "mangleWasmImports", false); + D(optimization, "portableRecords", records); + D(optimization, "realContentHash", production); + D(optimization, "minimize", production); + A(optimization, "minimizer", () => [ + { + apply: compiler => { + // Lazy load the Terser plugin + const TerserPlugin = __webpack_require__(56052); + new TerserPlugin({ + terserOptions: { + compress: { + passes: 2 + } + } + }).apply(compiler); + } + } + ]); + F(optimization, "nodeEnv", () => { + if (production) return "production"; + if (development) return "development"; + return false; + }); + const { splitChunks } = optimization; + if (splitChunks) { + A(splitChunks, "defaultSizeTypes", () => ["javascript", "unknown"]); + D(splitChunks, "hidePathInfo", production); + D(splitChunks, "chunks", "async"); + D(splitChunks, "usedExports", optimization.usedExports === true); + D(splitChunks, "minChunks", 1); + F(splitChunks, "minSize", () => (production ? 20000 : 10000)); + F(splitChunks, "minRemainingSize", () => (development ? 0 : undefined)); + F(splitChunks, "enforceSizeThreshold", () => (production ? 50000 : 30000)); + F(splitChunks, "maxAsyncRequests", () => (production ? 30 : Infinity)); + F(splitChunks, "maxInitialRequests", () => (production ? 30 : Infinity)); + D(splitChunks, "automaticNameDelimiter", "-"); + const { cacheGroups } = splitChunks; + F(cacheGroups, "default", () => ({ + idHint: "", + reuseExistingChunk: true, + minChunks: 2, + priority: -20 + })); + F(cacheGroups, "defaultVendors", () => ({ + idHint: "vendors", + reuseExistingChunk: true, + test: NODE_MODULES_REGEXP, + priority: -10 + })); } }; -module.exports = CachedConstDependency; +/** + * @param {Object} options options + * @param {boolean} options.cache is cache enable + * @param {string} options.context build context + * @param {TargetProperties | false} options.targetProperties target properties + * @param {Mode} options.mode mode + * @returns {ResolveOptions} resolve options + */ +const getResolveDefaults = ({ cache, context, targetProperties, mode }) => { + /** @type {string[]} */ + const conditions = ["webpack"]; + conditions.push(mode === "development" ? "development" : "production"); -/***/ }), + if (targetProperties) { + if (targetProperties.webworker) conditions.push("worker"); + if (targetProperties.node) conditions.push("node"); + if (targetProperties.web) conditions.push("browser"); + if (targetProperties.electron) conditions.push("electron"); + if (targetProperties.nwjs) conditions.push("nwjs"); + } -/***/ 95217: -/***/ (function(__unused_webpack_module, exports, __webpack_require__) { + const jsExtensions = [".js", ".json", ".wasm"]; -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ + const tp = targetProperties; + const browserField = + tp && tp.web && (!tp.node || (tp.electron && tp.electronRenderer)); + /** @type {function(): ResolveOptions} */ + const cjsDeps = () => ({ + aliasFields: browserField ? ["browser"] : [], + mainFields: browserField ? ["browser", "module", "..."] : ["module", "..."], + conditionNames: ["require", "module", "..."], + extensions: [...jsExtensions] + }); + /** @type {function(): ResolveOptions} */ + const esmDeps = () => ({ + aliasFields: browserField ? ["browser"] : [], + mainFields: browserField ? ["browser", "module", "..."] : ["module", "..."], + conditionNames: ["import", "module", "..."], + extensions: [...jsExtensions] + }); + /** @type {ResolveOptions} */ + const resolveOptions = { + cache, + modules: ["node_modules"], + conditionNames: conditions, + mainFiles: ["index"], + extensions: [], + aliasFields: [], + exportsFields: ["exports"], + roots: [context], + mainFields: ["main"], + byDependency: { + wasm: esmDeps(), + esm: esmDeps(), + loaderImport: esmDeps(), + url: { + preferRelative: true + }, + worker: { + ...esmDeps(), + preferRelative: true + }, + commonjs: cjsDeps(), + amd: cjsDeps(), + // for backward-compat: loadModule + loader: cjsDeps(), + // for backward-compat: Custom Dependency + unknown: cjsDeps(), + // for backward-compat: getResolve without dependencyType + undefined: cjsDeps() + } + }; -const RuntimeGlobals = __webpack_require__(49404); + return resolveOptions; +}; -exports.handleDependencyBase = (depBase, module, runtimeRequirements) => { - let base = undefined; - let type; - switch (depBase) { - case "exports": - runtimeRequirements.add(RuntimeGlobals.exports); - base = module.exportsArgument; - type = "expression"; - break; - case "module.exports": - runtimeRequirements.add(RuntimeGlobals.module); - base = `${module.moduleArgument}.exports`; - type = "expression"; - break; - case "this": - runtimeRequirements.add(RuntimeGlobals.thisAsExports); - base = "this"; - type = "expression"; - break; - case "Object.defineProperty(exports)": - runtimeRequirements.add(RuntimeGlobals.exports); - base = module.exportsArgument; - type = "Object.defineProperty"; - break; - case "Object.defineProperty(module.exports)": - runtimeRequirements.add(RuntimeGlobals.module); - base = `${module.moduleArgument}.exports`; - type = "Object.defineProperty"; - break; - case "Object.defineProperty(this)": - runtimeRequirements.add(RuntimeGlobals.thisAsExports); - base = "this"; - type = "Object.defineProperty"; - break; - default: - throw new Error(`Unsupported base ${depBase}`); - } +/** + * @param {Object} options options + * @param {boolean} options.cache is cache enable + * @returns {ResolveOptions} resolve options + */ +const getResolveLoaderDefaults = ({ cache }) => { + /** @type {ResolveOptions} */ + const resolveOptions = { + cache, + conditionNames: ["loader", "require", "node"], + exportsFields: ["exports"], + mainFields: ["loader", "main"], + extensions: [".js"], + mainFiles: ["index"] + }; - return [type, base]; + return resolveOptions; +}; + +/** + * @param {InfrastructureLogging} infrastructureLogging options + * @returns {void} + */ +const applyInfrastructureLoggingDefaults = infrastructureLogging => { + F(infrastructureLogging, "stream", () => process.stderr); + const tty = + /** @type {any} */ (infrastructureLogging.stream).isTTY && + process.env.TERM !== "dumb"; + D(infrastructureLogging, "level", "info"); + D(infrastructureLogging, "debug", false); + D(infrastructureLogging, "colors", tty); + D(infrastructureLogging, "appendOnly", !tty); }; +exports.applyWebpackOptionsBaseDefaults = applyWebpackOptionsBaseDefaults; +exports.applyWebpackOptionsDefaults = applyWebpackOptionsDefaults; + /***/ }), -/***/ 76922: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { +/***/ 52975: +/***/ (function(__unused_webpack_module, exports, __webpack_require__) { "use strict"; /* @@ -74876,379 +72070,528 @@ exports.handleDependencyBase = (depBase, module, runtimeRequirements) => { -const Dependency = __webpack_require__(50384); -const { UsageState } = __webpack_require__(4295); -const Template = __webpack_require__(92066); -const { equals } = __webpack_require__(21537); -const makeSerializable = __webpack_require__(26522); -const propertyAccess = __webpack_require__(86709); -const { handleDependencyBase } = __webpack_require__(95217); -const ModuleDependency = __webpack_require__(80944); -const processExportInfo = __webpack_require__(35873); - -/** @typedef {import("webpack-sources").ReplaceSource} ReplaceSource */ -/** @typedef {import("../Dependency").ExportsSpec} ExportsSpec */ -/** @typedef {import("../Dependency").ReferencedExport} ReferencedExport */ -/** @typedef {import("../Dependency").TRANSITIVE} TRANSITIVE */ -/** @typedef {import("../DependencyTemplate").DependencyTemplateContext} DependencyTemplateContext */ -/** @typedef {import("../Module")} Module */ -/** @typedef {import("../ModuleGraph")} ModuleGraph */ -/** @typedef {import("../util/runtime").RuntimeSpec} RuntimeSpec */ - -const idsSymbol = Symbol("CommonJsExportRequireDependency.ids"); - -const EMPTY_OBJECT = {}; - -class CommonJsExportRequireDependency extends ModuleDependency { - constructor(range, valueRange, base, names, request, ids, resultUsed) { - super(request); - this.range = range; - this.valueRange = valueRange; - this.base = base; - this.names = names; - this.ids = ids; - this.resultUsed = resultUsed; - this.asiSafe = undefined; - } - - get type() { - return "cjs export require"; - } - - /** - * @returns {boolean | TRANSITIVE} true, when changes to the referenced module could affect the referencing module; TRANSITIVE, when changes to the referenced module could affect referencing modules of the referencing module - */ - couldAffectReferencingModule() { - return Dependency.TRANSITIVE; - } - - /** - * @param {ModuleGraph} moduleGraph the module graph - * @returns {string[]} the imported id - */ - getIds(moduleGraph) { - return moduleGraph.getMeta(this)[idsSymbol] || this.ids; - } - - /** - * @param {ModuleGraph} moduleGraph the module graph - * @param {string[]} ids the imported ids - * @returns {void} - */ - setIds(moduleGraph, ids) { - moduleGraph.getMeta(this)[idsSymbol] = ids; - } - - /** - * Returns list of exports referenced by this dependency - * @param {ModuleGraph} moduleGraph module graph - * @param {RuntimeSpec} runtime the runtime for which the module is analysed - * @returns {(string[] | ReferencedExport)[]} referenced exports - */ - getReferencedExports(moduleGraph, runtime) { - const ids = this.getIds(moduleGraph); - const getFullResult = () => { - if (ids.length === 0) { - return Dependency.EXPORTS_OBJECT_REFERENCED; - } else { - return [ - { - name: ids, - canMangle: false - } - ]; - } - }; - if (this.resultUsed) return getFullResult(); - let exportsInfo = moduleGraph.getExportsInfo( - moduleGraph.getParentModule(this) - ); - for (const name of this.names) { - const exportInfo = exportsInfo.getReadOnlyExportInfo(name); - const used = exportInfo.getUsed(runtime); - if (used === UsageState.Unused) return Dependency.NO_EXPORTS_REFERENCED; - if (used !== UsageState.OnlyPropertiesUsed) return getFullResult(); - exportsInfo = exportInfo.exportsInfo; - if (!exportsInfo) return getFullResult(); - } - if (exportsInfo.otherExportsInfo.getUsed(runtime) !== UsageState.Unused) { - return getFullResult(); - } - /** @type {string[][]} */ - const referencedExports = []; - for (const exportInfo of exportsInfo.orderedExports) { - processExportInfo( - runtime, - referencedExports, - ids.concat(exportInfo.name), - exportInfo, - false - ); - } - return referencedExports.map(name => ({ - name, - canMangle: false - })); - } - - /** - * Returns the exported names - * @param {ModuleGraph} moduleGraph module graph - * @returns {ExportsSpec | undefined} export names - */ - getExports(moduleGraph) { - const ids = this.getIds(moduleGraph); - if (this.names.length === 1) { - const name = this.names[0]; - const from = moduleGraph.getConnection(this); - if (!from) return; - return { - exports: [ - { - name, - from, - export: ids.length === 0 ? null : ids, - // we can't mangle names that are in an empty object - // because one could access the prototype property - // when export isn't set yet - canMangle: !(name in EMPTY_OBJECT) && false - } - ], - dependencies: [from.module] - }; - } else if (this.names.length > 0) { - const name = this.names[0]; - return { - exports: [ - { - name, - // we can't mangle names that are in an empty object - // because one could access the prototype property - // when export isn't set yet - canMangle: !(name in EMPTY_OBJECT) && false - } - ], - dependencies: undefined - }; - } else { - const from = moduleGraph.getConnection(this); - if (!from) return; - const reexportInfo = this.getStarReexports( - moduleGraph, - undefined, - from.module - ); - if (reexportInfo) { - return { - exports: Array.from(reexportInfo.exports, name => { - return { - name, - from, - export: ids.concat(name), - canMangle: !(name in EMPTY_OBJECT) && false - }; - }), - // TODO handle deep reexports - dependencies: [from.module] - }; - } else { - return { - exports: true, - from: ids.length === 0 ? from : undefined, - canMangle: false, - dependencies: [from.module] - }; - } - } - } - - /** - * @param {ModuleGraph} moduleGraph the module graph - * @param {RuntimeSpec} runtime the runtime - * @param {Module} importedModule the imported module (optional) - * @returns {{exports?: Set, checked?: Set}} information - */ - getStarReexports( - moduleGraph, - runtime, - importedModule = moduleGraph.getModule(this) - ) { - let importedExportsInfo = moduleGraph.getExportsInfo(importedModule); - const ids = this.getIds(moduleGraph); - if (ids.length > 0) - importedExportsInfo = importedExportsInfo.getNestedExportsInfo(ids); - let exportsInfo = moduleGraph.getExportsInfo( - moduleGraph.getParentModule(this) - ); - if (this.names.length > 0) - exportsInfo = exportsInfo.getNestedExportsInfo(this.names); - - const noExtraExports = - importedExportsInfo && - importedExportsInfo.otherExportsInfo.provided === false; - const noExtraImports = - exportsInfo && - exportsInfo.otherExportsInfo.getUsed(runtime) === UsageState.Unused; - - if (!noExtraExports && !noExtraImports) { - return; - } - - const isNamespaceImport = - importedModule.getExportsType(moduleGraph, false) === "namespace"; - - /** @type {Set} */ - const exports = new Set(); - /** @type {Set} */ - const checked = new Set(); - - if (noExtraImports) { - for (const exportInfo of exportsInfo.orderedExports) { - const name = exportInfo.name; - if (exportInfo.getUsed(runtime) === UsageState.Unused) continue; - if (name === "__esModule" && isNamespaceImport) { - exports.add(name); - } else if (importedExportsInfo) { - const importedExportInfo = - importedExportsInfo.getReadOnlyExportInfo(name); - if (importedExportInfo.provided === false) continue; - exports.add(name); - if (importedExportInfo.provided === true) continue; - checked.add(name); - } else { - exports.add(name); - checked.add(name); - } - } - } else if (noExtraExports) { - for (const importedExportInfo of importedExportsInfo.orderedExports) { - const name = importedExportInfo.name; - if (importedExportInfo.provided === false) continue; - if (exportsInfo) { - const exportInfo = exportsInfo.getReadOnlyExportInfo(name); - if (exportInfo.getUsed(runtime) === UsageState.Unused) continue; - } - exports.add(name); - if (importedExportInfo.provided === true) continue; - checked.add(name); - } - if (isNamespaceImport) { - exports.add("__esModule"); - checked.delete("__esModule"); - } +const util = __webpack_require__(31669); + +/** @typedef {import("../../declarations/WebpackOptions").EntryStatic} EntryStatic */ +/** @typedef {import("../../declarations/WebpackOptions").EntryStaticNormalized} EntryStaticNormalized */ +/** @typedef {import("../../declarations/WebpackOptions").LibraryName} LibraryName */ +/** @typedef {import("../../declarations/WebpackOptions").LibraryOptions} LibraryOptions */ +/** @typedef {import("../../declarations/WebpackOptions").OptimizationRuntimeChunk} OptimizationRuntimeChunk */ +/** @typedef {import("../../declarations/WebpackOptions").OptimizationRuntimeChunkNormalized} OptimizationRuntimeChunkNormalized */ +/** @typedef {import("../../declarations/WebpackOptions").OutputNormalized} OutputNormalized */ +/** @typedef {import("../../declarations/WebpackOptions").WebpackOptions} WebpackOptions */ +/** @typedef {import("../../declarations/WebpackOptions").WebpackOptionsNormalized} WebpackOptionsNormalized */ + +const handledDeprecatedNoEmitOnErrors = util.deprecate( + (noEmitOnErrors, emitOnErrors) => { + if (emitOnErrors !== undefined && !noEmitOnErrors === !emitOnErrors) { + throw new Error( + "Conflicting use of 'optimization.noEmitOnErrors' and 'optimization.emitOnErrors'. Remove deprecated 'optimization.noEmitOnErrors' from config." + ); } + return !noEmitOnErrors; + }, + "optimization.noEmitOnErrors is deprecated in favor of optimization.emitOnErrors", + "DEP_WEBPACK_CONFIGURATION_OPTIMIZATION_NO_EMIT_ON_ERRORS" +); - return { exports, checked }; - } +/** + * @template T + * @template R + * @param {T|undefined} value value or not + * @param {function(T): R} fn nested handler + * @returns {R} result value + */ +const nestedConfig = (value, fn) => + value === undefined ? fn(/** @type {T} */ ({})) : fn(value); - serialize(context) { - const { write } = context; - write(this.asiSafe); - write(this.range); - write(this.valueRange); - write(this.base); - write(this.names); - write(this.ids); - write(this.resultUsed); - super.serialize(context); - } +/** + * @template T + * @param {T|undefined} value value or not + * @returns {T} result value + */ +const cloneObject = value => { + return /** @type {T} */ ({ ...value }); +}; - deserialize(context) { - const { read } = context; - this.asiSafe = read(); - this.range = read(); - this.valueRange = read(); - this.base = read(); - this.names = read(); - this.ids = read(); - this.resultUsed = read(); - super.deserialize(context); - } -} +/** + * @template T + * @template R + * @param {T|undefined} value value or not + * @param {function(T): R} fn nested handler + * @returns {R|undefined} result value + */ +const optionalNestedConfig = (value, fn) => + value === undefined ? undefined : fn(value); -makeSerializable( - CommonJsExportRequireDependency, - "webpack/lib/dependencies/CommonJsExportRequireDependency" -); +/** + * @template T + * @template R + * @param {T[]|undefined} value array or not + * @param {function(T[]): R[]} fn nested handler + * @returns {R[]|undefined} cloned value + */ +const nestedArray = (value, fn) => (Array.isArray(value) ? fn(value) : fn([])); -CommonJsExportRequireDependency.Template = class CommonJsExportRequireDependencyTemplate extends ( - ModuleDependency.Template -) { - /** - * @param {Dependency} dependency the dependency for which the template should be applied - * @param {ReplaceSource} source the current replace source which can be modified - * @param {DependencyTemplateContext} templateContext the context object - * @returns {void} - */ - apply( - dependency, - source, - { - module, - runtimeTemplate, - chunkGraph, - moduleGraph, - runtimeRequirements, - runtime +/** + * @template T + * @template R + * @param {T[]|undefined} value array or not + * @param {function(T[]): R[]} fn nested handler + * @returns {R[]|undefined} cloned value + */ +const optionalNestedArray = (value, fn) => + Array.isArray(value) ? fn(value) : undefined; + +/** + * @template T + * @template R + * @param {Record|undefined} value value or not + * @param {function(T): R} fn nested handler + * @param {Record=} customKeys custom nested handler for some keys + * @returns {Record} result value + */ +const keyedNestedConfig = (value, fn, customKeys) => { + const result = + value === undefined + ? {} + : Object.keys(value).reduce( + (obj, key) => ( + (obj[key] = ( + customKeys && key in customKeys ? customKeys[key] : fn + )(value[key])), + obj + ), + /** @type {Record} */ ({}) + ); + if (customKeys) { + for (const key of Object.keys(customKeys)) { + if (!(key in result)) { + result[key] = customKeys[key](/** @type {T} */ ({})); + } } - ) { - const dep = /** @type {CommonJsExportRequireDependency} */ (dependency); - const used = moduleGraph - .getExportsInfo(module) - .getUsedName(dep.names, runtime); + } + return result; +}; - const [type, base] = handleDependencyBase( - dep.base, - module, - runtimeRequirements - ); +/** + * @param {WebpackOptions} config input config + * @returns {WebpackOptionsNormalized} normalized options + */ +const getNormalizedWebpackOptions = config => { + return { + amd: config.amd, + bail: config.bail, + cache: optionalNestedConfig(config.cache, cache => { + if (cache === false) return false; + if (cache === true) { + return { + type: "memory", + maxGenerations: undefined + }; + } + switch (cache.type) { + case "filesystem": + return { + type: "filesystem", + allowCollectingMemory: cache.allowCollectingMemory, + maxMemoryGenerations: cache.maxMemoryGenerations, + maxAge: cache.maxAge, + profile: cache.profile, + buildDependencies: cloneObject(cache.buildDependencies), + cacheDirectory: cache.cacheDirectory, + cacheLocation: cache.cacheLocation, + hashAlgorithm: cache.hashAlgorithm, + compression: cache.compression, + idleTimeout: cache.idleTimeout, + idleTimeoutForInitialStore: cache.idleTimeoutForInitialStore, + idleTimeoutAfterLargeChanges: cache.idleTimeoutAfterLargeChanges, + name: cache.name, + store: cache.store, + version: cache.version + }; + case undefined: + case "memory": + return { + type: "memory", + maxGenerations: cache.maxGenerations + }; + default: + // @ts-expect-error Property 'type' does not exist on type 'never'. ts(2339) + throw new Error(`Not implemented cache.type ${cache.type}`); + } + }), + context: config.context, + dependencies: config.dependencies, + devServer: optionalNestedConfig(config.devServer, devServer => ({ + ...devServer + })), + devtool: config.devtool, + entry: + config.entry === undefined + ? { main: {} } + : typeof config.entry === "function" + ? ( + fn => () => + Promise.resolve().then(fn).then(getNormalizedEntryStatic) + )(config.entry) + : getNormalizedEntryStatic(config.entry), + experiments: nestedConfig(config.experiments, experiments => ({ + ...experiments, + buildHttp: optionalNestedConfig(experiments.buildHttp, options => + Array.isArray(options) ? { allowedUris: options } : options + ), + lazyCompilation: optionalNestedConfig( + experiments.lazyCompilation, + options => + options === true ? {} : options === false ? undefined : options + ) + })), + externals: config.externals, + externalsPresets: cloneObject(config.externalsPresets), + externalsType: config.externalsType, + ignoreWarnings: config.ignoreWarnings + ? config.ignoreWarnings.map(ignore => { + if (typeof ignore === "function") return ignore; + const i = ignore instanceof RegExp ? { message: ignore } : ignore; + return (warning, { requestShortener }) => { + if (!i.message && !i.module && !i.file) return false; + if (i.message && !i.message.test(warning.message)) { + return false; + } + if ( + i.module && + (!warning.module || + !i.module.test( + warning.module.readableIdentifier(requestShortener) + )) + ) { + return false; + } + if (i.file && (!warning.file || !i.file.test(warning.file))) { + return false; + } + return true; + }; + }) + : undefined, + infrastructureLogging: cloneObject(config.infrastructureLogging), + loader: cloneObject(config.loader), + mode: config.mode, + module: nestedConfig(config.module, module => ({ + noParse: module.noParse, + unsafeCache: module.unsafeCache, + parser: keyedNestedConfig(module.parser, cloneObject, { + javascript: parserOptions => ({ + unknownContextRequest: module.unknownContextRequest, + unknownContextRegExp: module.unknownContextRegExp, + unknownContextRecursive: module.unknownContextRecursive, + unknownContextCritical: module.unknownContextCritical, + exprContextRequest: module.exprContextRequest, + exprContextRegExp: module.exprContextRegExp, + exprContextRecursive: module.exprContextRecursive, + exprContextCritical: module.exprContextCritical, + wrappedContextRegExp: module.wrappedContextRegExp, + wrappedContextRecursive: module.wrappedContextRecursive, + wrappedContextCritical: module.wrappedContextCritical, + // TODO webpack 6 remove + strictExportPresence: module.strictExportPresence, + strictThisContextOnImports: module.strictThisContextOnImports, + ...parserOptions + }) + }), + generator: cloneObject(module.generator), + defaultRules: optionalNestedArray(module.defaultRules, r => [...r]), + rules: nestedArray(module.rules, r => [...r]) + })), + name: config.name, + node: nestedConfig( + config.node, + node => + node && { + ...node + } + ), + optimization: nestedConfig(config.optimization, optimization => { + return { + ...optimization, + runtimeChunk: getNormalizedOptimizationRuntimeChunk( + optimization.runtimeChunk + ), + splitChunks: nestedConfig( + optimization.splitChunks, + splitChunks => + splitChunks && { + ...splitChunks, + defaultSizeTypes: splitChunks.defaultSizeTypes + ? [...splitChunks.defaultSizeTypes] + : ["..."], + cacheGroups: cloneObject(splitChunks.cacheGroups) + } + ), + emitOnErrors: + optimization.noEmitOnErrors !== undefined + ? handledDeprecatedNoEmitOnErrors( + optimization.noEmitOnErrors, + optimization.emitOnErrors + ) + : optimization.emitOnErrors + }; + }), + output: nestedConfig(config.output, output => { + const { library } = output; + const libraryAsName = /** @type {LibraryName} */ (library); + const libraryBase = + typeof library === "object" && + library && + !Array.isArray(library) && + "type" in library + ? library + : libraryAsName || output.libraryTarget + ? /** @type {LibraryOptions} */ ({ + name: libraryAsName + }) + : undefined; + /** @type {OutputNormalized} */ + const result = { + assetModuleFilename: output.assetModuleFilename, + asyncChunks: output.asyncChunks, + charset: output.charset, + chunkFilename: output.chunkFilename, + chunkFormat: output.chunkFormat, + chunkLoading: output.chunkLoading, + chunkLoadingGlobal: output.chunkLoadingGlobal, + chunkLoadTimeout: output.chunkLoadTimeout, + clean: output.clean, + compareBeforeEmit: output.compareBeforeEmit, + crossOriginLoading: output.crossOriginLoading, + devtoolFallbackModuleFilenameTemplate: + output.devtoolFallbackModuleFilenameTemplate, + devtoolModuleFilenameTemplate: output.devtoolModuleFilenameTemplate, + devtoolNamespace: output.devtoolNamespace, + environment: cloneObject(output.environment), + enabledChunkLoadingTypes: output.enabledChunkLoadingTypes + ? [...output.enabledChunkLoadingTypes] + : ["..."], + enabledLibraryTypes: output.enabledLibraryTypes + ? [...output.enabledLibraryTypes] + : ["..."], + enabledWasmLoadingTypes: output.enabledWasmLoadingTypes + ? [...output.enabledWasmLoadingTypes] + : ["..."], + filename: output.filename, + globalObject: output.globalObject, + hashDigest: output.hashDigest, + hashDigestLength: output.hashDigestLength, + hashFunction: output.hashFunction, + hashSalt: output.hashSalt, + hotUpdateChunkFilename: output.hotUpdateChunkFilename, + hotUpdateGlobal: output.hotUpdateGlobal, + hotUpdateMainFilename: output.hotUpdateMainFilename, + iife: output.iife, + importFunctionName: output.importFunctionName, + importMetaName: output.importMetaName, + scriptType: output.scriptType, + library: libraryBase && { + type: + output.libraryTarget !== undefined + ? output.libraryTarget + : libraryBase.type, + auxiliaryComment: + output.auxiliaryComment !== undefined + ? output.auxiliaryComment + : libraryBase.auxiliaryComment, + export: + output.libraryExport !== undefined + ? output.libraryExport + : libraryBase.export, + name: libraryBase.name, + umdNamedDefine: + output.umdNamedDefine !== undefined + ? output.umdNamedDefine + : libraryBase.umdNamedDefine + }, + module: output.module, + path: output.path, + pathinfo: output.pathinfo, + publicPath: output.publicPath, + sourceMapFilename: output.sourceMapFilename, + sourcePrefix: output.sourcePrefix, + strictModuleExceptionHandling: output.strictModuleExceptionHandling, + trustedTypes: optionalNestedConfig( + output.trustedTypes, + trustedTypes => { + if (trustedTypes === true) return {}; + if (typeof trustedTypes === "string") + return { policyName: trustedTypes }; + return { ...trustedTypes }; + } + ), + uniqueName: output.uniqueName, + wasmLoading: output.wasmLoading, + webassemblyModuleFilename: output.webassemblyModuleFilename, + workerChunkLoading: output.workerChunkLoading, + workerWasmLoading: output.workerWasmLoading + }; + return result; + }), + parallelism: config.parallelism, + performance: optionalNestedConfig(config.performance, performance => { + if (performance === false) return false; + return { + ...performance + }; + }), + plugins: nestedArray(config.plugins, p => [...p]), + profile: config.profile, + recordsInputPath: + config.recordsInputPath !== undefined + ? config.recordsInputPath + : config.recordsPath, + recordsOutputPath: + config.recordsOutputPath !== undefined + ? config.recordsOutputPath + : config.recordsPath, + resolve: nestedConfig(config.resolve, resolve => ({ + ...resolve, + byDependency: keyedNestedConfig(resolve.byDependency, cloneObject) + })), + resolveLoader: cloneObject(config.resolveLoader), + snapshot: nestedConfig(config.snapshot, snapshot => ({ + resolveBuildDependencies: optionalNestedConfig( + snapshot.resolveBuildDependencies, + resolveBuildDependencies => ({ + timestamp: resolveBuildDependencies.timestamp, + hash: resolveBuildDependencies.hash + }) + ), + buildDependencies: optionalNestedConfig( + snapshot.buildDependencies, + buildDependencies => ({ + timestamp: buildDependencies.timestamp, + hash: buildDependencies.hash + }) + ), + resolve: optionalNestedConfig(snapshot.resolve, resolve => ({ + timestamp: resolve.timestamp, + hash: resolve.hash + })), + module: optionalNestedConfig(snapshot.module, module => ({ + timestamp: module.timestamp, + hash: module.hash + })), + immutablePaths: optionalNestedArray(snapshot.immutablePaths, p => [...p]), + managedPaths: optionalNestedArray(snapshot.managedPaths, p => [...p]) + })), + stats: nestedConfig(config.stats, stats => { + if (stats === false) { + return { + preset: "none" + }; + } + if (stats === true) { + return { + preset: "normal" + }; + } + if (typeof stats === "string") { + return { + preset: stats + }; + } + return { + ...stats + }; + }), + target: config.target, + watch: config.watch, + watchOptions: cloneObject(config.watchOptions) + }; +}; - const importedModule = moduleGraph.getModule(dep); - let requireExpr = runtimeTemplate.moduleExports({ - module: importedModule, - chunkGraph, - request: dep.request, - weak: dep.weak, - runtimeRequirements - }); - if (importedModule) { - const ids = dep.getIds(moduleGraph); - const usedImported = moduleGraph - .getExportsInfo(importedModule) - .getUsedName(ids, runtime); - if (usedImported) { - const comment = equals(usedImported, ids) - ? "" - : Template.toNormalComment(propertyAccess(ids)) + " "; - requireExpr += `${comment}${propertyAccess(usedImported)}`; +/** + * @param {EntryStatic} entry static entry options + * @returns {EntryStaticNormalized} normalized static entry options + */ +const getNormalizedEntryStatic = entry => { + if (typeof entry === "string") { + return { + main: { + import: [entry] + } + }; + } + if (Array.isArray(entry)) { + return { + main: { + import: entry } + }; + } + /** @type {EntryStaticNormalized} */ + const result = {}; + for (const key of Object.keys(entry)) { + const value = entry[key]; + if (typeof value === "string") { + result[key] = { + import: [value] + }; + } else if (Array.isArray(value)) { + result[key] = { + import: value + }; + } else { + result[key] = { + import: + value.import && + (Array.isArray(value.import) ? value.import : [value.import]), + filename: value.filename, + layer: value.layer, + runtime: value.runtime, + publicPath: value.publicPath, + chunkLoading: value.chunkLoading, + asyncChunks: value.asyncChunks, + wasmLoading: value.wasmLoading, + dependOn: + value.dependOn && + (Array.isArray(value.dependOn) ? value.dependOn : [value.dependOn]), + library: value.library + }; } + } + return result; +}; - switch (type) { - case "expression": - source.replace( - dep.range[0], - dep.range[1] - 1, - used - ? `${base}${propertyAccess(used)} = ${requireExpr}` - : `/* unused reexport */ ${requireExpr}` - ); - return; - case "Object.defineProperty": - throw new Error("TODO"); - default: - throw new Error("Unexpected type"); - } +/** + * @param {OptimizationRuntimeChunk=} runtimeChunk runtimeChunk option + * @returns {OptimizationRuntimeChunkNormalized=} normalized runtimeChunk option + */ +const getNormalizedOptimizationRuntimeChunk = runtimeChunk => { + if (runtimeChunk === undefined) return undefined; + if (runtimeChunk === false) return false; + if (runtimeChunk === "single") { + return { + name: () => "runtime" + }; + } + if (runtimeChunk === true || runtimeChunk === "multiple") { + return { + name: entrypoint => `runtime~${entrypoint.name}` + }; } + const { name } = runtimeChunk; + return { + name: typeof name === "function" ? name : () => name + }; }; -module.exports = CommonJsExportRequireDependency; +exports.getNormalizedWebpackOptions = getNormalizedWebpackOptions; /***/ }), -/***/ 9585: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { +/***/ 23451: +/***/ (function(__unused_webpack_module, exports, __webpack_require__) { "use strict"; /* @@ -75258,1336 +72601,1043 @@ module.exports = CommonJsExportRequireDependency; -const InitFragment = __webpack_require__(51739); -const makeSerializable = __webpack_require__(26522); -const propertyAccess = __webpack_require__(86709); -const { handleDependencyBase } = __webpack_require__(95217); -const NullDependency = __webpack_require__(65845); - -/** @typedef {import("webpack-sources").ReplaceSource} ReplaceSource */ -/** @typedef {import("../Dependency")} Dependency */ -/** @typedef {import("../Dependency").ExportsSpec} ExportsSpec */ -/** @typedef {import("../DependencyTemplate").DependencyTemplateContext} DependencyTemplateContext */ -/** @typedef {import("../ModuleGraph")} ModuleGraph */ - -const EMPTY_OBJECT = {}; - -class CommonJsExportsDependency extends NullDependency { - constructor(range, valueRange, base, names) { - super(); - this.range = range; - this.valueRange = valueRange; - this.base = base; - this.names = names; - } +const memoize = __webpack_require__(84297); - get type() { - return "cjs exports"; - } +const getBrowserslistTargetHandler = memoize(() => + __webpack_require__(82852) +); - /** - * Returns the exported names - * @param {ModuleGraph} moduleGraph module graph - * @returns {ExportsSpec | undefined} export names - */ - getExports(moduleGraph) { - const name = this.names[0]; - return { - exports: [ - { - name, - // we can't mangle names that are in an empty object - // because one could access the prototype property - // when export isn't set yet - canMangle: !(name in EMPTY_OBJECT) - } - ], - dependencies: undefined - }; - } +/** + * @param {string} context the context directory + * @returns {string} default target + */ +const getDefaultTarget = context => { + const browsers = getBrowserslistTargetHandler().load(null, context); + return browsers ? "browserslist" : "web"; +}; - serialize(context) { - const { write } = context; - write(this.range); - write(this.valueRange); - write(this.base); - write(this.names); - super.serialize(context); - } +/** + * @typedef {Object} PlatformTargetProperties + * @property {boolean | null} web web platform, importing of http(s) and std: is available + * @property {boolean | null} browser browser platform, running in a normal web browser + * @property {boolean | null} webworker (Web)Worker platform, running in a web/shared/service worker + * @property {boolean | null} node node platform, require of node built-in modules is available + * @property {boolean | null} nwjs nwjs platform, require of legacy nw.gui is available + * @property {boolean | null} electron electron platform, require of some electron built-in modules is available + */ - deserialize(context) { - const { read } = context; - this.range = read(); - this.valueRange = read(); - this.base = read(); - this.names = read(); - super.deserialize(context); - } -} +/** + * @typedef {Object} ElectronContextTargetProperties + * @property {boolean | null} electronMain in main context + * @property {boolean | null} electronPreload in preload context + * @property {boolean | null} electronRenderer in renderer context with node integration + */ -makeSerializable( - CommonJsExportsDependency, - "webpack/lib/dependencies/CommonJsExportsDependency" -); +/** + * @typedef {Object} ApiTargetProperties + * @property {boolean | null} require has require function available + * @property {boolean | null} nodeBuiltins has node.js built-in modules available + * @property {boolean | null} document has document available (allows script tags) + * @property {boolean | null} importScripts has importScripts available + * @property {boolean | null} importScriptsInWorker has importScripts available when creating a worker + * @property {boolean | null} fetchWasm has fetch function available for WebAssembly + * @property {boolean | null} global has global variable available + */ -CommonJsExportsDependency.Template = class CommonJsExportsDependencyTemplate extends ( - NullDependency.Template -) { - /** - * @param {Dependency} dependency the dependency for which the template should be applied - * @param {ReplaceSource} source the current replace source which can be modified - * @param {DependencyTemplateContext} templateContext the context object - * @returns {void} - */ - apply( - dependency, - source, - { module, moduleGraph, initFragments, runtimeRequirements, runtime } - ) { - const dep = /** @type {CommonJsExportsDependency} */ (dependency); - const used = moduleGraph - .getExportsInfo(module) - .getUsedName(dep.names, runtime); +/** + * @typedef {Object} EcmaTargetProperties + * @property {boolean | null} globalThis has globalThis variable available + * @property {boolean | null} bigIntLiteral big int literal syntax is available + * @property {boolean | null} const const and let variable declarations are available + * @property {boolean | null} arrowFunction arrow functions are available + * @property {boolean | null} forOf for of iteration is available + * @property {boolean | null} destructuring destructuring is available + * @property {boolean | null} dynamicImport async import() is available + * @property {boolean | null} dynamicImportInWorker async import() is available when creating a worker + * @property {boolean | null} module ESM syntax is available (when in module) + */ - const [type, base] = handleDependencyBase( - dep.base, - module, - runtimeRequirements - ); +///** @typedef {PlatformTargetProperties | ApiTargetProperties | EcmaTargetProperties | PlatformTargetProperties & ApiTargetProperties | PlatformTargetProperties & EcmaTargetProperties | ApiTargetProperties & EcmaTargetProperties} TargetProperties */ +/** @template T @typedef {{ [P in keyof T]?: never }} Never */ +/** @template A @template B @typedef {(A & Never) | (Never & B) | (A & B)} Mix */ +/** @typedef {Mix, Mix>} TargetProperties */ - switch (type) { - case "expression": - if (!used) { - initFragments.push( - new InitFragment( - "var __webpack_unused_export__;\n", - InitFragment.STAGE_CONSTANTS, - 0, - "__webpack_unused_export__" - ) - ); - source.replace( - dep.range[0], - dep.range[1] - 1, - "__webpack_unused_export__" - ); - return; - } - source.replace( - dep.range[0], - dep.range[1] - 1, - `${base}${propertyAccess(used)}` - ); - return; - case "Object.defineProperty": - if (!used) { - initFragments.push( - new InitFragment( - "var __webpack_unused_export__;\n", - InitFragment.STAGE_CONSTANTS, - 0, - "__webpack_unused_export__" - ) - ); - source.replace( - dep.range[0], - dep.valueRange[0] - 1, - "__webpack_unused_export__ = (" - ); - source.replace(dep.valueRange[1], dep.range[1] - 1, ")"); - return; - } - source.replace( - dep.range[0], - dep.valueRange[0] - 1, - `Object.defineProperty(${base}${propertyAccess( - used.slice(0, -1) - )}, ${JSON.stringify(used[used.length - 1])}, (` - ); - source.replace(dep.valueRange[1], dep.range[1] - 1, "))"); - return; - } - } +const versionDependent = (major, minor) => { + if (!major) return () => /** @type {undefined} */ (undefined); + major = +major; + minor = minor ? +minor : 0; + return (vMajor, vMinor = 0) => { + return major > vMajor || (major === vMajor && minor >= vMinor); + }; }; -module.exports = CommonJsExportsDependency; - - -/***/ }), - -/***/ 49577: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { +/** @type {[string, string, RegExp, (...args: string[]) => TargetProperties | false][]} */ +const TARGETS = [ + [ + "browserslist / browserslist:env / browserslist:query / browserslist:path-to-config / browserslist:path-to-config:env", + "Resolve features from browserslist. Will resolve browserslist config automatically. Only browser or node queries are supported (electron is not supported). Examples: 'browserslist:modern' to use 'modern' environment from browserslist config", + /^browserslist(?::(.+))?$/, + (rest, context) => { + const browserslistTargetHandler = getBrowserslistTargetHandler(); + const browsers = browserslistTargetHandler.load( + rest ? rest.trim() : null, + context + ); + if (!browsers) { + throw new Error(`No browserslist config found to handle the 'browserslist' target. +See https://github.com/browserslist/browserslist#queries for possible ways to provide a config. +The recommended way is to add a 'browserslist' key to your package.json and list supported browsers (resp. node.js versions). +You can also more options via the 'target' option: 'browserslist' / 'browserslist:env' / 'browserslist:query' / 'browserslist:path-to-config' / 'browserslist:path-to-config:env'`); + } + return browserslistTargetHandler.resolve(browsers); + } + ], + [ + "web", + "Web browser.", + /^web$/, + () => { + return { + web: true, + browser: true, + webworker: null, + node: false, + electron: false, + nwjs: false, -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ + document: true, + importScriptsInWorker: true, + fetchWasm: true, + nodeBuiltins: false, + importScripts: false, + require: false, + global: false + }; + } + ], + [ + "webworker", + "Web Worker, SharedWorker or Service Worker.", + /^webworker$/, + () => { + return { + web: true, + browser: true, + webworker: true, + node: false, + electron: false, + nwjs: false, + importScripts: true, + importScriptsInWorker: true, + fetchWasm: true, + nodeBuiltins: false, + require: false, + document: false, + global: false + }; + } + ], + [ + "[async-]node[X[.Y]]", + "Node.js in version X.Y. The 'async-' prefix will load chunks asynchronously via 'fs' and 'vm' instead of 'require()'. Examples: node14.5, async-node10.", + /^(async-)?node(\d+(?:\.(\d+))?)?$/, + (asyncFlag, major, minor) => { + const v = versionDependent(major, minor); + // see https://node.green/ + return { + node: true, + electron: false, + nwjs: false, + web: false, + webworker: false, + browser: false, + require: !asyncFlag, + nodeBuiltins: true, + global: true, + document: false, + fetchWasm: false, + importScripts: false, + importScriptsInWorker: false, -const RuntimeGlobals = __webpack_require__(49404); -const formatLocation = __webpack_require__(57261); -const { evaluateToString } = __webpack_require__(28723); -const propertyAccess = __webpack_require__(86709); -const CommonJsExportRequireDependency = __webpack_require__(76922); -const CommonJsExportsDependency = __webpack_require__(9585); -const CommonJsSelfReferenceDependency = __webpack_require__(69217); -const DynamicExports = __webpack_require__(87370); -const HarmonyExports = __webpack_require__(37637); -const ModuleDecoratorDependency = __webpack_require__(58969); + globalThis: v(12), + const: v(6), + arrowFunction: v(6), + forOf: v(5), + destructuring: v(6), + bigIntLiteral: v(10, 4), + dynamicImport: v(12, 17), + dynamicImportInWorker: major ? false : undefined, + module: v(12, 17) + }; + } + ], + [ + "electron[X[.Y]]-main/preload/renderer", + "Electron in version X.Y. Script is running in main, preload resp. renderer context.", + /^electron(\d+(?:\.(\d+))?)?-(main|preload|renderer)$/, + (major, minor, context) => { + const v = versionDependent(major, minor); + // see https://node.green/ + https://github.com/electron/releases + return { + node: true, + electron: true, + web: context !== "main", + webworker: false, + browser: false, + nwjs: false, -/** @typedef {import("estree").Expression} ExpressionNode */ -/** @typedef {import("../NormalModule")} NormalModule */ -/** @typedef {import("../javascript/BasicEvaluatedExpression")} BasicEvaluatedExpression */ -/** @typedef {import("../javascript/JavascriptParser")} JavascriptParser */ + electronMain: context === "main", + electronPreload: context === "preload", + electronRenderer: context === "renderer", -const getValueOfPropertyDescription = expr => { - if (expr.type !== "ObjectExpression") return; - for (const property of expr.properties) { - if (property.computed) continue; - const key = property.key; - if (key.type !== "Identifier" || key.name !== "value") continue; - return property.value; - } -}; + global: true, + nodeBuiltins: true, + require: true, + document: context === "renderer", + fetchWasm: context === "renderer", + importScripts: false, + importScriptsInWorker: true, -const isTruthyLiteral = expr => { - switch (expr.type) { - case "Literal": - return !!expr.value; - case "UnaryExpression": - if (expr.operator === "!") return isFalsyLiteral(expr.argument); - } - return false; -}; + globalThis: v(5), + const: v(1, 1), + arrowFunction: v(1, 1), + forOf: v(0, 36), + destructuring: v(1, 1), + bigIntLiteral: v(4), + dynamicImport: v(11), + dynamicImportInWorker: major ? false : undefined, + module: v(11) + }; + } + ], + [ + "nwjs[X[.Y]] / node-webkit[X[.Y]]", + "NW.js in version X.Y.", + /^(?:nwjs|node-webkit)(\d+(?:\.(\d+))?)?$/, + (major, minor) => { + const v = versionDependent(major, minor); + // see https://node.green/ + https://github.com/nwjs/nw.js/blob/nw48/CHANGELOG.md + return { + node: true, + web: true, + nwjs: true, + webworker: null, + browser: false, + electron: false, -const isFalsyLiteral = expr => { - switch (expr.type) { - case "Literal": - return !expr.value; - case "UnaryExpression": - if (expr.operator === "!") return isTruthyLiteral(expr.argument); - } - return false; -}; + global: true, + nodeBuiltins: true, + document: false, + importScriptsInWorker: false, + fetchWasm: false, + importScripts: false, + require: false, + + globalThis: v(0, 43), + const: v(0, 15), + arrowFunction: v(0, 15), + forOf: v(0, 13), + destructuring: v(0, 15), + bigIntLiteral: v(0, 32), + dynamicImport: v(0, 43), + dynamicImportInWorker: major ? false : undefined, + module: v(0, 43) + }; + } + ], + [ + "esX", + "EcmaScript in this version. Examples: es2020, es5.", + /^es(\d+)$/, + version => { + let v = +version; + if (v < 1000) v = v + 2009; + return { + const: v >= 2015, + arrowFunction: v >= 2015, + forOf: v >= 2015, + destructuring: v >= 2015, + module: v >= 2015, + globalThis: v >= 2020, + bigIntLiteral: v >= 2020, + dynamicImport: v >= 2020, + dynamicImportInWorker: v >= 2020 + }; + } + ] +]; /** - * @param {JavascriptParser} parser the parser - * @param {ExpressionNode} expr expression - * @returns {{ argument: BasicEvaluatedExpression, ids: string[] } | undefined} parsed call + * @param {string} target the target + * @param {string} context the context directory + * @returns {TargetProperties} target properties */ -const parseRequireCall = (parser, expr) => { - const ids = []; - while (expr.type === "MemberExpression") { - if (expr.object.type === "Super") return; - if (!expr.property) return; - const prop = expr.property; - if (expr.computed) { - if (prop.type !== "Literal") return; - ids.push(`${prop.value}`); - } else { - if (prop.type !== "Identifier") return; - ids.push(prop.name); +const getTargetProperties = (target, context) => { + for (const [, , regExp, handler] of TARGETS) { + const match = regExp.exec(target); + if (match) { + const [, ...args] = match; + const result = handler(...args, context); + if (result) return result; } - expr = expr.object; - } - if (expr.type !== "CallExpression" || expr.arguments.length !== 1) return; - const callee = expr.callee; - if ( - callee.type !== "Identifier" || - parser.getVariableInfo(callee.name) !== "require" - ) { - return; } - const arg = expr.arguments[0]; - if (arg.type === "SpreadElement") return; - const argValue = parser.evaluateExpression(arg); - return { argument: argValue, ids: ids.reverse() }; + throw new Error( + `Unknown target '${target}'. The following targets are supported:\n${TARGETS.map( + ([name, description]) => `* ${name}: ${description}` + ).join("\n")}` + ); }; -class CommonJsExportsParserPlugin { - constructor(moduleGraph) { - this.moduleGraph = moduleGraph; +const mergeTargetProperties = targetProperties => { + const keys = new Set(); + for (const tp of targetProperties) { + for (const key of Object.keys(tp)) { + keys.add(key); + } } - - /** - * @param {JavascriptParser} parser the parser - */ - apply(parser) { - const enableStructuredExports = () => { - DynamicExports.enable(parser.state); - }; - const checkNamespace = (topLevel, members, valueExpr) => { - if (!DynamicExports.isEnabled(parser.state)) return; - if (members.length > 0 && members[0] === "__esModule") { - if (valueExpr && isTruthyLiteral(valueExpr) && topLevel) { - DynamicExports.setFlagged(parser.state); - } else { - DynamicExports.setDynamic(parser.state); - } - } - }; - const bailout = reason => { - DynamicExports.bailout(parser.state); - if (reason) bailoutHint(reason); - }; - const bailoutHint = reason => { - this.moduleGraph - .getOptimizationBailout(parser.state.module) - .push(`CommonJS bailout: ${reason}`); - }; - - // metadata // - parser.hooks.evaluateTypeof - .for("module") - .tap("CommonJsExportsParserPlugin", evaluateToString("object")); - parser.hooks.evaluateTypeof - .for("exports") - .tap("CommonJsPlugin", evaluateToString("object")); - - // exporting // - const handleAssignExport = (expr, base, members) => { - if (HarmonyExports.isEnabled(parser.state)) return; - // Handle reexporting - const requireCall = parseRequireCall(parser, expr.right); - if ( - requireCall && - requireCall.argument.isString() && - (members.length === 0 || members[0] !== "__esModule") - ) { - enableStructuredExports(); - // It's possible to reexport __esModule, so we must convert to a dynamic module - if (members.length === 0) DynamicExports.setDynamic(parser.state); - const dep = new CommonJsExportRequireDependency( - expr.range, - null, - base, - members, - requireCall.argument.string, - requireCall.ids, - !parser.isStatementLevelExpression(expr) - ); - dep.loc = expr.loc; - dep.optional = !!parser.scope.inTry; - parser.state.module.addDependency(dep); - return true; + const result = {}; + for (const key of keys) { + let hasTrue = false; + let hasFalse = false; + for (const tp of targetProperties) { + const value = tp[key]; + switch (value) { + case true: + hasTrue = true; + break; + case false: + hasFalse = true; + break; } - if (members.length === 0) return; - enableStructuredExports(); - const remainingMembers = members; - checkNamespace( - parser.statementPath.length === 1 && - parser.isStatementLevelExpression(expr), - remainingMembers, - expr.right - ); - const dep = new CommonJsExportsDependency( - expr.left.range, - null, - base, - remainingMembers - ); - dep.loc = expr.loc; - parser.state.module.addDependency(dep); - parser.walkExpression(expr.right); - return true; - }; - parser.hooks.assignMemberChain - .for("exports") - .tap("CommonJsExportsParserPlugin", (expr, members) => { - return handleAssignExport(expr, "exports", members); - }); - parser.hooks.assignMemberChain - .for("this") - .tap("CommonJsExportsParserPlugin", (expr, members) => { - if (!parser.scope.topLevelScope) return; - return handleAssignExport(expr, "this", members); - }); - parser.hooks.assignMemberChain - .for("module") - .tap("CommonJsExportsParserPlugin", (expr, members) => { - if (members[0] !== "exports") return; - return handleAssignExport(expr, "module.exports", members.slice(1)); - }); - parser.hooks.call - .for("Object.defineProperty") - .tap("CommonJsExportsParserPlugin", expression => { - const expr = /** @type {import("estree").CallExpression} */ ( - expression - ); - if (!parser.isStatementLevelExpression(expr)) return; - if (expr.arguments.length !== 3) return; - if (expr.arguments[0].type === "SpreadElement") return; - if (expr.arguments[1].type === "SpreadElement") return; - if (expr.arguments[2].type === "SpreadElement") return; - const exportsArg = parser.evaluateExpression(expr.arguments[0]); - if (!exportsArg || !exportsArg.isIdentifier()) return; - if ( - exportsArg.identifier !== "exports" && - exportsArg.identifier !== "module.exports" && - (exportsArg.identifier !== "this" || !parser.scope.topLevelScope) - ) { - return; - } - const propertyArg = parser.evaluateExpression(expr.arguments[1]); - if (!propertyArg) return; - const property = propertyArg.asString(); - if (typeof property !== "string") return; - enableStructuredExports(); - const descArg = expr.arguments[2]; - checkNamespace( - parser.statementPath.length === 1, - [property], - getValueOfPropertyDescription(descArg) - ); - const dep = new CommonJsExportsDependency( - expr.range, - expr.arguments[2].range, - `Object.defineProperty(${exportsArg.identifier})`, - [property] - ); - dep.loc = expr.loc; - parser.state.module.addDependency(dep); - - parser.walkExpression(expr.arguments[2]); - return true; - }); + } + if (hasTrue || hasFalse) + result[key] = hasFalse && hasTrue ? null : hasTrue ? true : false; + } + return /** @type {TargetProperties} */ (result); +}; - // Self reference // - const handleAccessExport = (expr, base, members, call = undefined) => { - if (HarmonyExports.isEnabled(parser.state)) return; - if (members.length === 0) { - bailout(`${base} is used directly at ${formatLocation(expr.loc)}`); - } - if (call && members.length === 1) { - bailoutHint( - `${base}${propertyAccess( - members - )}(...) prevents optimization as ${base} is passed as call context at ${formatLocation( - expr.loc - )}` - ); - } - const dep = new CommonJsSelfReferenceDependency( - expr.range, - base, - members, - !!call - ); - dep.loc = expr.loc; - parser.state.module.addDependency(dep); - if (call) { - parser.walkExpressions(call.arguments); - } - return true; - }; - parser.hooks.callMemberChain - .for("exports") - .tap("CommonJsExportsParserPlugin", (expr, members) => { - return handleAccessExport(expr.callee, "exports", members, expr); - }); - parser.hooks.expressionMemberChain - .for("exports") - .tap("CommonJsExportsParserPlugin", (expr, members) => { - return handleAccessExport(expr, "exports", members); - }); - parser.hooks.expression - .for("exports") - .tap("CommonJsExportsParserPlugin", expr => { - return handleAccessExport(expr, "exports", []); - }); - parser.hooks.callMemberChain - .for("module") - .tap("CommonJsExportsParserPlugin", (expr, members) => { - if (members[0] !== "exports") return; - return handleAccessExport( - expr.callee, - "module.exports", - members.slice(1), - expr - ); - }); - parser.hooks.expressionMemberChain - .for("module") - .tap("CommonJsExportsParserPlugin", (expr, members) => { - if (members[0] !== "exports") return; - return handleAccessExport(expr, "module.exports", members.slice(1)); - }); - parser.hooks.expression - .for("module.exports") - .tap("CommonJsExportsParserPlugin", expr => { - return handleAccessExport(expr, "module.exports", []); - }); - parser.hooks.callMemberChain - .for("this") - .tap("CommonJsExportsParserPlugin", (expr, members) => { - if (!parser.scope.topLevelScope) return; - return handleAccessExport(expr.callee, "this", members, expr); - }); - parser.hooks.expressionMemberChain - .for("this") - .tap("CommonJsExportsParserPlugin", (expr, members) => { - if (!parser.scope.topLevelScope) return; - return handleAccessExport(expr, "this", members); - }); - parser.hooks.expression - .for("this") - .tap("CommonJsExportsParserPlugin", expr => { - if (!parser.scope.topLevelScope) return; - return handleAccessExport(expr, "this", []); - }); +/** + * @param {string[]} targets the targets + * @param {string} context the context directory + * @returns {TargetProperties} target properties + */ +const getTargetsProperties = (targets, context) => { + return mergeTargetProperties( + targets.map(t => getTargetProperties(t, context)) + ); +}; - // Bailouts // - parser.hooks.expression.for("module").tap("CommonJsPlugin", expr => { - bailout(); - const isHarmony = HarmonyExports.isEnabled(parser.state); - const dep = new ModuleDecoratorDependency( - isHarmony - ? RuntimeGlobals.harmonyModuleDecorator - : RuntimeGlobals.nodeModuleDecorator, - !isHarmony - ); - dep.loc = expr.loc; - parser.state.module.addDependency(dep); - return true; - }); - } -} -module.exports = CommonJsExportsParserPlugin; +exports.getDefaultTarget = getDefaultTarget; +exports.getTargetProperties = getTargetProperties; +exports.getTargetsProperties = getTargetsProperties; /***/ }), -/***/ 29496: +/***/ 44055: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; /* MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra + Author Tobias Koppers @sokra, Zackary Jackson @ScriptedAlchemy, Marais Rossouw @maraisr */ -const Template = __webpack_require__(92066); -const { equals } = __webpack_require__(21537); +const Dependency = __webpack_require__(50384); const makeSerializable = __webpack_require__(26522); -const propertyAccess = __webpack_require__(86709); -const ModuleDependency = __webpack_require__(80944); -/** @typedef {import("webpack-sources").ReplaceSource} ReplaceSource */ -/** @typedef {import("../Dependency")} Dependency */ -/** @typedef {import("../Dependency").ReferencedExport} ReferencedExport */ -/** @typedef {import("../DependencyTemplate").DependencyTemplateContext} DependencyTemplateContext */ -/** @typedef {import("../ModuleGraph")} ModuleGraph */ -/** @typedef {import("../util/runtime").RuntimeSpec} RuntimeSpec */ - -class CommonJsFullRequireDependency extends ModuleDependency { - /** - * @param {string} request the request string - * @param {[number, number]} range location in source code - * @param {string[]} names accessed properties on module - */ - constructor(request, range, names) { - super(request); - this.range = range; - this.names = names; - this.call = false; - this.asiSafe = undefined; - } +/** @typedef {import("./ContainerEntryModule").ExposeOptions} ExposeOptions */ +class ContainerEntryDependency extends Dependency { /** - * Returns list of exports referenced by this dependency - * @param {ModuleGraph} moduleGraph module graph - * @param {RuntimeSpec} runtime the runtime for which the module is analysed - * @returns {(string[] | ReferencedExport)[]} referenced exports + * @param {string} name entry name + * @param {[string, ExposeOptions][]} exposes list of exposed modules + * @param {string} shareScope name of the share scope */ - getReferencedExports(moduleGraph, runtime) { - if (this.call) { - const importedModule = moduleGraph.getModule(this); - if ( - !importedModule || - importedModule.getExportsType(moduleGraph, false) !== "namespace" - ) { - return [this.names.slice(0, -1)]; - } - } - return [this.names]; - } - - serialize(context) { - const { write } = context; - write(this.names); - write(this.call); - write(this.asiSafe); - super.serialize(context); - } - - deserialize(context) { - const { read } = context; - this.names = read(); - this.call = read(); - this.asiSafe = read(); - super.deserialize(context); - } - - get type() { - return "cjs full require"; - } - - get category() { - return "commonjs"; + constructor(name, exposes, shareScope) { + super(); + this.name = name; + this.exposes = exposes; + this.shareScope = shareScope; } -} - -CommonJsFullRequireDependency.Template = class CommonJsFullRequireDependencyTemplate extends ( - ModuleDependency.Template -) { - /** - * @param {Dependency} dependency the dependency for which the template should be applied - * @param {ReplaceSource} source the current replace source which can be modified - * @param {DependencyTemplateContext} templateContext the context object - * @returns {void} - */ - apply( - dependency, - source, - { - module, - runtimeTemplate, - moduleGraph, - chunkGraph, - runtimeRequirements, - runtime, - initFragments - } - ) { - const dep = /** @type {CommonJsFullRequireDependency} */ (dependency); - if (!dep.range) return; - const importedModule = moduleGraph.getModule(dep); - let requireExpr = runtimeTemplate.moduleExports({ - module: importedModule, - chunkGraph, - request: dep.request, - weak: dep.weak, - runtimeRequirements - }); - if (importedModule) { - const ids = dep.names; - const usedImported = moduleGraph - .getExportsInfo(importedModule) - .getUsedName(ids, runtime); - if (usedImported) { - const comment = equals(usedImported, ids) - ? "" - : Template.toNormalComment(propertyAccess(ids)) + " "; - const access = `${comment}${propertyAccess(usedImported)}`; - requireExpr = - dep.asiSafe === true - ? `(${requireExpr}${access})` - : `${requireExpr}${access}`; - } - } - source.replace(dep.range[0], dep.range[1] - 1, requireExpr); + + /** + * @returns {string | null} an identifier to merge equal requests + */ + getResourceIdentifier() { + return `container-entry-${this.name}`; } -}; + + get type() { + return "container entry"; + } + + get category() { + return "esm"; + } +} makeSerializable( - CommonJsFullRequireDependency, - "webpack/lib/dependencies/CommonJsFullRequireDependency" + ContainerEntryDependency, + "webpack/lib/container/ContainerEntryDependency" ); -module.exports = CommonJsFullRequireDependency; +module.exports = ContainerEntryDependency; /***/ }), -/***/ 78321: +/***/ 3234: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; /* MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra + Author Tobias Koppers @sokra, Zackary Jackson @ScriptedAlchemy, Marais Rossouw @maraisr */ -const CommentCompilationWarning = __webpack_require__(28151); +const { OriginalSource, RawSource } = __webpack_require__(96192); +const AsyncDependenciesBlock = __webpack_require__(11315); +const Module = __webpack_require__(85887); const RuntimeGlobals = __webpack_require__(49404); -const UnsupportedFeatureWarning = __webpack_require__(9532); -const { - evaluateToIdentifier, - evaluateToString, - expressionIsUnsupported, - toConstantDependency -} = __webpack_require__(28723); -const CommonJsFullRequireDependency = __webpack_require__(29496); -const CommonJsRequireContextDependency = __webpack_require__(84175); -const CommonJsRequireDependency = __webpack_require__(38604); -const ConstDependency = __webpack_require__(60864); -const ContextDependencyHelpers = __webpack_require__(7114); -const LocalModuleDependency = __webpack_require__(67494); -const { getLocalModule } = __webpack_require__(6311); -const RequireHeaderDependency = __webpack_require__(57010); -const RequireResolveContextDependency = __webpack_require__(48789); -const RequireResolveDependency = __webpack_require__(93172); -const RequireResolveHeaderDependency = __webpack_require__(24128); +const Template = __webpack_require__(92066); +const makeSerializable = __webpack_require__(26522); +const ContainerExposedDependency = __webpack_require__(50); -/** @typedef {import("../../declarations/WebpackOptions").JavascriptParserOptions} JavascriptParserOptions */ +/** @typedef {import("../../declarations/WebpackOptions").WebpackOptionsNormalized} WebpackOptions */ +/** @typedef {import("../ChunkGraph")} ChunkGraph */ +/** @typedef {import("../ChunkGroup")} ChunkGroup */ +/** @typedef {import("../Compilation")} Compilation */ +/** @typedef {import("../Module").CodeGenerationContext} CodeGenerationContext */ +/** @typedef {import("../Module").CodeGenerationResult} CodeGenerationResult */ +/** @typedef {import("../Module").LibIdentOptions} LibIdentOptions */ +/** @typedef {import("../Module").NeedBuildContext} NeedBuildContext */ +/** @typedef {import("../RequestShortener")} RequestShortener */ +/** @typedef {import("../ResolverFactory").ResolverWithOptions} ResolverWithOptions */ +/** @typedef {import("../WebpackError")} WebpackError */ +/** @typedef {import("../util/Hash")} Hash */ +/** @typedef {import("../util/fs").InputFileSystem} InputFileSystem */ +/** @typedef {import("./ContainerEntryDependency")} ContainerEntryDependency */ -class CommonJsImportsParserPlugin { +/** + * @typedef {Object} ExposeOptions + * @property {string[]} import requests to exposed modules (last one is exported) + * @property {string} name custom chunk name for the exposed module + */ + +const SOURCE_TYPES = new Set(["javascript"]); + +class ContainerEntryModule extends Module { /** - * @param {JavascriptParserOptions} options parser options + * @param {string} name container entry name + * @param {[string, ExposeOptions][]} exposes list of exposed modules + * @param {string} shareScope name of the share scope */ - constructor(options) { - this.options = options; + constructor(name, exposes, shareScope) { + super("javascript/dynamic", null); + this._name = name; + this._exposes = exposes; + this._shareScope = shareScope; } - apply(parser) { - const options = this.options; + /** + * @returns {Set} types available (do not mutate) + */ + getSourceTypes() { + return SOURCE_TYPES; + } - // metadata // - const tapRequireExpression = (expression, getMembers) => { - parser.hooks.typeof - .for(expression) - .tap( - "CommonJsPlugin", - toConstantDependency(parser, JSON.stringify("function")) - ); - parser.hooks.evaluateTypeof - .for(expression) - .tap("CommonJsPlugin", evaluateToString("function")); - parser.hooks.evaluateIdentifier - .for(expression) - .tap( - "CommonJsPlugin", - evaluateToIdentifier(expression, "require", getMembers, true) - ); - }; - tapRequireExpression("require", () => []); - tapRequireExpression("require.resolve", () => ["resolve"]); - tapRequireExpression("require.resolveWeak", () => ["resolveWeak"]); + /** + * @returns {string} a unique identifier of the module + */ + identifier() { + return `container entry (${this._shareScope}) ${JSON.stringify( + this._exposes + )}`; + } - // Weird stuff // - parser.hooks.assign.for("require").tap("CommonJsPlugin", expr => { - // to not leak to global "require", we need to define a local require here. - const dep = new ConstDependency("var require;", 0); - dep.loc = expr.loc; - parser.state.module.addPresentationalDependency(dep); - return true; - }); + /** + * @param {RequestShortener} requestShortener the request shortener + * @returns {string} a user readable identifier of the module + */ + readableIdentifier(requestShortener) { + return `container entry`; + } - // Unsupported // - parser.hooks.expression - .for("require.main.require") - .tap( - "CommonJsPlugin", - expressionIsUnsupported( - parser, - "require.main.require is not supported by webpack." - ) - ); - parser.hooks.call - .for("require.main.require") - .tap( - "CommonJsPlugin", - expressionIsUnsupported( - parser, - "require.main.require is not supported by webpack." - ) - ); - parser.hooks.expression - .for("module.parent.require") - .tap( - "CommonJsPlugin", - expressionIsUnsupported( - parser, - "module.parent.require is not supported by webpack." - ) - ); - parser.hooks.call - .for("module.parent.require") - .tap( - "CommonJsPlugin", - expressionIsUnsupported( - parser, - "module.parent.require is not supported by webpack." - ) - ); + /** + * @param {LibIdentOptions} options options + * @returns {string | null} an identifier for library inclusion + */ + libIdent(options) { + return `webpack/container/entry/${this._name}`; + } - // renaming // - parser.hooks.canRename.for("require").tap("CommonJsPlugin", () => true); - parser.hooks.rename.for("require").tap("CommonJsPlugin", expr => { - // To avoid "not defined" error, replace the value with undefined - const dep = new ConstDependency("undefined", expr.range); - dep.loc = expr.loc; - parser.state.module.addPresentationalDependency(dep); - return false; - }); + /** + * @param {NeedBuildContext} context context info + * @param {function(WebpackError=, boolean=): void} callback callback function, returns true, if the module needs a rebuild + * @returns {void} + */ + needBuild(context, callback) { + return callback(null, !this.buildMeta); + } - // inspection // - parser.hooks.expression - .for("require.cache") - .tap( - "CommonJsImportsParserPlugin", - toConstantDependency(parser, RuntimeGlobals.moduleCache, [ - RuntimeGlobals.moduleCache, - RuntimeGlobals.moduleId, - RuntimeGlobals.moduleLoaded - ]) - ); + /** + * @param {WebpackOptions} options webpack options + * @param {Compilation} compilation the compilation + * @param {ResolverWithOptions} resolver the resolver + * @param {InputFileSystem} fs the file system + * @param {function(WebpackError=): void} callback callback function + * @returns {void} + */ + build(options, compilation, resolver, fs, callback) { + this.buildMeta = {}; + this.buildInfo = { + strict: true, + topLevelDeclarations: new Set(["moduleMap", "get", "init"]) + }; - // require as expression // - parser.hooks.expression - .for("require") - .tap("CommonJsImportsParserPlugin", expr => { - const dep = new CommonJsRequireContextDependency( - { - request: options.unknownContextRequest, - recursive: options.unknownContextRecursive, - regExp: options.unknownContextRegExp, - mode: "sync" - }, - expr.range, - undefined, - parser.scope.inShorthand - ); - dep.critical = - options.unknownContextCritical && - "require function is used in a way in which dependencies cannot be statically extracted"; - dep.loc = expr.loc; - dep.optional = !!parser.scope.inTry; - parser.state.current.addDependency(dep); - return true; - }); + this.clearDependenciesAndBlocks(); - // require // - const processRequireItem = (expr, param) => { - if (param.isString()) { - const dep = new CommonJsRequireDependency(param.string, param.range); - dep.loc = expr.loc; - dep.optional = !!parser.scope.inTry; - parser.state.current.addDependency(dep); - return true; - } - }; - const processRequireContext = (expr, param) => { - const dep = ContextDependencyHelpers.create( - CommonJsRequireContextDependency, - expr.range, - param, - expr, - options, + for (const [name, options] of this._exposes) { + const block = new AsyncDependenciesBlock( { - category: "commonjs" + name: options.name }, - parser + { name }, + options.import[options.import.length - 1] ); - if (!dep) return; - dep.loc = expr.loc; - dep.optional = !!parser.scope.inTry; - parser.state.current.addDependency(dep); - return true; - }; - const createRequireHandler = callNew => expr => { - if (options.commonjsMagicComments) { - const { options: requireOptions, errors: commentErrors } = - parser.parseCommentOptions(expr.range); + let idx = 0; + for (const request of options.import) { + const dep = new ContainerExposedDependency(name, request); + dep.loc = { + name, + index: idx++ + }; - if (commentErrors) { - for (const e of commentErrors) { - const { comment } = e; - parser.state.module.addWarning( - new CommentCompilationWarning( - `Compilation error while processing magic comment(-s): /*${comment.value}*/: ${e.message}`, - comment.loc - ) - ); - } - } - if (requireOptions) { - if (requireOptions.webpackIgnore !== undefined) { - if (typeof requireOptions.webpackIgnore !== "boolean") { - parser.state.module.addWarning( - new UnsupportedFeatureWarning( - `\`webpackIgnore\` expected a boolean, but received: ${requireOptions.webpackIgnore}.`, - expr.loc - ) - ); - } else { - // Do not instrument `require()` if `webpackIgnore` is `true` - if (requireOptions.webpackIgnore) { - return true; - } - } - } - } + block.addDependency(dep); } + this.addBlock(block); + } - if (expr.arguments.length !== 1) return; - let localModule; - const param = parser.evaluateExpression(expr.arguments[0]); - if (param.isConditional()) { - let isExpression = false; - for (const p of param.options) { - const result = processRequireItem(expr, p); - if (result === undefined) { - isExpression = true; - } - } - if (!isExpression) { - const dep = new RequireHeaderDependency(expr.callee.range); - dep.loc = expr.loc; - parser.state.module.addPresentationalDependency(dep); - return true; - } - } - if ( - param.isString() && - (localModule = getLocalModule(parser.state, param.string)) - ) { - localModule.flagUsed(); - const dep = new LocalModuleDependency(localModule, expr.range, callNew); - dep.loc = expr.loc; - parser.state.module.addPresentationalDependency(dep); - return true; - } else { - const result = processRequireItem(expr, param); - if (result === undefined) { - processRequireContext(expr, param); - } else { - const dep = new RequireHeaderDependency(expr.callee.range); - dep.loc = expr.loc; - parser.state.module.addPresentationalDependency(dep); - } - return true; - } - }; - parser.hooks.call - .for("require") - .tap("CommonJsImportsParserPlugin", createRequireHandler(false)); - parser.hooks.new - .for("require") - .tap("CommonJsImportsParserPlugin", createRequireHandler(true)); - parser.hooks.call - .for("module.require") - .tap("CommonJsImportsParserPlugin", createRequireHandler(false)); - parser.hooks.new - .for("module.require") - .tap("CommonJsImportsParserPlugin", createRequireHandler(true)); + callback(); + } - // require with property access // - const chainHandler = (expr, calleeMembers, callExpr, members) => { - if (callExpr.arguments.length !== 1) return; - const param = parser.evaluateExpression(callExpr.arguments[0]); - if (param.isString() && !getLocalModule(parser.state, param.string)) { - const dep = new CommonJsFullRequireDependency( - param.string, - expr.range, - members - ); - dep.asiSafe = !parser.isAsiPosition(expr.range[0]); - dep.optional = !!parser.scope.inTry; - dep.loc = expr.loc; - parser.state.current.addDependency(dep); - return true; - } - }; - const callChainHandler = (expr, calleeMembers, callExpr, members) => { - if (callExpr.arguments.length !== 1) return; - const param = parser.evaluateExpression(callExpr.arguments[0]); - if (param.isString() && !getLocalModule(parser.state, param.string)) { - const dep = new CommonJsFullRequireDependency( - param.string, - expr.callee.range, - members - ); - dep.call = true; - dep.asiSafe = !parser.isAsiPosition(expr.range[0]); - dep.optional = !!parser.scope.inTry; - dep.loc = expr.callee.loc; - parser.state.current.addDependency(dep); - parser.walkExpressions(expr.arguments); - return true; - } - }; - parser.hooks.memberChainOfCallMemberChain - .for("require") - .tap("CommonJsImportsParserPlugin", chainHandler); - parser.hooks.memberChainOfCallMemberChain - .for("module.require") - .tap("CommonJsImportsParserPlugin", chainHandler); - parser.hooks.callMemberChainOfCallMemberChain - .for("require") - .tap("CommonJsImportsParserPlugin", callChainHandler); - parser.hooks.callMemberChainOfCallMemberChain - .for("module.require") - .tap("CommonJsImportsParserPlugin", callChainHandler); + /** + * @param {CodeGenerationContext} context context for code generation + * @returns {CodeGenerationResult} result + */ + codeGeneration({ moduleGraph, chunkGraph, runtimeTemplate }) { + const sources = new Map(); + const runtimeRequirements = new Set([ + RuntimeGlobals.definePropertyGetters, + RuntimeGlobals.hasOwnProperty, + RuntimeGlobals.exports + ]); + const getters = []; - // require.resolve // - const processResolve = (expr, weak) => { - if (expr.arguments.length !== 1) return; - const param = parser.evaluateExpression(expr.arguments[0]); - if (param.isConditional()) { - for (const option of param.options) { - const result = processResolveItem(expr, option, weak); - if (result === undefined) { - processResolveContext(expr, option, weak); - } - } - const dep = new RequireResolveHeaderDependency(expr.callee.range); - dep.loc = expr.loc; - parser.state.module.addPresentationalDependency(dep); - return true; + for (const block of this.blocks) { + const { dependencies } = block; + + const modules = dependencies.map(dependency => { + const dep = /** @type {ContainerExposedDependency} */ (dependency); + return { + name: dep.exposedName, + module: moduleGraph.getModule(dep), + request: dep.userRequest + }; + }); + + let str; + + if (modules.some(m => !m.module)) { + str = runtimeTemplate.throwMissingModuleErrorBlock({ + request: modules.map(m => m.request).join(", ") + }); } else { - const result = processResolveItem(expr, param, weak); - if (result === undefined) { - processResolveContext(expr, param, weak); - } - const dep = new RequireResolveHeaderDependency(expr.callee.range); - dep.loc = expr.loc; - parser.state.module.addPresentationalDependency(dep); - return true; - } - }; - const processResolveItem = (expr, param, weak) => { - if (param.isString()) { - const dep = new RequireResolveDependency(param.string, param.range); - dep.loc = expr.loc; - dep.optional = !!parser.scope.inTry; - dep.weak = weak; - parser.state.current.addDependency(dep); - return true; - } - }; - const processResolveContext = (expr, param, weak) => { - const dep = ContextDependencyHelpers.create( - RequireResolveContextDependency, - param.range, - param, - expr, - options, - { - category: "commonjs", - mode: weak ? "weak" : "sync" - }, - parser + str = `return ${runtimeTemplate.blockPromise({ + block, + message: "", + chunkGraph, + runtimeRequirements + })}.then(${runtimeTemplate.returningFunction( + runtimeTemplate.returningFunction( + `(${modules + .map(({ module, request }) => + runtimeTemplate.moduleRaw({ + module, + chunkGraph, + request, + weak: false, + runtimeRequirements + }) + ) + .join(", ")})` + ) + )});`; + } + + getters.push( + `${JSON.stringify(modules[0].name)}: ${runtimeTemplate.basicFunction( + "", + str + )}` ); - if (!dep) return; - dep.loc = expr.loc; - dep.optional = !!parser.scope.inTry; - parser.state.current.addDependency(dep); - return true; + } + + const source = Template.asString([ + `var moduleMap = {`, + Template.indent(getters.join(",\n")), + "};", + `var get = ${runtimeTemplate.basicFunction("module, getScope", [ + `${RuntimeGlobals.currentRemoteGetScope} = getScope;`, + // reusing the getScope variable to avoid creating a new var (and module is also used later) + "getScope = (", + Template.indent([ + `${RuntimeGlobals.hasOwnProperty}(moduleMap, module)`, + Template.indent([ + "? moduleMap[module]()", + `: Promise.resolve().then(${runtimeTemplate.basicFunction( + "", + "throw new Error('Module \"' + module + '\" does not exist in container.');" + )})` + ]) + ]), + ");", + `${RuntimeGlobals.currentRemoteGetScope} = undefined;`, + "return getScope;" + ])};`, + `var init = ${runtimeTemplate.basicFunction("shareScope, initScope", [ + `if (!${RuntimeGlobals.shareScopeMap}) return;`, + `var oldScope = ${RuntimeGlobals.shareScopeMap}[${JSON.stringify( + this._shareScope + )}];`, + `var name = ${JSON.stringify(this._shareScope)}`, + `if(oldScope && oldScope !== shareScope) throw new Error("Container initialization failed as it has already been initialized with a different share scope");`, + `${RuntimeGlobals.shareScopeMap}[name] = shareScope;`, + `return ${RuntimeGlobals.initializeSharing}(name, initScope);` + ])};`, + "", + "// This exports getters to disallow modifications", + `${RuntimeGlobals.definePropertyGetters}(exports, {`, + Template.indent([ + `get: ${runtimeTemplate.returningFunction("get")},`, + `init: ${runtimeTemplate.returningFunction("init")}` + ]), + "});" + ]); + + sources.set( + "javascript", + this.useSourceMap || this.useSimpleSourceMap + ? new OriginalSource(source, "webpack/container-entry") + : new RawSource(source) + ); + + return { + sources, + runtimeRequirements }; + } - parser.hooks.call - .for("require.resolve") - .tap("RequireResolveDependencyParserPlugin", expr => { - return processResolve(expr, false); - }); - parser.hooks.call - .for("require.resolveWeak") - .tap("RequireResolveDependencyParserPlugin", expr => { - return processResolve(expr, true); - }); + /** + * @param {string=} type the source type for which the size should be estimated + * @returns {number} the estimated size of the module (must be non-zero) + */ + size(type) { + return 42; + } + + serialize(context) { + const { write } = context; + write(this._name); + write(this._exposes); + write(this._shareScope); + super.serialize(context); + } + + static deserialize(context) { + const { read } = context; + const obj = new ContainerEntryModule(read(), read(), read()); + obj.deserialize(context); + return obj; } } -module.exports = CommonJsImportsParserPlugin; + +makeSerializable( + ContainerEntryModule, + "webpack/lib/container/ContainerEntryModule" +); + +module.exports = ContainerEntryModule; /***/ }), -/***/ 8615: +/***/ 52644: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; /* MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra + Author Tobias Koppers @sokra, Zackary Jackson @ScriptedAlchemy, Marais Rossouw @maraisr */ -const RuntimeGlobals = __webpack_require__(49404); -const RuntimeModule = __webpack_require__(61439); -const SelfModuleFactory = __webpack_require__(31374); -const Template = __webpack_require__(92066); -const CommonJsExportsDependency = __webpack_require__(9585); -const CommonJsFullRequireDependency = __webpack_require__(29496); -const CommonJsRequireContextDependency = __webpack_require__(84175); -const CommonJsRequireDependency = __webpack_require__(38604); -const CommonJsSelfReferenceDependency = __webpack_require__(69217); -const ModuleDecoratorDependency = __webpack_require__(58969); -const RequireHeaderDependency = __webpack_require__(57010); -const RequireResolveContextDependency = __webpack_require__(48789); -const RequireResolveDependency = __webpack_require__(93172); -const RequireResolveHeaderDependency = __webpack_require__(24128); -const RuntimeRequirementsDependency = __webpack_require__(75941); +const ModuleFactory = __webpack_require__(61574); +const ContainerEntryModule = __webpack_require__(3234); -const CommonJsExportsParserPlugin = __webpack_require__(49577); -const CommonJsImportsParserPlugin = __webpack_require__(78321); +/** @typedef {import("../ModuleFactory").ModuleFactoryCreateData} ModuleFactoryCreateData */ +/** @typedef {import("../ModuleFactory").ModuleFactoryResult} ModuleFactoryResult */ +/** @typedef {import("./ContainerEntryDependency")} ContainerEntryDependency */ -const { - evaluateToIdentifier, - toConstantDependency -} = __webpack_require__(28723); -const CommonJsExportRequireDependency = __webpack_require__(76922); +module.exports = class ContainerEntryModuleFactory extends ModuleFactory { + /** + * @param {ModuleFactoryCreateData} data data object + * @param {function(Error=, ModuleFactoryResult=): void} callback callback + * @returns {void} + */ + create({ dependencies: [dependency] }, callback) { + const dep = /** @type {ContainerEntryDependency} */ (dependency); + callback(null, { + module: new ContainerEntryModule(dep.name, dep.exposes, dep.shareScope) + }); + } +}; -class CommonJsPlugin { - apply(compiler) { - compiler.hooks.compilation.tap( - "CommonJsPlugin", - (compilation, { contextModuleFactory, normalModuleFactory }) => { - compilation.dependencyFactories.set( - CommonJsRequireDependency, - normalModuleFactory - ); - compilation.dependencyTemplates.set( - CommonJsRequireDependency, - new CommonJsRequireDependency.Template() - ); - compilation.dependencyFactories.set( - CommonJsFullRequireDependency, - normalModuleFactory - ); - compilation.dependencyTemplates.set( - CommonJsFullRequireDependency, - new CommonJsFullRequireDependency.Template() - ); +/***/ }), - compilation.dependencyFactories.set( - CommonJsRequireContextDependency, - contextModuleFactory - ); - compilation.dependencyTemplates.set( - CommonJsRequireContextDependency, - new CommonJsRequireContextDependency.Template() - ); +/***/ 50: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - compilation.dependencyFactories.set( - RequireResolveDependency, - normalModuleFactory - ); - compilation.dependencyTemplates.set( - RequireResolveDependency, - new RequireResolveDependency.Template() - ); +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra, Zackary Jackson @ScriptedAlchemy, Marais Rossouw @maraisr +*/ - compilation.dependencyFactories.set( - RequireResolveContextDependency, - contextModuleFactory - ); - compilation.dependencyTemplates.set( - RequireResolveContextDependency, - new RequireResolveContextDependency.Template() - ); - compilation.dependencyTemplates.set( - RequireResolveHeaderDependency, - new RequireResolveHeaderDependency.Template() - ); - compilation.dependencyTemplates.set( - RequireHeaderDependency, - new RequireHeaderDependency.Template() - ); +const ModuleDependency = __webpack_require__(80944); +const makeSerializable = __webpack_require__(26522); - compilation.dependencyTemplates.set( - CommonJsExportsDependency, - new CommonJsExportsDependency.Template() - ); +class ContainerExposedDependency extends ModuleDependency { + /** + * @param {string} exposedName public name + * @param {string} request request to module + */ + constructor(exposedName, request) { + super(request); + this.exposedName = exposedName; + } - compilation.dependencyFactories.set( - CommonJsExportRequireDependency, - normalModuleFactory - ); - compilation.dependencyTemplates.set( - CommonJsExportRequireDependency, - new CommonJsExportRequireDependency.Template() - ); + get type() { + return "container exposed"; + } - const selfFactory = new SelfModuleFactory(compilation.moduleGraph); + get category() { + return "esm"; + } - compilation.dependencyFactories.set( - CommonJsSelfReferenceDependency, - selfFactory - ); - compilation.dependencyTemplates.set( - CommonJsSelfReferenceDependency, - new CommonJsSelfReferenceDependency.Template() - ); + /** + * @returns {string | null} an identifier to merge equal requests + */ + getResourceIdentifier() { + return `exposed dependency ${this.exposedName}=${this.request}`; + } - compilation.dependencyFactories.set( - ModuleDecoratorDependency, - selfFactory - ); - compilation.dependencyTemplates.set( - ModuleDecoratorDependency, - new ModuleDecoratorDependency.Template() - ); + serialize(context) { + context.write(this.exposedName); + super.serialize(context); + } - compilation.hooks.runtimeRequirementInModule - .for(RuntimeGlobals.harmonyModuleDecorator) - .tap("CommonJsPlugin", (module, set) => { - set.add(RuntimeGlobals.module); - set.add(RuntimeGlobals.requireScope); - }); + deserialize(context) { + this.exposedName = context.read(); + super.deserialize(context); + } +} - compilation.hooks.runtimeRequirementInModule - .for(RuntimeGlobals.nodeModuleDecorator) - .tap("CommonJsPlugin", (module, set) => { - set.add(RuntimeGlobals.module); - set.add(RuntimeGlobals.requireScope); - }); +makeSerializable( + ContainerExposedDependency, + "webpack/lib/container/ContainerExposedDependency" +); - compilation.hooks.runtimeRequirementInTree - .for(RuntimeGlobals.harmonyModuleDecorator) - .tap("CommonJsPlugin", (chunk, set) => { - compilation.addRuntimeModule( - chunk, - new HarmonyModuleDecoratorRuntimeModule() - ); - }); +module.exports = ContainerExposedDependency; - compilation.hooks.runtimeRequirementInTree - .for(RuntimeGlobals.nodeModuleDecorator) - .tap("CommonJsPlugin", (chunk, set) => { - compilation.addRuntimeModule( - chunk, - new NodeModuleDecoratorRuntimeModule() - ); - }); - const handler = (parser, parserOptions) => { - if (parserOptions.commonjs !== undefined && !parserOptions.commonjs) - return; - parser.hooks.typeof - .for("module") - .tap( - "CommonJsPlugin", - toConstantDependency(parser, JSON.stringify("object")) - ); +/***/ }), - parser.hooks.expression - .for("require.main") - .tap( - "CommonJsPlugin", - toConstantDependency( - parser, - `${RuntimeGlobals.moduleCache}[${RuntimeGlobals.entryModuleId}]`, - [RuntimeGlobals.moduleCache, RuntimeGlobals.entryModuleId] - ) - ); - parser.hooks.expression - .for("module.loaded") - .tap("CommonJsPlugin", expr => { - parser.state.module.buildInfo.moduleConcatenationBailout = - "module.loaded"; - const dep = new RuntimeRequirementsDependency([ - RuntimeGlobals.moduleLoaded - ]); - dep.loc = expr.loc; - parser.state.module.addPresentationalDependency(dep); - return true; - }); +/***/ 20962: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - parser.hooks.expression - .for("module.id") - .tap("CommonJsPlugin", expr => { - parser.state.module.buildInfo.moduleConcatenationBailout = - "module.id"; - const dep = new RuntimeRequirementsDependency([ - RuntimeGlobals.moduleId - ]); - dep.loc = expr.loc; - parser.state.module.addPresentationalDependency(dep); - return true; - }); +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra, Zackary Jackson @ScriptedAlchemy, Marais Rossouw @maraisr +*/ - parser.hooks.evaluateIdentifier.for("module.hot").tap( - "CommonJsPlugin", - evaluateToIdentifier("module.hot", "module", () => ["hot"], null) - ); - new CommonJsImportsParserPlugin(parserOptions).apply(parser); - new CommonJsExportsParserPlugin(compilation.moduleGraph).apply( - parser - ); - }; - normalModuleFactory.hooks.parser - .for("javascript/auto") - .tap("CommonJsPlugin", handler); - normalModuleFactory.hooks.parser - .for("javascript/dynamic") - .tap("CommonJsPlugin", handler); +const createSchemaValidation = __webpack_require__(77695); +const ContainerEntryDependency = __webpack_require__(44055); +const ContainerEntryModuleFactory = __webpack_require__(52644); +const ContainerExposedDependency = __webpack_require__(50); +const { parseOptions } = __webpack_require__(56084); + +/** @typedef {import("../../declarations/plugins/container/ContainerPlugin").ContainerPluginOptions} ContainerPluginOptions */ +/** @typedef {import("../Compiler")} Compiler */ + +const validate = createSchemaValidation( + __webpack_require__(3844), + () => __webpack_require__(18374), + { + name: "Container Plugin", + baseDataPath: "options" + } +); + +const PLUGIN_NAME = "ContainerPlugin"; + +class ContainerPlugin { + /** + * @param {ContainerPluginOptions} options options + */ + constructor(options) { + validate(options); + + this._options = { + name: options.name, + shareScope: options.shareScope || "default", + library: options.library || { + type: "var", + name: options.name + }, + runtime: options.runtime, + filename: options.filename || undefined, + exposes: parseOptions( + options.exposes, + item => ({ + import: Array.isArray(item) ? item : [item], + name: undefined + }), + item => ({ + import: Array.isArray(item.import) ? item.import : [item.import], + name: item.name || undefined + }) + ) + }; + } + + /** + * Apply the plugin + * @param {Compiler} compiler the compiler instance + * @returns {void} + */ + apply(compiler) { + const { name, exposes, shareScope, filename, library, runtime } = + this._options; + + compiler.options.output.enabledLibraryTypes.push(library.type); + + compiler.hooks.make.tapAsync(PLUGIN_NAME, (compilation, callback) => { + const dep = new ContainerEntryDependency(name, exposes, shareScope); + dep.loc = { name }; + compilation.addEntry( + compilation.options.context, + dep, + { + name, + filename, + runtime, + library + }, + error => { + if (error) return callback(error); + callback(); + } + ); + }); + + compiler.hooks.thisCompilation.tap( + PLUGIN_NAME, + (compilation, { normalModuleFactory }) => { + compilation.dependencyFactories.set( + ContainerEntryDependency, + new ContainerEntryModuleFactory() + ); + + compilation.dependencyFactories.set( + ContainerExposedDependency, + normalModuleFactory + ); } ); } } -class HarmonyModuleDecoratorRuntimeModule extends RuntimeModule { - constructor() { - super("harmony module decorator"); +module.exports = ContainerPlugin; + + +/***/ }), + +/***/ 17813: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra and Zackary Jackson @ScriptedAlchemy +*/ + + + +const ExternalsPlugin = __webpack_require__(361); +const RuntimeGlobals = __webpack_require__(49404); +const createSchemaValidation = __webpack_require__(77695); +const FallbackDependency = __webpack_require__(41061); +const FallbackItemDependency = __webpack_require__(33393); +const FallbackModuleFactory = __webpack_require__(88180); +const RemoteModule = __webpack_require__(581); +const RemoteRuntimeModule = __webpack_require__(4603); +const RemoteToExternalDependency = __webpack_require__(44637); +const { parseOptions } = __webpack_require__(56084); + +/** @typedef {import("../../declarations/plugins/container/ContainerReferencePlugin").ContainerReferencePluginOptions} ContainerReferencePluginOptions */ +/** @typedef {import("../../declarations/plugins/container/ContainerReferencePlugin").RemotesConfig} RemotesConfig */ +/** @typedef {import("../Compiler")} Compiler */ + +const validate = createSchemaValidation( + __webpack_require__(4464), + () => + __webpack_require__(31339), + { + name: "Container Reference Plugin", + baseDataPath: "options" } +); + +const slashCode = "/".charCodeAt(0); +class ContainerReferencePlugin { /** - * @returns {string} runtime code + * @param {ContainerReferencePluginOptions} options options */ - generate() { - const { runtimeTemplate } = this.compilation; - return Template.asString([ - `${ - RuntimeGlobals.harmonyModuleDecorator - } = ${runtimeTemplate.basicFunction("module", [ - "module = Object.create(module);", - "if (!module.children) module.children = [];", - "Object.defineProperty(module, 'exports', {", - Template.indent([ - "enumerable: true,", - `set: ${runtimeTemplate.basicFunction("", [ - "throw new Error('ES Modules may not assign module.exports or exports.*, Use ESM export syntax, instead: ' + module.id);" - ])}` - ]), - "});", - "return module;" - ])};` - ]); - } -} + constructor(options) { + validate(options); -class NodeModuleDecoratorRuntimeModule extends RuntimeModule { - constructor() { - super("node module decorator"); + this._remoteType = options.remoteType; + this._remotes = parseOptions( + options.remotes, + item => ({ + external: Array.isArray(item) ? item : [item], + shareScope: options.shareScope || "default" + }), + item => ({ + external: Array.isArray(item.external) + ? item.external + : [item.external], + shareScope: item.shareScope || options.shareScope || "default" + }) + ); } /** - * @returns {string} runtime code + * Apply the plugin + * @param {Compiler} compiler the compiler instance + * @returns {void} */ - generate() { - const { runtimeTemplate } = this.compilation; - return Template.asString([ - `${RuntimeGlobals.nodeModuleDecorator} = ${runtimeTemplate.basicFunction( - "module", - [ - "module.paths = [];", - "if (!module.children) module.children = [];", - "return module;" - ] - )};` - ]); + apply(compiler) { + const { _remotes: remotes, _remoteType: remoteType } = this; + + /** @type {Record} */ + const remoteExternals = {}; + for (const [key, config] of remotes) { + let i = 0; + for (const external of config.external) { + if (external.startsWith("internal ")) continue; + remoteExternals[ + `webpack/container/reference/${key}${i ? `/fallback-${i}` : ""}` + ] = external; + i++; + } + } + + new ExternalsPlugin(remoteType, remoteExternals).apply(compiler); + + compiler.hooks.compilation.tap( + "ContainerReferencePlugin", + (compilation, { normalModuleFactory }) => { + compilation.dependencyFactories.set( + RemoteToExternalDependency, + normalModuleFactory + ); + + compilation.dependencyFactories.set( + FallbackItemDependency, + normalModuleFactory + ); + + compilation.dependencyFactories.set( + FallbackDependency, + new FallbackModuleFactory() + ); + + normalModuleFactory.hooks.factorize.tap( + "ContainerReferencePlugin", + data => { + if (!data.request.includes("!")) { + for (const [key, config] of remotes) { + if ( + data.request.startsWith(`${key}`) && + (data.request.length === key.length || + data.request.charCodeAt(key.length) === slashCode) + ) { + return new RemoteModule( + data.request, + config.external.map((external, i) => + external.startsWith("internal ") + ? external.slice(9) + : `webpack/container/reference/${key}${ + i ? `/fallback-${i}` : "" + }` + ), + `.${data.request.slice(key.length)}`, + config.shareScope + ); + } + } + } + } + ); + + compilation.hooks.runtimeRequirementInTree + .for(RuntimeGlobals.ensureChunkHandlers) + .tap("ContainerReferencePlugin", (chunk, set) => { + set.add(RuntimeGlobals.module); + set.add(RuntimeGlobals.moduleFactoriesAddOnly); + set.add(RuntimeGlobals.hasOwnProperty); + set.add(RuntimeGlobals.initializeSharing); + set.add(RuntimeGlobals.shareScopeMap); + compilation.addRuntimeModule(chunk, new RemoteRuntimeModule()); + }); + } + ); } } -module.exports = CommonJsPlugin; +module.exports = ContainerReferencePlugin; /***/ }), -/***/ 84175: +/***/ 41061: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; @@ -76598,59 +73648,55 @@ module.exports = CommonJsPlugin; +const Dependency = __webpack_require__(50384); const makeSerializable = __webpack_require__(26522); -const ContextDependency = __webpack_require__(67840); -const ContextDependencyTemplateAsRequireCall = __webpack_require__(18259); -class CommonJsRequireContextDependency extends ContextDependency { - constructor(options, range, valueRange, inShorthand) { - super(options); +class FallbackDependency extends Dependency { + constructor(requests) { + super(); + this.requests = requests; + } - this.range = range; - this.valueRange = valueRange; - // inShorthand must be serialized by subclasses that use it - this.inShorthand = inShorthand; + /** + * @returns {string | null} an identifier to merge equal requests + */ + getResourceIdentifier() { + return `fallback ${this.requests.join(" ")}`; } get type() { - return "cjs require context"; + return "fallback"; + } + + get category() { + return "esm"; } serialize(context) { const { write } = context; - - write(this.range); - write(this.valueRange); - write(this.inShorthand); - + write(this.requests); super.serialize(context); } - deserialize(context) { + static deserialize(context) { const { read } = context; - - this.range = read(); - this.valueRange = read(); - this.inShorthand = read(); - - super.deserialize(context); + const obj = new FallbackDependency(read()); + obj.deserialize(context); + return obj; } } makeSerializable( - CommonJsRequireContextDependency, - "webpack/lib/dependencies/CommonJsRequireContextDependency" + FallbackDependency, + "webpack/lib/container/FallbackDependency" ); -CommonJsRequireContextDependency.Template = - ContextDependencyTemplateAsRequireCall; - -module.exports = CommonJsRequireContextDependency; +module.exports = FallbackDependency; /***/ }), -/***/ 38604: +/***/ 33393: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; @@ -76661,459 +73707,664 @@ module.exports = CommonJsRequireContextDependency; -const makeSerializable = __webpack_require__(26522); const ModuleDependency = __webpack_require__(80944); -const ModuleDependencyTemplateAsId = __webpack_require__(35795); +const makeSerializable = __webpack_require__(26522); -class CommonJsRequireDependency extends ModuleDependency { - constructor(request, range) { +class FallbackItemDependency extends ModuleDependency { + constructor(request) { super(request); - this.range = range; } get type() { - return "cjs require"; + return "fallback item"; } get category() { - return "commonjs"; + return "esm"; } } -CommonJsRequireDependency.Template = ModuleDependencyTemplateAsId; - makeSerializable( - CommonJsRequireDependency, - "webpack/lib/dependencies/CommonJsRequireDependency" + FallbackItemDependency, + "webpack/lib/container/FallbackItemDependency" ); -module.exports = CommonJsRequireDependency; +module.exports = FallbackItemDependency; /***/ }), -/***/ 69217: +/***/ 95193: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; /* MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra + Author Tobias Koppers @sokra and Zackary Jackson @ScriptedAlchemy */ +const { RawSource } = __webpack_require__(96192); +const Module = __webpack_require__(85887); const RuntimeGlobals = __webpack_require__(49404); -const { equals } = __webpack_require__(21537); +const Template = __webpack_require__(92066); const makeSerializable = __webpack_require__(26522); -const propertyAccess = __webpack_require__(86709); -const NullDependency = __webpack_require__(65845); +const FallbackItemDependency = __webpack_require__(33393); -/** @typedef {import("webpack-sources").ReplaceSource} ReplaceSource */ -/** @typedef {import("../Dependency")} Dependency */ -/** @typedef {import("../Dependency").ExportsSpec} ExportsSpec */ -/** @typedef {import("../Dependency").ReferencedExport} ReferencedExport */ -/** @typedef {import("../DependencyTemplate").DependencyTemplateContext} DependencyTemplateContext */ -/** @typedef {import("../ModuleGraph")} ModuleGraph */ -/** @typedef {import("../util/runtime").RuntimeSpec} RuntimeSpec */ +/** @typedef {import("../../declarations/WebpackOptions").WebpackOptionsNormalized} WebpackOptions */ +/** @typedef {import("../Chunk")} Chunk */ +/** @typedef {import("../ChunkGraph")} ChunkGraph */ +/** @typedef {import("../ChunkGroup")} ChunkGroup */ +/** @typedef {import("../Compilation")} Compilation */ +/** @typedef {import("../Module").CodeGenerationContext} CodeGenerationContext */ +/** @typedef {import("../Module").CodeGenerationResult} CodeGenerationResult */ +/** @typedef {import("../Module").LibIdentOptions} LibIdentOptions */ +/** @typedef {import("../Module").NeedBuildContext} NeedBuildContext */ +/** @typedef {import("../RequestShortener")} RequestShortener */ +/** @typedef {import("../ResolverFactory").ResolverWithOptions} ResolverWithOptions */ +/** @typedef {import("../WebpackError")} WebpackError */ +/** @typedef {import("../util/Hash")} Hash */ +/** @typedef {import("../util/fs").InputFileSystem} InputFileSystem */ -class CommonJsSelfReferenceDependency extends NullDependency { - constructor(range, base, names, call) { - super(); - this.range = range; - this.base = base; - this.names = names; - this.call = call; +const TYPES = new Set(["javascript"]); +const RUNTIME_REQUIREMENTS = new Set([RuntimeGlobals.module]); + +class FallbackModule extends Module { + /** + * @param {string[]} requests list of requests to choose one + */ + constructor(requests) { + super("fallback-module"); + this.requests = requests; + this._identifier = `fallback ${this.requests.join(" ")}`; } - get type() { - return "cjs self exports reference"; + /** + * @returns {string} a unique identifier of the module + */ + identifier() { + return this._identifier; } - get category() { - return "self"; + /** + * @param {RequestShortener} requestShortener the request shortener + * @returns {string} a user readable identifier of the module + */ + readableIdentifier(requestShortener) { + return this._identifier; } /** - * @returns {string | null} an identifier to merge equal requests + * @param {LibIdentOptions} options options + * @returns {string | null} an identifier for library inclusion */ - getResourceIdentifier() { - return `self`; + libIdent(options) { + return `webpack/container/fallback/${this.requests[0]}/and ${ + this.requests.length - 1 + } more`; } /** - * Returns list of exports referenced by this dependency - * @param {ModuleGraph} moduleGraph module graph - * @param {RuntimeSpec} runtime the runtime for which the module is analysed - * @returns {(string[] | ReferencedExport)[]} referenced exports + * @param {Chunk} chunk the chunk which condition should be checked + * @param {Compilation} compilation the compilation + * @returns {boolean} true, if the chunk is ok for the module */ - getReferencedExports(moduleGraph, runtime) { - return [this.call ? this.names.slice(0, -1) : this.names]; + chunkCondition(chunk, { chunkGraph }) { + return chunkGraph.getNumberOfEntryModules(chunk) > 0; + } + + /** + * @param {NeedBuildContext} context context info + * @param {function(WebpackError=, boolean=): void} callback callback function, returns true, if the module needs a rebuild + * @returns {void} + */ + needBuild(context, callback) { + callback(null, !this.buildInfo); + } + + /** + * @param {WebpackOptions} options webpack options + * @param {Compilation} compilation the compilation + * @param {ResolverWithOptions} resolver the resolver + * @param {InputFileSystem} fs the file system + * @param {function(WebpackError=): void} callback callback function + * @returns {void} + */ + build(options, compilation, resolver, fs, callback) { + this.buildMeta = {}; + this.buildInfo = { + strict: true + }; + + this.clearDependenciesAndBlocks(); + for (const request of this.requests) + this.addDependency(new FallbackItemDependency(request)); + + callback(); + } + + /** + * @param {string=} type the source type for which the size should be estimated + * @returns {number} the estimated size of the module (must be non-zero) + */ + size(type) { + return this.requests.length * 5 + 42; + } + + /** + * @returns {Set} types available (do not mutate) + */ + getSourceTypes() { + return TYPES; + } + + /** + * @param {CodeGenerationContext} context context for code generation + * @returns {CodeGenerationResult} result + */ + codeGeneration({ runtimeTemplate, moduleGraph, chunkGraph }) { + const ids = this.dependencies.map(dep => + chunkGraph.getModuleId(moduleGraph.getModule(dep)) + ); + const code = Template.asString([ + `var ids = ${JSON.stringify(ids)};`, + "var error, result, i = 0;", + `var loop = ${runtimeTemplate.basicFunction("next", [ + "while(i < ids.length) {", + Template.indent([ + "try { next = __webpack_require__(ids[i++]); } catch(e) { return handleError(e); }", + "if(next) return next.then ? next.then(handleResult, handleError) : handleResult(next);" + ]), + "}", + "if(error) throw error;" + ])}`, + `var handleResult = ${runtimeTemplate.basicFunction("result", [ + "if(result) return result;", + "return loop();" + ])};`, + `var handleError = ${runtimeTemplate.basicFunction("e", [ + "error = e;", + "return loop();" + ])};`, + "module.exports = loop();" + ]); + const sources = new Map(); + sources.set("javascript", new RawSource(code)); + return { sources, runtimeRequirements: RUNTIME_REQUIREMENTS }; } serialize(context) { const { write } = context; - write(this.range); - write(this.base); - write(this.names); - write(this.call); + write(this.requests); super.serialize(context); } - deserialize(context) { + static deserialize(context) { const { read } = context; - this.range = read(); - this.base = read(); - this.names = read(); - this.call = read(); - super.deserialize(context); + const obj = new FallbackModule(read()); + obj.deserialize(context); + return obj; } } -makeSerializable( - CommonJsSelfReferenceDependency, - "webpack/lib/dependencies/CommonJsSelfReferenceDependency" -); +makeSerializable(FallbackModule, "webpack/lib/container/FallbackModule"); -CommonJsSelfReferenceDependency.Template = class CommonJsSelfReferenceDependencyTemplate extends ( - NullDependency.Template -) { +module.exports = FallbackModule; + + +/***/ }), + +/***/ 88180: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra, Zackary Jackson @ScriptedAlchemy, Marais Rossouw @maraisr +*/ + + + +const ModuleFactory = __webpack_require__(61574); +const FallbackModule = __webpack_require__(95193); + +/** @typedef {import("../ModuleFactory").ModuleFactoryCreateData} ModuleFactoryCreateData */ +/** @typedef {import("../ModuleFactory").ModuleFactoryResult} ModuleFactoryResult */ +/** @typedef {import("./FallbackDependency")} FallbackDependency */ + +module.exports = class FallbackModuleFactory extends ModuleFactory { /** - * @param {Dependency} dependency the dependency for which the template should be applied - * @param {ReplaceSource} source the current replace source which can be modified - * @param {DependencyTemplateContext} templateContext the context object + * @param {ModuleFactoryCreateData} data data object + * @param {function(Error=, ModuleFactoryResult=): void} callback callback * @returns {void} */ - apply( - dependency, - source, - { module, moduleGraph, runtime, runtimeRequirements } - ) { - const dep = /** @type {CommonJsSelfReferenceDependency} */ (dependency); - let used; - if (dep.names.length === 0) { - used = dep.names; - } else { - used = moduleGraph.getExportsInfo(module).getUsedName(dep.names, runtime); - } - if (!used) { - throw new Error( - "Self-reference dependency has unused export name: This should not happen" - ); - } + create({ dependencies: [dependency] }, callback) { + const dep = /** @type {FallbackDependency} */ (dependency); + callback(null, { + module: new FallbackModule(dep.requests) + }); + } +}; - let base = undefined; - switch (dep.base) { - case "exports": - runtimeRequirements.add(RuntimeGlobals.exports); - base = module.exportsArgument; - break; - case "module.exports": - runtimeRequirements.add(RuntimeGlobals.module); - base = `${module.moduleArgument}.exports`; - break; - case "this": - runtimeRequirements.add(RuntimeGlobals.thisAsExports); - base = "this"; - break; - default: - throw new Error(`Unsupported base ${dep.base}`); - } - if (base === dep.base && equals(used, dep.names)) { - // Nothing has to be changed - // We don't use a replacement for compat reasons - // for plugins that update `module._source` which they - // shouldn't do! - return; +/***/ }), + +/***/ 22814: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra and Zackary Jackson @ScriptedAlchemy +*/ + + + +const isValidExternalsType = __webpack_require__(11482); +const SharePlugin = __webpack_require__(25790); +const createSchemaValidation = __webpack_require__(77695); +const ContainerPlugin = __webpack_require__(20962); +const ContainerReferencePlugin = __webpack_require__(17813); + +/** @typedef {import("../../declarations/plugins/container/ModuleFederationPlugin").ExternalsType} ExternalsType */ +/** @typedef {import("../../declarations/plugins/container/ModuleFederationPlugin").ModuleFederationPluginOptions} ModuleFederationPluginOptions */ +/** @typedef {import("../../declarations/plugins/container/ModuleFederationPlugin").Shared} Shared */ +/** @typedef {import("../Compiler")} Compiler */ + +const validate = createSchemaValidation( + __webpack_require__(83622), + () => __webpack_require__(2320), + { + name: "Module Federation Plugin", + baseDataPath: "options" + } +); +class ModuleFederationPlugin { + /** + * @param {ModuleFederationPluginOptions} options options + */ + constructor(options) { + validate(options); + + this._options = options; + } + + /** + * Apply the plugin + * @param {Compiler} compiler the compiler instance + * @returns {void} + */ + apply(compiler) { + const { _options: options } = this; + const library = options.library || { type: "var", name: options.name }; + const remoteType = + options.remoteType || + (options.library && isValidExternalsType(options.library.type) + ? /** @type {ExternalsType} */ (options.library.type) + : "script"); + if ( + library && + !compiler.options.output.enabledLibraryTypes.includes(library.type) + ) { + compiler.options.output.enabledLibraryTypes.push(library.type); } - - source.replace( - dep.range[0], - dep.range[1] - 1, - `${base}${propertyAccess(used)}` - ); + compiler.hooks.afterPlugins.tap("ModuleFederationPlugin", () => { + if ( + options.exposes && + (Array.isArray(options.exposes) + ? options.exposes.length > 0 + : Object.keys(options.exposes).length > 0) + ) { + new ContainerPlugin({ + name: options.name, + library, + filename: options.filename, + runtime: options.runtime, + exposes: options.exposes + }).apply(compiler); + } + if ( + options.remotes && + (Array.isArray(options.remotes) + ? options.remotes.length > 0 + : Object.keys(options.remotes).length > 0) + ) { + new ContainerReferencePlugin({ + remoteType, + remotes: options.remotes + }).apply(compiler); + } + if (options.shared) { + new SharePlugin({ + shared: options.shared, + shareScope: options.shareScope + }).apply(compiler); + } + }); } -}; +} -module.exports = CommonJsSelfReferenceDependency; +module.exports = ModuleFederationPlugin; /***/ }), -/***/ 60864: +/***/ 581: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; /* MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra + Author Tobias Koppers @sokra and Zackary Jackson @ScriptedAlchemy */ +const { RawSource } = __webpack_require__(96192); +const Module = __webpack_require__(85887); +const RuntimeGlobals = __webpack_require__(49404); const makeSerializable = __webpack_require__(26522); -const NullDependency = __webpack_require__(65845); +const FallbackDependency = __webpack_require__(41061); +const RemoteToExternalDependency = __webpack_require__(44637); -/** @typedef {import("webpack-sources").ReplaceSource} ReplaceSource */ +/** @typedef {import("../../declarations/WebpackOptions").WebpackOptionsNormalized} WebpackOptions */ /** @typedef {import("../ChunkGraph")} ChunkGraph */ -/** @typedef {import("../Dependency")} Dependency */ -/** @typedef {import("../Dependency").UpdateHashContext} UpdateHashContext */ -/** @typedef {import("../DependencyTemplate").DependencyTemplateContext} DependencyTemplateContext */ -/** @typedef {import("../ModuleGraph")} ModuleGraph */ -/** @typedef {import("../ModuleGraphConnection").ConnectionState} ConnectionState */ +/** @typedef {import("../ChunkGroup")} ChunkGroup */ +/** @typedef {import("../Compilation")} Compilation */ +/** @typedef {import("../Module").CodeGenerationContext} CodeGenerationContext */ +/** @typedef {import("../Module").CodeGenerationResult} CodeGenerationResult */ +/** @typedef {import("../Module").LibIdentOptions} LibIdentOptions */ +/** @typedef {import("../Module").NeedBuildContext} NeedBuildContext */ +/** @typedef {import("../RequestShortener")} RequestShortener */ +/** @typedef {import("../ResolverFactory").ResolverWithOptions} ResolverWithOptions */ +/** @typedef {import("../WebpackError")} WebpackError */ /** @typedef {import("../util/Hash")} Hash */ +/** @typedef {import("../util/fs").InputFileSystem} InputFileSystem */ -class ConstDependency extends NullDependency { +const TYPES = new Set(["remote", "share-init"]); +const RUNTIME_REQUIREMENTS = new Set([RuntimeGlobals.module]); + +class RemoteModule extends Module { /** - * @param {string} expression the expression - * @param {number|[number, number]} range the source range - * @param {string[]=} runtimeRequirements runtime requirements + * @param {string} request request string + * @param {string[]} externalRequests list of external requests to containers + * @param {string} internalRequest name of exposed module in container + * @param {string} shareScope the used share scope name */ - constructor(expression, range, runtimeRequirements) { - super(); - this.expression = expression; - this.range = range; - this.runtimeRequirements = runtimeRequirements - ? new Set(runtimeRequirements) - : null; - this._hashUpdate = undefined; + constructor(request, externalRequests, internalRequest, shareScope) { + super("remote-module"); + this.request = request; + this.externalRequests = externalRequests; + this.internalRequest = internalRequest; + this.shareScope = shareScope; + this._identifier = `remote (${shareScope}) ${this.externalRequests.join( + " " + )} ${this.internalRequest}`; } /** - * Update the hash - * @param {Hash} hash hash to be updated - * @param {UpdateHashContext} context context - * @returns {void} + * @returns {string} a unique identifier of the module */ - updateHash(hash, context) { - if (this._hashUpdate === undefined) { - let hashUpdate = "" + this.range + "|" + this.expression; - if (this.runtimeRequirements) { - for (const item of this.runtimeRequirements) { - hashUpdate += "|"; - hashUpdate += item; - } - } - this._hashUpdate = hashUpdate; - } - hash.update(this._hashUpdate); + identifier() { + return this._identifier; } /** - * @param {ModuleGraph} moduleGraph the module graph - * @returns {ConnectionState} how this dependency connects the module to referencing modules + * @param {RequestShortener} requestShortener the request shortener + * @returns {string} a user readable identifier of the module */ - getModuleEvaluationSideEffectsState(moduleGraph) { - return false; - } - - serialize(context) { - const { write } = context; - write(this.expression); - write(this.range); - write(this.runtimeRequirements); - super.serialize(context); + readableIdentifier(requestShortener) { + return `remote ${this.request}`; } - deserialize(context) { - const { read } = context; - this.expression = read(); - this.range = read(); - this.runtimeRequirements = read(); - super.deserialize(context); + /** + * @param {LibIdentOptions} options options + * @returns {string | null} an identifier for library inclusion + */ + libIdent(options) { + return `webpack/container/remote/${this.request}`; } -} - -makeSerializable(ConstDependency, "webpack/lib/dependencies/ConstDependency"); -ConstDependency.Template = class ConstDependencyTemplate extends ( - NullDependency.Template -) { /** - * @param {Dependency} dependency the dependency for which the template should be applied - * @param {ReplaceSource} source the current replace source which can be modified - * @param {DependencyTemplateContext} templateContext the context object + * @param {NeedBuildContext} context context info + * @param {function(WebpackError=, boolean=): void} callback callback function, returns true, if the module needs a rebuild * @returns {void} */ - apply(dependency, source, templateContext) { - const dep = /** @type {ConstDependency} */ (dependency); - if (dep.runtimeRequirements) { - for (const req of dep.runtimeRequirements) { - templateContext.runtimeRequirements.add(req); - } - } - if (typeof dep.range === "number") { - source.insert(dep.range, dep.expression); - return; - } - - source.replace(dep.range[0], dep.range[1] - 1, dep.expression); + needBuild(context, callback) { + callback(null, !this.buildInfo); } -}; - -module.exports = ConstDependency; - - -/***/ }), - -/***/ 67840: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ - - - -const Dependency = __webpack_require__(50384); -const DependencyTemplate = __webpack_require__(17600); -const makeSerializable = __webpack_require__(26522); -const memoize = __webpack_require__(84297); - -/** @typedef {import("../ContextModule").ContextOptions} ContextOptions */ -/** @typedef {import("../Dependency").TRANSITIVE} TRANSITIVE */ -/** @typedef {import("../ModuleGraph")} ModuleGraph */ -/** @typedef {import("../WebpackError")} WebpackError */ - -const getCriticalDependencyWarning = memoize(() => - __webpack_require__(14190) -); - -/** @typedef {ContextOptions & { request: string }} ContextDependencyOptions */ - -const regExpToString = r => (r ? r + "" : ""); -class ContextDependency extends Dependency { /** - * @param {ContextDependencyOptions} options options for the context module + * @param {WebpackOptions} options webpack options + * @param {Compilation} compilation the compilation + * @param {ResolverWithOptions} resolver the resolver + * @param {InputFileSystem} fs the file system + * @param {function(WebpackError=): void} callback callback function + * @returns {void} */ - constructor(options) { - super(); - - this.options = options; - this.userRequest = this.options && this.options.request; - /** @type {false | string} */ - this.critical = false; - this.hadGlobalOrStickyRegExp = false; + build(options, compilation, resolver, fs, callback) { + this.buildMeta = {}; + this.buildInfo = { + strict: true + }; - if ( - this.options && - (this.options.regExp.global || this.options.regExp.sticky) - ) { - this.options = { ...this.options, regExp: null }; - this.hadGlobalOrStickyRegExp = true; + this.clearDependenciesAndBlocks(); + if (this.externalRequests.length === 1) { + this.addDependency( + new RemoteToExternalDependency(this.externalRequests[0]) + ); + } else { + this.addDependency(new FallbackDependency(this.externalRequests)); } - this.request = undefined; - this.range = undefined; - this.valueRange = undefined; - this.inShorthand = undefined; - // TODO refactor this - this.replaces = undefined; + callback(); } - get category() { - return "commonjs"; + /** + * @param {string=} type the source type for which the size should be estimated + * @returns {number} the estimated size of the module (must be non-zero) + */ + size(type) { + return 6; } /** - * @returns {boolean | TRANSITIVE} true, when changes to the referenced module could affect the referencing module; TRANSITIVE, when changes to the referenced module could affect referencing modules of the referencing module + * @returns {Set} types available (do not mutate) */ - couldAffectReferencingModule() { - return true; + getSourceTypes() { + return TYPES; } /** - * @returns {string | null} an identifier to merge equal requests + * @returns {string | null} absolute path which should be used for condition matching (usually the resource path) */ - getResourceIdentifier() { - return ( - `context${this.options.request} ${this.options.recursive} ` + - `${regExpToString(this.options.regExp)} ${regExpToString( - this.options.include - )} ${regExpToString(this.options.exclude)} ` + - `${this.options.mode} ${this.options.chunkName} ` + - `${JSON.stringify(this.options.groupOptions)}` - ); + nameForCondition() { + return this.request; } /** - * Returns warnings - * @param {ModuleGraph} moduleGraph module graph - * @returns {WebpackError[]} warnings + * @param {CodeGenerationContext} context context for code generation + * @returns {CodeGenerationResult} result */ - getWarnings(moduleGraph) { - let warnings = super.getWarnings(moduleGraph); - - if (this.critical) { - if (!warnings) warnings = []; - const CriticalDependencyWarning = getCriticalDependencyWarning(); - warnings.push(new CriticalDependencyWarning(this.critical)); - } - - if (this.hadGlobalOrStickyRegExp) { - if (!warnings) warnings = []; - const CriticalDependencyWarning = getCriticalDependencyWarning(); - warnings.push( - new CriticalDependencyWarning( - "Contexts can't use RegExps with the 'g' or 'y' flags." - ) - ); - } - - return warnings; + codeGeneration({ runtimeTemplate, moduleGraph, chunkGraph }) { + const module = moduleGraph.getModule(this.dependencies[0]); + const id = module && chunkGraph.getModuleId(module); + const sources = new Map(); + sources.set("remote", new RawSource("")); + const data = new Map(); + data.set("share-init", [ + { + shareScope: this.shareScope, + initStage: 20, + init: id === undefined ? "" : `initExternal(${JSON.stringify(id)});` + } + ]); + return { sources, data, runtimeRequirements: RUNTIME_REQUIREMENTS }; } serialize(context) { const { write } = context; - - write(this.options); - write(this.userRequest); - write(this.critical); - write(this.hadGlobalOrStickyRegExp); write(this.request); - write(this.range); - write(this.valueRange); - write(this.prepend); - write(this.replaces); - + write(this.externalRequests); + write(this.internalRequest); + write(this.shareScope); super.serialize(context); } - deserialize(context) { + static deserialize(context) { const { read } = context; - - this.options = read(); - this.userRequest = read(); - this.critical = read(); - this.hadGlobalOrStickyRegExp = read(); - this.request = read(); - this.range = read(); - this.valueRange = read(); - this.prepend = read(); - this.replaces = read(); - - super.deserialize(context); + const obj = new RemoteModule(read(), read(), read(), read()); + obj.deserialize(context); + return obj; } } -makeSerializable( - ContextDependency, - "webpack/lib/dependencies/ContextDependency" -); +makeSerializable(RemoteModule, "webpack/lib/container/RemoteModule"); -ContextDependency.Template = DependencyTemplate; +module.exports = RemoteModule; -module.exports = ContextDependency; + +/***/ }), + +/***/ 4603: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ + + + +const RuntimeGlobals = __webpack_require__(49404); +const RuntimeModule = __webpack_require__(61439); +const Template = __webpack_require__(92066); + +/** @typedef {import("./RemoteModule")} RemoteModule */ + +class RemoteRuntimeModule extends RuntimeModule { + constructor() { + super("remotes loading"); + } + + /** + * @returns {string} runtime code + */ + generate() { + const { compilation, chunkGraph } = this; + const { runtimeTemplate, moduleGraph } = compilation; + const chunkToRemotesMapping = {}; + const idToExternalAndNameMapping = {}; + for (const chunk of this.chunk.getAllAsyncChunks()) { + const modules = chunkGraph.getChunkModulesIterableBySourceType( + chunk, + "remote" + ); + if (!modules) continue; + const remotes = (chunkToRemotesMapping[chunk.id] = []); + for (const m of modules) { + const module = /** @type {RemoteModule} */ (m); + const name = module.internalRequest; + const id = chunkGraph.getModuleId(module); + const shareScope = module.shareScope; + const dep = module.dependencies[0]; + const externalModule = moduleGraph.getModule(dep); + const externalModuleId = + externalModule && chunkGraph.getModuleId(externalModule); + remotes.push(id); + idToExternalAndNameMapping[id] = [shareScope, name, externalModuleId]; + } + } + return Template.asString([ + `var chunkMapping = ${JSON.stringify( + chunkToRemotesMapping, + null, + "\t" + )};`, + `var idToExternalAndNameMapping = ${JSON.stringify( + idToExternalAndNameMapping, + null, + "\t" + )};`, + `${ + RuntimeGlobals.ensureChunkHandlers + }.remotes = ${runtimeTemplate.basicFunction("chunkId, promises", [ + `if(${RuntimeGlobals.hasOwnProperty}(chunkMapping, chunkId)) {`, + Template.indent([ + `chunkMapping[chunkId].forEach(${runtimeTemplate.basicFunction("id", [ + `var getScope = ${RuntimeGlobals.currentRemoteGetScope};`, + "if(!getScope) getScope = [];", + "var data = idToExternalAndNameMapping[id];", + "if(getScope.indexOf(data) >= 0) return;", + "getScope.push(data);", + `if(data.p) return promises.push(data.p);`, + `var onError = ${runtimeTemplate.basicFunction("error", [ + 'if(!error) error = new Error("Container missing");', + 'if(typeof error.message === "string")', + Template.indent( + `error.message += '\\nwhile loading "' + data[1] + '" from ' + data[2];` + ), + `__webpack_modules__[id] = ${runtimeTemplate.basicFunction("", [ + "throw error;" + ])}`, + "data.p = 0;" + ])};`, + `var handleFunction = ${runtimeTemplate.basicFunction( + "fn, arg1, arg2, d, next, first", + [ + "try {", + Template.indent([ + "var promise = fn(arg1, arg2);", + "if(promise && promise.then) {", + Template.indent([ + `var p = promise.then(${runtimeTemplate.returningFunction( + "next(result, d)", + "result" + )}, onError);`, + `if(first) promises.push(data.p = p); else return p;` + ]), + "} else {", + Template.indent(["return next(promise, d, first);"]), + "}" + ]), + "} catch(error) {", + Template.indent(["onError(error);"]), + "}" + ] + )}`, + `var onExternal = ${runtimeTemplate.returningFunction( + `external ? handleFunction(${RuntimeGlobals.initializeSharing}, data[0], 0, external, onInitialized, first) : onError()`, + "external, _, first" + )};`, + `var onInitialized = ${runtimeTemplate.returningFunction( + `handleFunction(external.get, data[1], getScope, 0, onFactory, first)`, + "_, external, first" + )};`, + `var onFactory = ${runtimeTemplate.basicFunction("factory", [ + "data.p = 1;", + `__webpack_modules__[id] = ${runtimeTemplate.basicFunction( + "module", + ["module.exports = factory();"] + )}` + ])};`, + "handleFunction(__webpack_require__, data[2], 0, 0, onExternal, 1);" + ])});` + ]), + "}" + ])}` + ]); + } +} + +module.exports = RemoteRuntimeModule; /***/ }), -/***/ 7114: -/***/ (function(__unused_webpack_module, exports, __webpack_require__) { +/***/ 44637: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; /* @@ -77123,546 +74374,594 @@ module.exports = ContextDependency; -const { parseResource } = __webpack_require__(96236); +const ModuleDependency = __webpack_require__(80944); +const makeSerializable = __webpack_require__(26522); -/** @typedef {import("estree").Node} EsTreeNode */ -/** @typedef {import("../../declarations/WebpackOptions").JavascriptParserOptions} JavascriptParserOptions */ -/** @typedef {import("../../declarations/WebpackOptions").ModuleOptionsNormalized} ModuleOptions */ -/** @typedef {import("../javascript/BasicEvaluatedExpression")} BasicEvaluatedExpression */ -/** @typedef {import("../javascript/JavascriptParser")} JavascriptParser */ -/** @typedef {import("./ContextDependency")} ContextDependency */ -/** @typedef {import("./ContextDependency").ContextDependencyOptions} ContextDependencyOptions */ +class RemoteToExternalDependency extends ModuleDependency { + constructor(request) { + super(request); + } -/** - * Escapes regular expression metacharacters - * @param {string} str String to quote - * @returns {string} Escaped string - */ -const quoteMeta = str => { - return str.replace(/[-[\]\\/{}()*+?.^$|]/g, "\\$&"); -}; + get type() { + return "remote to external"; + } -const splitContextFromPrefix = prefix => { - const idx = prefix.lastIndexOf("/"); - let context = "."; - if (idx >= 0) { - context = prefix.substr(0, idx); - prefix = `.${prefix.substr(idx)}`; + get category() { + return "esm"; } - return { - context, - prefix - }; -}; +} -/** @typedef {Partial>} PartialContextDependencyOptions */ +makeSerializable( + RemoteToExternalDependency, + "webpack/lib/container/RemoteToExternalDependency" +); -/** @typedef {{ new(options: ContextDependencyOptions, range: [number, number], valueRange: [number, number]): ContextDependency }} ContextDependencyConstructor */ +module.exports = RemoteToExternalDependency; -/** - * @param {ContextDependencyConstructor} Dep the Dependency class - * @param {[number, number]} range source range - * @param {BasicEvaluatedExpression} param context param - * @param {EsTreeNode} expr expr - * @param {Pick} options options for context creation - * @param {PartialContextDependencyOptions} contextOptions options for the ContextModule - * @param {JavascriptParser} parser the parser - * @returns {ContextDependency} the created Dependency - */ -exports.create = (Dep, range, param, expr, options, contextOptions, parser) => { - if (param.isTemplateString()) { - let prefixRaw = param.quasis[0].string; - let postfixRaw = - param.quasis.length > 1 - ? param.quasis[param.quasis.length - 1].string - : ""; - const valueRange = param.range; - const { context, prefix } = splitContextFromPrefix(prefixRaw); - const { - path: postfix, - query, - fragment - } = parseResource(postfixRaw, parser); +/***/ }), - // When there are more than two quasis, the generated RegExp can be more precise - // We join the quasis with the expression regexp - const innerQuasis = param.quasis.slice(1, param.quasis.length - 1); - const innerRegExp = - options.wrappedContextRegExp.source + - innerQuasis - .map(q => quoteMeta(q.string) + options.wrappedContextRegExp.source) - .join(""); +/***/ 56084: +/***/ (function(__unused_webpack_module, exports) { - // Example: `./context/pre${e}inner${e}inner2${e}post?query#frag` - // context: "./context" - // prefix: "./pre" - // innerQuasis: [BEE("inner"), BEE("inner2")] - // (BEE = BasicEvaluatedExpression) - // postfix: "post" - // query: "?query" - // fragment: "#frag" - // regExp: /^\.\/pre.*inner.*inner2.*post$/ - const regExp = new RegExp( - `^${quoteMeta(prefix)}${innerRegExp}${quoteMeta(postfix)}$` - ); - const dep = new Dep( - { - request: context + query + fragment, - recursive: options.wrappedContextRecursive, - regExp, - mode: "sync", - ...contextOptions - }, - range, - valueRange - ); - dep.loc = expr.loc; - const replaces = []; +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ - param.parts.forEach((part, i) => { - if (i % 2 === 0) { - // Quasis or merged quasi - let range = part.range; - let value = part.string; - if (param.templateStringKind === "cooked") { - value = JSON.stringify(value); - value = value.slice(1, value.length - 1); - } - if (i === 0) { - // prefix - value = prefix; - range = [param.range[0], part.range[1]]; - value = - (param.templateStringKind === "cooked" ? "`" : "String.raw`") + - value; - } else if (i === param.parts.length - 1) { - // postfix - value = postfix; - range = [part.range[0], param.range[1]]; - value = value + "`"; - } else if ( - part.expression && - part.expression.type === "TemplateElement" && - part.expression.value.raw === value - ) { - // Shortcut when it's a single quasi and doesn't need to be replaced - return; - } - replaces.push({ - range, - value - }); + + +/** @template T @typedef {(string | Record)[] | Record} ContainerOptionsFormat */ + +/** + * @template T + * @template N + * @param {ContainerOptionsFormat} options options passed by the user + * @param {function(string | string[], string) : N} normalizeSimple normalize a simple item + * @param {function(T, string) : N} normalizeOptions normalize a complex item + * @param {function(string, N): void} fn processing function + * @returns {void} + */ +const process = (options, normalizeSimple, normalizeOptions, fn) => { + const array = items => { + for (const item of items) { + if (typeof item === "string") { + fn(item, normalizeSimple(item, item)); + } else if (item && typeof item === "object") { + object(item); } else { - // Expression - parser.walkExpression(part.expression); + throw new Error("Unexpected options format"); } - }); - - dep.replaces = replaces; - dep.critical = - options.wrappedContextCritical && - "a part of the request of a dependency is an expression"; - return dep; - } else if ( - param.isWrapped() && - ((param.prefix && param.prefix.isString()) || - (param.postfix && param.postfix.isString())) - ) { - let prefixRaw = - param.prefix && param.prefix.isString() ? param.prefix.string : ""; - let postfixRaw = - param.postfix && param.postfix.isString() ? param.postfix.string : ""; - const prefixRange = - param.prefix && param.prefix.isString() ? param.prefix.range : null; - const postfixRange = - param.postfix && param.postfix.isString() ? param.postfix.range : null; - const valueRange = param.range; - const { context, prefix } = splitContextFromPrefix(prefixRaw); - const { - path: postfix, - query, - fragment - } = parseResource(postfixRaw, parser); - const regExp = new RegExp( - `^${quoteMeta(prefix)}${options.wrappedContextRegExp.source}${quoteMeta( - postfix - )}$` - ); - const dep = new Dep( - { - request: context + query + fragment, - recursive: options.wrappedContextRecursive, - regExp, - mode: "sync", - ...contextOptions - }, - range, - valueRange - ); - dep.loc = expr.loc; - const replaces = []; - if (prefixRange) { - replaces.push({ - range: prefixRange, - value: JSON.stringify(prefix) - }); - } - if (postfixRange) { - replaces.push({ - range: postfixRange, - value: JSON.stringify(postfix) - }); } - dep.replaces = replaces; - dep.critical = - options.wrappedContextCritical && - "a part of the request of a dependency is an expression"; - - if (parser && param.wrappedInnerExpressions) { - for (const part of param.wrappedInnerExpressions) { - if (part.expression) parser.walkExpression(part.expression); + }; + const object = obj => { + for (const [key, value] of Object.entries(obj)) { + if (typeof value === "string" || Array.isArray(value)) { + fn(key, normalizeSimple(value, key)); + } else { + fn(key, normalizeOptions(value, key)); } } - - return dep; + }; + if (!options) { + return; + } else if (Array.isArray(options)) { + array(options); + } else if (typeof options === "object") { + object(options); } else { - const dep = new Dep( - { - request: options.exprContextRequest, - recursive: options.exprContextRecursive, - regExp: /** @type {RegExp} */ (options.exprContextRegExp), - mode: "sync", - ...contextOptions - }, - range, - param.range - ); - dep.loc = expr.loc; - dep.critical = - options.exprContextCritical && - "the request of a dependency is an expression"; + throw new Error("Unexpected options format"); + } +}; - parser.walkExpression(param.expression); +/** + * @template T + * @template R + * @param {ContainerOptionsFormat} options options passed by the user + * @param {function(string | string[], string) : R} normalizeSimple normalize a simple item + * @param {function(T, string) : R} normalizeOptions normalize a complex item + * @returns {[string, R][]} parsed options + */ +const parseOptions = (options, normalizeSimple, normalizeOptions) => { + /** @type {[string, R][]} */ + const items = []; + process(options, normalizeSimple, normalizeOptions, (key, value) => { + items.push([key, value]); + }); + return items; +}; - return dep; - } +/** + * @template T + * @param {string} scope scope name + * @param {ContainerOptionsFormat} options options passed by the user + * @returns {Record} options to spread or pass + */ +const scope = (scope, options) => { + /** @type {Record} */ + const obj = {}; + process( + options, + item => /** @type {string | string[] | T} */ (item), + item => /** @type {string | string[] | T} */ (item), + (key, value) => { + obj[ + key.startsWith("./") ? `${scope}${key.slice(1)}` : `${scope}/${key}` + ] = value; + } + ); + return obj; }; +exports.parseOptions = parseOptions; +exports.scope = scope; + /***/ }), -/***/ 95080: +/***/ 52034: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; /* MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra */ -const ContextDependency = __webpack_require__(67840); - -/** @typedef {import("webpack-sources").ReplaceSource} ReplaceSource */ -/** @typedef {import("../Dependency")} Dependency */ -/** @typedef {import("../DependencyTemplate").DependencyTemplateContext} DependencyTemplateContext */ +const { Tracer } = __webpack_require__(92430); +const createSchemaValidation = __webpack_require__(77695); +const { dirname, mkdirpSync } = __webpack_require__(93204); -class ContextDependencyTemplateAsId extends ContextDependency.Template { - /** - * @param {Dependency} dependency the dependency for which the template should be applied - * @param {ReplaceSource} source the current replace source which can be modified - * @param {DependencyTemplateContext} templateContext the context object - * @returns {void} - */ - apply( - dependency, - source, - { runtimeTemplate, moduleGraph, chunkGraph, runtimeRequirements } - ) { - const dep = /** @type {ContextDependency} */ (dependency); - const moduleExports = runtimeTemplate.moduleExports({ - module: moduleGraph.getModule(dep), - chunkGraph, - request: dep.request, - weak: dep.weak, - runtimeRequirements - }); +/** @typedef {import("../../declarations/plugins/debug/ProfilingPlugin").ProfilingPluginOptions} ProfilingPluginOptions */ +/** @typedef {import("../util/fs").IntermediateFileSystem} IntermediateFileSystem */ - if (moduleGraph.getModule(dep)) { - if (dep.valueRange) { - if (Array.isArray(dep.replaces)) { - for (let i = 0; i < dep.replaces.length; i++) { - const rep = dep.replaces[i]; - source.replace(rep.range[0], rep.range[1] - 1, rep.value); - } - } - source.replace(dep.valueRange[1], dep.range[1] - 1, ")"); - source.replace( - dep.range[0], - dep.valueRange[0] - 1, - `${moduleExports}.resolve(` - ); - } else { - source.replace( - dep.range[0], - dep.range[1] - 1, - `${moduleExports}.resolve` - ); - } - } else { - source.replace(dep.range[0], dep.range[1] - 1, moduleExports); - } +const validate = createSchemaValidation( + __webpack_require__(93129), + () => __webpack_require__(26281), + { + name: "Profiling Plugin", + baseDataPath: "options" } -} -module.exports = ContextDependencyTemplateAsId; - - -/***/ }), +); +let inspector = undefined; -/***/ 18259: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { +try { + // eslint-disable-next-line node/no-unsupported-features/node-builtins + inspector = __webpack_require__(57012); +} catch (e) { + console.log("Unable to CPU profile in < node 8.0"); +} -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ +class Profiler { + constructor(inspector) { + this.session = undefined; + this.inspector = inspector; + this._startTime = 0; + } + hasSession() { + return this.session !== undefined; + } + startProfiling() { + if (this.inspector === undefined) { + return Promise.resolve(); + } -const ContextDependency = __webpack_require__(67840); + try { + this.session = new inspector.Session(); + this.session.connect(); + } catch (_) { + this.session = undefined; + return Promise.resolve(); + } -/** @typedef {import("webpack-sources").ReplaceSource} ReplaceSource */ -/** @typedef {import("../Dependency")} Dependency */ -/** @typedef {import("../DependencyTemplate").DependencyTemplateContext} DependencyTemplateContext */ + const hrtime = process.hrtime(); + this._startTime = hrtime[0] * 1000000 + Math.round(hrtime[1] / 1000); -class ContextDependencyTemplateAsRequireCall extends ContextDependency.Template { - /** - * @param {Dependency} dependency the dependency for which the template should be applied - * @param {ReplaceSource} source the current replace source which can be modified - * @param {DependencyTemplateContext} templateContext the context object - * @returns {void} - */ - apply( - dependency, - source, - { runtimeTemplate, moduleGraph, chunkGraph, runtimeRequirements } - ) { - const dep = /** @type {ContextDependency} */ (dependency); - let moduleExports = runtimeTemplate.moduleExports({ - module: moduleGraph.getModule(dep), - chunkGraph, - request: dep.request, - runtimeRequirements - }); + return Promise.all([ + this.sendCommand("Profiler.setSamplingInterval", { + interval: 100 + }), + this.sendCommand("Profiler.enable"), + this.sendCommand("Profiler.start") + ]); + } - if (dep.inShorthand) { - moduleExports = `${dep.inShorthand}: ${moduleExports}`; - } - if (moduleGraph.getModule(dep)) { - if (dep.valueRange) { - if (Array.isArray(dep.replaces)) { - for (let i = 0; i < dep.replaces.length; i++) { - const rep = dep.replaces[i]; - source.replace(rep.range[0], rep.range[1] - 1, rep.value); + sendCommand(method, params) { + if (this.hasSession()) { + return new Promise((res, rej) => { + return this.session.post(method, params, (err, params) => { + if (err !== null) { + rej(err); + } else { + res(params); } - } - source.replace(dep.valueRange[1], dep.range[1] - 1, ")"); - source.replace( - dep.range[0], - dep.valueRange[0] - 1, - `${moduleExports}(` - ); - } else { - source.replace(dep.range[0], dep.range[1] - 1, moduleExports); - } + }); + }); } else { - source.replace(dep.range[0], dep.range[1] - 1, moduleExports); + return Promise.resolve(); } } -} -module.exports = ContextDependencyTemplateAsRequireCall; - - -/***/ }), -/***/ 83853: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ + destroy() { + if (this.hasSession()) { + this.session.disconnect(); + } + return Promise.resolve(); + } + stopProfiling() { + return this.sendCommand("Profiler.stop").then(({ profile }) => { + const hrtime = process.hrtime(); + const endTime = hrtime[0] * 1000000 + Math.round(hrtime[1] / 1000); + if (profile.startTime < this._startTime || profile.endTime > endTime) { + // In some cases timestamps mismatch and we need to adjust them + // Both process.hrtime and the inspector timestamps claim to be relative + // to a unknown point in time. But they do not guarantee that this is the + // same point in time. + const duration = profile.endTime - profile.startTime; + const ownDuration = endTime - this._startTime; + const untracked = Math.max(0, ownDuration - duration); + profile.startTime = this._startTime + untracked / 2; + profile.endTime = endTime - untracked / 2; + } + return { profile }; + }); + } +} -const Dependency = __webpack_require__(50384); -const makeSerializable = __webpack_require__(26522); -const ModuleDependency = __webpack_require__(80944); +/** + * an object that wraps Tracer and Profiler with a counter + * @typedef {Object} Trace + * @property {Tracer} trace instance of Tracer + * @property {number} counter Counter + * @property {Profiler} profiler instance of Profiler + * @property {Function} end the end function + */ -/** @typedef {import("../Dependency").ReferencedExport} ReferencedExport */ -/** @typedef {import("../ModuleGraph")} ModuleGraph */ -/** @typedef {import("../util/runtime").RuntimeSpec} RuntimeSpec */ +/** + * @param {IntermediateFileSystem} fs filesystem used for output + * @param {string} outputPath The location where to write the log. + * @returns {Trace} The trace object + */ +const createTrace = (fs, outputPath) => { + const trace = new Tracer({ + noStream: true + }); + const profiler = new Profiler(inspector); + if (/\/|\\/.test(outputPath)) { + const dirPath = dirname(fs, outputPath); + mkdirpSync(fs, dirPath); + } + const fsStream = fs.createWriteStream(outputPath); -class ContextElementDependency extends ModuleDependency { - constructor(request, userRequest, typePrefix, category, referencedExports) { - super(request); - this.referencedExports = referencedExports; - this._typePrefix = typePrefix; - this._category = category; + let counter = 0; - if (userRequest) { - this.userRequest = userRequest; + trace.pipe(fsStream); + // These are critical events that need to be inserted so that tools like + // chrome dev tools can load the profile. + trace.instantEvent({ + name: "TracingStartedInPage", + id: ++counter, + cat: ["disabled-by-default-devtools.timeline"], + args: { + data: { + sessionId: "-1", + page: "0xfff", + frames: [ + { + frame: "0xfff", + url: "webpack", + name: "" + } + ] + } } - } + }); - get type() { - if (this._typePrefix) { - return `${this._typePrefix} context element`; + trace.instantEvent({ + name: "TracingStartedInBrowser", + id: ++counter, + cat: ["disabled-by-default-devtools.timeline"], + args: { + data: { + sessionId: "-1" + } } + }); - return "context element"; - } + return { + trace, + counter, + profiler, + end: callback => { + // Wait until the write stream finishes. + fsStream.on("close", () => { + callback(); + }); + // Tear down the readable trace stream. + trace.push(null); + } + }; +}; - get category() { - return this._category; - } +const pluginName = "ProfilingPlugin"; +class ProfilingPlugin { /** - * Returns list of exports referenced by this dependency - * @param {ModuleGraph} moduleGraph module graph - * @param {RuntimeSpec} runtime the runtime for which the module is analysed - * @returns {(string[] | ReferencedExport)[]} referenced exports + * @param {ProfilingPluginOptions=} options options object */ - getReferencedExports(moduleGraph, runtime) { - return this.referencedExports - ? this.referencedExports.map(e => ({ - name: e, - canMangle: false - })) - : Dependency.EXPORTS_OBJECT_REFERENCED; - } - - serialize(context) { - context.write(this.referencedExports); - super.serialize(context); - } - - deserialize(context) { - this.referencedExports = context.read(); - super.deserialize(context); + constructor(options = {}) { + validate(options); + this.outputPath = options.outputPath || "events.json"; } -} - -makeSerializable( - ContextElementDependency, - "webpack/lib/dependencies/ContextElementDependency" -); - -module.exports = ContextElementDependency; + apply(compiler) { + const tracer = createTrace( + compiler.intermediateFileSystem, + this.outputPath + ); + tracer.profiler.startProfiling(); -/***/ }), + // Compiler Hooks + Object.keys(compiler.hooks).forEach(hookName => { + const hook = compiler.hooks[hookName]; + if (hook) { + hook.intercept(makeInterceptorFor("Compiler", tracer)(hookName)); + } + }); -/***/ 29829: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + Object.keys(compiler.resolverFactory.hooks).forEach(hookName => { + const hook = compiler.resolverFactory.hooks[hookName]; + if (hook) { + hook.intercept(makeInterceptorFor("Resolver", tracer)(hookName)); + } + }); -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ + compiler.hooks.compilation.tap( + pluginName, + (compilation, { normalModuleFactory, contextModuleFactory }) => { + interceptAllHooksFor(compilation, tracer, "Compilation"); + interceptAllHooksFor( + normalModuleFactory, + tracer, + "Normal Module Factory" + ); + interceptAllHooksFor( + contextModuleFactory, + tracer, + "Context Module Factory" + ); + interceptAllParserHooks(normalModuleFactory, tracer); + interceptAllJavascriptModulesPluginHooks(compilation, tracer); + } + ); + // We need to write out the CPU profile when we are all done. + compiler.hooks.done.tapAsync( + { + name: pluginName, + stage: Infinity + }, + (stats, callback) => { + tracer.profiler.stopProfiling().then(parsedResults => { + if (parsedResults === undefined) { + tracer.profiler.destroy(); + tracer.trace.flush(); + tracer.end(callback); + return; + } + const cpuStartTime = parsedResults.profile.startTime; + const cpuEndTime = parsedResults.profile.endTime; -const RuntimeGlobals = __webpack_require__(49404); -const makeSerializable = __webpack_require__(26522); -const NullDependency = __webpack_require__(65845); + tracer.trace.completeEvent({ + name: "TaskQueueManager::ProcessTaskFromWorkQueue", + id: ++tracer.counter, + cat: ["toplevel"], + ts: cpuStartTime, + args: { + src_file: "../../ipc/ipc_moji_bootstrap.cc", + src_func: "Accept" + } + }); -/** @typedef {import("webpack-sources").ReplaceSource} ReplaceSource */ -/** @typedef {import("../Dependency")} Dependency */ -/** @typedef {import("../DependencyTemplate").DependencyTemplateContext} DependencyTemplateContext */ + tracer.trace.completeEvent({ + name: "EvaluateScript", + id: ++tracer.counter, + cat: ["devtools.timeline"], + ts: cpuStartTime, + dur: cpuEndTime - cpuStartTime, + args: { + data: { + url: "webpack", + lineNumber: 1, + columnNumber: 1, + frame: "0xFFF" + } + } + }); -class CreateScriptUrlDependency extends NullDependency { - /** - * @param {[number, number]} range range - */ - constructor(range) { - super(); - this.range = range; - } + tracer.trace.instantEvent({ + name: "CpuProfile", + id: ++tracer.counter, + cat: ["disabled-by-default-devtools.timeline"], + ts: cpuEndTime, + args: { + data: { + cpuProfile: parsedResults.profile + } + } + }); - get type() { - return "create script url"; + tracer.profiler.destroy(); + tracer.trace.flush(); + tracer.end(callback); + }); + } + ); } } -CreateScriptUrlDependency.Template = class CreateScriptUrlDependencyTemplate extends ( - NullDependency.Template -) { - /** - * @param {Dependency} dependency the dependency for which the template should be applied - * @param {ReplaceSource} source the current replace source which can be modified - * @param {DependencyTemplateContext} templateContext the context object - * @returns {void} - */ - apply(dependency, source, { runtimeRequirements }) { - const dep = /** @type {CreateScriptUrlDependency} */ (dependency); - - runtimeRequirements.add(RuntimeGlobals.createScriptUrl); - - source.insert(dep.range[0], `${RuntimeGlobals.createScriptUrl}(`); - source.insert(dep.range[1], ")"); +const interceptAllHooksFor = (instance, tracer, logLabel) => { + if (Reflect.has(instance, "hooks")) { + Object.keys(instance.hooks).forEach(hookName => { + const hook = instance.hooks[hookName]; + if (hook && !hook._fakeHook) { + hook.intercept(makeInterceptorFor(logLabel, tracer)(hookName)); + } + }); } }; -makeSerializable( - CreateScriptUrlDependency, - "webpack/lib/dependencies/CreateScriptUrlDependency" -); - -module.exports = CreateScriptUrlDependency; - - -/***/ }), +const interceptAllParserHooks = (moduleFactory, tracer) => { + const moduleTypes = [ + "javascript/auto", + "javascript/dynamic", + "javascript/esm", + "json", + "webassembly/async", + "webassembly/sync" + ]; -/***/ 14190: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + moduleTypes.forEach(moduleType => { + moduleFactory.hooks.parser + .for(moduleType) + .tap("ProfilingPlugin", (parser, parserOpts) => { + interceptAllHooksFor(parser, tracer, "Parser"); + }); + }); +}; -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ +const interceptAllJavascriptModulesPluginHooks = (compilation, tracer) => { + interceptAllHooksFor( + { + hooks: + __webpack_require__(76767).getCompilationHooks( + compilation + ) + }, + tracer, + "JavascriptModulesPlugin" + ); +}; +const makeInterceptorFor = (instance, tracer) => hookName => ({ + register: ({ name, type, context, fn }) => { + const newFn = makeNewProfiledTapFn(hookName, tracer, { + name, + type, + fn + }); + return { + name, + type, + context, + fn: newFn + }; + } +}); +// TODO improve typing +/** @typedef {(...args: TODO[]) => void | Promise} PluginFunction */ -const WebpackError = __webpack_require__(68422); -const makeSerializable = __webpack_require__(26522); +/** + * @param {string} hookName Name of the hook to profile. + * @param {Trace} tracer The trace object. + * @param {object} options Options for the profiled fn. + * @param {string} options.name Plugin name + * @param {string} options.type Plugin type (sync | async | promise) + * @param {PluginFunction} options.fn Plugin function + * @returns {PluginFunction} Chainable hooked function. + */ +const makeNewProfiledTapFn = (hookName, tracer, { name, type, fn }) => { + const defaultCategory = ["blink.user_timing"]; -class CriticalDependencyWarning extends WebpackError { - constructor(message) { - super(); + switch (type) { + case "promise": + return (...args) => { + const id = ++tracer.counter; + tracer.trace.begin({ + name, + id, + cat: defaultCategory + }); + const promise = /** @type {Promise<*>} */ (fn(...args)); + return promise.then(r => { + tracer.trace.end({ + name, + id, + cat: defaultCategory + }); + return r; + }); + }; + case "async": + return (...args) => { + const id = ++tracer.counter; + tracer.trace.begin({ + name, + id, + cat: defaultCategory + }); + const callback = args.pop(); + fn(...args, (...r) => { + tracer.trace.end({ + name, + id, + cat: defaultCategory + }); + callback(...r); + }); + }; + case "sync": + return (...args) => { + const id = ++tracer.counter; + // Do not instrument ourself due to the CPU + // profile needing to be the last event in the trace. + if (name === pluginName) { + return fn(...args); + } - this.name = "CriticalDependencyWarning"; - this.message = "Critical dependency: " + message; + tracer.trace.begin({ + name, + id, + cat: defaultCategory + }); + let r; + try { + r = fn(...args); + } catch (error) { + tracer.trace.end({ + name, + id, + cat: defaultCategory + }); + throw error; + } + tracer.trace.end({ + name, + id, + cat: defaultCategory + }); + return r; + }; + default: + break; } -} - -makeSerializable( - CriticalDependencyWarning, - "webpack/lib/dependencies/CriticalDependencyWarning" -); +}; -module.exports = CriticalDependencyWarning; +module.exports = ProfilingPlugin; +module.exports.Profiler = Profiler; /***/ }), -/***/ 82766: +/***/ 76309: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; @@ -77673,166 +74972,225 @@ module.exports = CriticalDependencyWarning; +const RuntimeGlobals = __webpack_require__(49404); const makeSerializable = __webpack_require__(26522); -const ModuleDependency = __webpack_require__(80944); - -class DelegatedSourceDependency extends ModuleDependency { - constructor(request) { - super(request); - } +const NullDependency = __webpack_require__(65845); - get type() { - return "delegated source"; - } +/** @typedef {import("webpack-sources").ReplaceSource} ReplaceSource */ +/** @typedef {import("../Dependency")} Dependency */ +/** @typedef {import("../DependencyTemplate").DependencyTemplateContext} DependencyTemplateContext */ - get category() { - return "esm"; +/** @type {Record} */ +const DEFINITIONS = { + f: { + definition: "var __WEBPACK_AMD_DEFINE_RESULT__;", + content: `!(__WEBPACK_AMD_DEFINE_RESULT__ = (#).call(exports, __webpack_require__, exports, module), + __WEBPACK_AMD_DEFINE_RESULT__ !== undefined && (module.exports = __WEBPACK_AMD_DEFINE_RESULT__))`, + requests: [ + RuntimeGlobals.require, + RuntimeGlobals.exports, + RuntimeGlobals.module + ] + }, + o: { + definition: "", + content: "!(module.exports = #)", + requests: [RuntimeGlobals.module] + }, + of: { + definition: + "var __WEBPACK_AMD_DEFINE_FACTORY__, __WEBPACK_AMD_DEFINE_RESULT__;", + content: `!(__WEBPACK_AMD_DEFINE_FACTORY__ = (#), + __WEBPACK_AMD_DEFINE_RESULT__ = (typeof __WEBPACK_AMD_DEFINE_FACTORY__ === 'function' ? + (__WEBPACK_AMD_DEFINE_FACTORY__.call(exports, __webpack_require__, exports, module)) : + __WEBPACK_AMD_DEFINE_FACTORY__), + __WEBPACK_AMD_DEFINE_RESULT__ !== undefined && (module.exports = __WEBPACK_AMD_DEFINE_RESULT__))`, + requests: [ + RuntimeGlobals.require, + RuntimeGlobals.exports, + RuntimeGlobals.module + ] + }, + af: { + definition: + "var __WEBPACK_AMD_DEFINE_ARRAY__, __WEBPACK_AMD_DEFINE_RESULT__;", + content: `!(__WEBPACK_AMD_DEFINE_ARRAY__ = #, __WEBPACK_AMD_DEFINE_RESULT__ = (#).apply(exports, __WEBPACK_AMD_DEFINE_ARRAY__), + __WEBPACK_AMD_DEFINE_RESULT__ !== undefined && (module.exports = __WEBPACK_AMD_DEFINE_RESULT__))`, + requests: [RuntimeGlobals.exports, RuntimeGlobals.module] + }, + ao: { + definition: "", + content: "!(#, module.exports = #)", + requests: [RuntimeGlobals.module] + }, + aof: { + definition: + "var __WEBPACK_AMD_DEFINE_FACTORY__, __WEBPACK_AMD_DEFINE_ARRAY__, __WEBPACK_AMD_DEFINE_RESULT__;", + content: `!(__WEBPACK_AMD_DEFINE_ARRAY__ = #, __WEBPACK_AMD_DEFINE_FACTORY__ = (#), + __WEBPACK_AMD_DEFINE_RESULT__ = (typeof __WEBPACK_AMD_DEFINE_FACTORY__ === 'function' ? + (__WEBPACK_AMD_DEFINE_FACTORY__.apply(exports, __WEBPACK_AMD_DEFINE_ARRAY__)) : __WEBPACK_AMD_DEFINE_FACTORY__), + __WEBPACK_AMD_DEFINE_RESULT__ !== undefined && (module.exports = __WEBPACK_AMD_DEFINE_RESULT__))`, + requests: [RuntimeGlobals.exports, RuntimeGlobals.module] + }, + lf: { + definition: "var XXX, XXXmodule;", + content: + "!(XXXmodule = { id: YYY, exports: {}, loaded: false }, XXX = (#).call(XXXmodule.exports, __webpack_require__, XXXmodule.exports, XXXmodule), XXXmodule.loaded = true, XXX === undefined && (XXX = XXXmodule.exports))", + requests: [RuntimeGlobals.require, RuntimeGlobals.module] + }, + lo: { + definition: "var XXX;", + content: "!(XXX = #)", + requests: [] + }, + lof: { + definition: "var XXX, XXXfactory, XXXmodule;", + content: + "!(XXXfactory = (#), (typeof XXXfactory === 'function' ? ((XXXmodule = { id: YYY, exports: {}, loaded: false }), (XXX = XXXfactory.call(XXXmodule.exports, __webpack_require__, XXXmodule.exports, XXXmodule)), (XXXmodule.loaded = true), XXX === undefined && (XXX = XXXmodule.exports)) : XXX = XXXfactory))", + requests: [RuntimeGlobals.require, RuntimeGlobals.module] + }, + laf: { + definition: "var __WEBPACK_AMD_DEFINE_ARRAY__, XXX, XXXexports;", + content: + "!(__WEBPACK_AMD_DEFINE_ARRAY__ = #, XXX = (#).apply(XXXexports = {}, __WEBPACK_AMD_DEFINE_ARRAY__), XXX === undefined && (XXX = XXXexports))", + requests: [] + }, + lao: { + definition: "var XXX;", + content: "!(#, XXX = #)", + requests: [] + }, + laof: { + definition: "var XXXarray, XXXfactory, XXXexports, XXX;", + content: `!(XXXarray = #, XXXfactory = (#), + (typeof XXXfactory === 'function' ? + ((XXX = XXXfactory.apply(XXXexports = {}, XXXarray)), XXX === undefined && (XXX = XXXexports)) : + (XXX = XXXfactory) + ))`, + requests: [] } -} - -makeSerializable( - DelegatedSourceDependency, - "webpack/lib/dependencies/DelegatedSourceDependency" -); - -module.exports = DelegatedSourceDependency; - - -/***/ }), - -/***/ 57839: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ - - - -const Dependency = __webpack_require__(50384); -const makeSerializable = __webpack_require__(26522); +}; -class DllEntryDependency extends Dependency { - constructor(dependencies, name) { +class AMDDefineDependency extends NullDependency { + constructor(range, arrayRange, functionRange, objectRange, namedModule) { super(); - - this.dependencies = dependencies; - this.name = name; + this.range = range; + this.arrayRange = arrayRange; + this.functionRange = functionRange; + this.objectRange = objectRange; + this.namedModule = namedModule; + this.localModule = null; } get type() { - return "dll entry"; + return "amd define"; } serialize(context) { const { write } = context; - - write(this.dependencies); - write(this.name); - + write(this.range); + write(this.arrayRange); + write(this.functionRange); + write(this.objectRange); + write(this.namedModule); + write(this.localModule); super.serialize(context); } deserialize(context) { const { read } = context; - - this.dependencies = read(); - this.name = read(); - + this.range = read(); + this.arrayRange = read(); + this.functionRange = read(); + this.objectRange = read(); + this.namedModule = read(); + this.localModule = read(); super.deserialize(context); } } makeSerializable( - DllEntryDependency, - "webpack/lib/dependencies/DllEntryDependency" + AMDDefineDependency, + "webpack/lib/dependencies/AMDDefineDependency" ); -module.exports = DllEntryDependency; - - -/***/ }), +AMDDefineDependency.Template = class AMDDefineDependencyTemplate extends ( + NullDependency.Template +) { + /** + * @param {Dependency} dependency the dependency for which the template should be applied + * @param {ReplaceSource} source the current replace source which can be modified + * @param {DependencyTemplateContext} templateContext the context object + * @returns {void} + */ + apply(dependency, source, { runtimeRequirements }) { + const dep = /** @type {AMDDefineDependency} */ (dependency); + const branch = this.branch(dep); + const { definition, content, requests } = DEFINITIONS[branch]; + for (const req of requests) { + runtimeRequirements.add(req); + } + this.replace(dep, source, definition, content); + } -/***/ 87370: -/***/ (function(__unused_webpack_module, exports) { + localModuleVar(dependency) { + return ( + dependency.localModule && + dependency.localModule.used && + dependency.localModule.variableName() + ); + } -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ + branch(dependency) { + const localModuleVar = this.localModuleVar(dependency) ? "l" : ""; + const arrayRange = dependency.arrayRange ? "a" : ""; + const objectRange = dependency.objectRange ? "o" : ""; + const functionRange = dependency.functionRange ? "f" : ""; + return localModuleVar + arrayRange + objectRange + functionRange; + } + replace(dependency, source, definition, text) { + const localModuleVar = this.localModuleVar(dependency); + if (localModuleVar) { + text = text.replace(/XXX/g, localModuleVar.replace(/\$/g, "$$$$")); + definition = definition.replace( + /XXX/g, + localModuleVar.replace(/\$/g, "$$$$") + ); + } + if (dependency.namedModule) { + text = text.replace(/YYY/g, JSON.stringify(dependency.namedModule)); + } -/** @typedef {import("../Parser").ParserState} ParserState */ + const texts = text.split("#"); -/** @type {WeakMap} */ -const parserStateExportsState = new WeakMap(); + if (definition) source.insert(0, definition); -/** - * @param {ParserState} parserState parser state - * @returns {void} - */ -exports.bailout = parserState => { - const value = parserStateExportsState.get(parserState); - parserStateExportsState.set(parserState, false); - if (value === true) { - parserState.module.buildMeta.exportsType = undefined; - parserState.module.buildMeta.defaultObject = false; - } -}; + let current = dependency.range[0]; + if (dependency.arrayRange) { + source.replace(current, dependency.arrayRange[0] - 1, texts.shift()); + current = dependency.arrayRange[1]; + } -/** - * @param {ParserState} parserState parser state - * @returns {void} - */ -exports.enable = parserState => { - const value = parserStateExportsState.get(parserState); - if (value === false) return; - parserStateExportsState.set(parserState, true); - if (value !== true) { - parserState.module.buildMeta.exportsType = "default"; - parserState.module.buildMeta.defaultObject = "redirect"; + if (dependency.objectRange) { + source.replace(current, dependency.objectRange[0] - 1, texts.shift()); + current = dependency.objectRange[1]; + } else if (dependency.functionRange) { + source.replace(current, dependency.functionRange[0] - 1, texts.shift()); + current = dependency.functionRange[1]; + } + source.replace(current, dependency.range[1] - 1, texts.shift()); + if (texts.length > 0) throw new Error("Implementation error"); } }; -/** - * @param {ParserState} parserState parser state - * @returns {void} - */ -exports.setFlagged = parserState => { - const value = parserStateExportsState.get(parserState); - if (value !== true) return; - const buildMeta = parserState.module.buildMeta; - if (buildMeta.exportsType === "dynamic") return; - buildMeta.exportsType = "flagged"; -}; - -/** - * @param {ParserState} parserState parser state - * @returns {void} - */ -exports.setDynamic = parserState => { - const value = parserStateExportsState.get(parserState); - if (value !== true) return; - parserState.module.buildMeta.exportsType = "dynamic"; -}; - -/** - * @param {ParserState} parserState parser state - * @returns {boolean} true, when enabled - */ -exports.isEnabled = parserState => { - const value = parserStateExportsState.get(parserState); - return value === true; -}; +module.exports = AMDDefineDependency; /***/ }), -/***/ 41075: +/***/ 78237: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; @@ -77843,179 +75201,358 @@ exports.isEnabled = parserState => { -const makeSerializable = __webpack_require__(26522); -const ModuleDependency = __webpack_require__(80944); - -class EntryDependency extends ModuleDependency { - /** - * @param {string} request request path for entry - */ - constructor(request) { - super(request); - } - - get type() { - return "entry"; - } - - get category() { - return "esm"; - } -} - -makeSerializable(EntryDependency, "webpack/lib/dependencies/EntryDependency"); - -module.exports = EntryDependency; - - -/***/ }), - -/***/ 30474: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { +const RuntimeGlobals = __webpack_require__(49404); +const AMDDefineDependency = __webpack_require__(76309); +const AMDRequireArrayDependency = __webpack_require__(98233); +const AMDRequireContextDependency = __webpack_require__(60958); +const AMDRequireItemDependency = __webpack_require__(90377); +const ConstDependency = __webpack_require__(60864); +const ContextDependencyHelpers = __webpack_require__(7114); +const DynamicExports = __webpack_require__(87370); +const LocalModuleDependency = __webpack_require__(67494); +const { addLocalModule, getLocalModule } = __webpack_require__(6311); -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ +const isBoundFunctionExpression = expr => { + if (expr.type !== "CallExpression") return false; + if (expr.callee.type !== "MemberExpression") return false; + if (expr.callee.computed) return false; + if (expr.callee.object.type !== "FunctionExpression") return false; + if (expr.callee.property.type !== "Identifier") return false; + if (expr.callee.property.name !== "bind") return false; + return true; +}; +const isUnboundFunctionExpression = expr => { + if (expr.type === "FunctionExpression") return true; + if (expr.type === "ArrowFunctionExpression") return true; + return false; +}; +const isCallable = expr => { + if (isUnboundFunctionExpression(expr)) return true; + if (isBoundFunctionExpression(expr)) return true; + return false; +}; -const { UsageState } = __webpack_require__(4295); -const makeSerializable = __webpack_require__(26522); -const NullDependency = __webpack_require__(65845); +class AMDDefineDependencyParserPlugin { + constructor(options) { + this.options = options; + } -/** @typedef {import("webpack-sources").ReplaceSource} ReplaceSource */ -/** @typedef {import("../ChunkGraph")} ChunkGraph */ -/** @typedef {import("../Dependency")} Dependency */ -/** @typedef {import("../Dependency").UpdateHashContext} UpdateHashContext */ -/** @typedef {import("../DependencyTemplate").DependencyTemplateContext} DependencyTemplateContext */ -/** @typedef {import("../Module")} Module */ -/** @typedef {import("../ModuleGraph")} ModuleGraph */ -/** @typedef {import("../util/Hash")} Hash */ -/** @typedef {import("../util/runtime").RuntimeSpec} RuntimeSpec */ + apply(parser) { + parser.hooks.call + .for("define") + .tap( + "AMDDefineDependencyParserPlugin", + this.processCallDefine.bind(this, parser) + ); + } -/** - * @param {ModuleGraph} moduleGraph the module graph - * @param {Module} module the module - * @param {string | null} exportName name of the export if any - * @param {string | null} property name of the requested property - * @param {RuntimeSpec} runtime for which runtime - * @returns {any} value of the property - */ -const getProperty = (moduleGraph, module, exportName, property, runtime) => { - if (!exportName) { - switch (property) { - case "usedExports": { - const usedExports = moduleGraph - .getExportsInfo(module) - .getUsedExports(runtime); + processArray(parser, expr, param, identifiers, namedModule) { + if (param.isArray()) { + param.items.forEach((param, idx) => { if ( - typeof usedExports === "boolean" || - usedExports === undefined || - usedExports === null - ) { - return usedExports; + param.isString() && + ["require", "module", "exports"].includes(param.string) + ) + identifiers[idx] = param.string; + const result = this.processItem(parser, expr, param, namedModule); + if (result === undefined) { + this.processContext(parser, expr, param); } - return Array.from(usedExports).sort(); + }); + return true; + } else if (param.isConstArray()) { + const deps = []; + param.array.forEach((request, idx) => { + let dep; + let localModule; + if (request === "require") { + identifiers[idx] = request; + dep = "__webpack_require__"; + } else if (["exports", "module"].includes(request)) { + identifiers[idx] = request; + dep = request; + } else if ((localModule = getLocalModule(parser.state, request))) { + localModule.flagUsed(); + dep = new LocalModuleDependency(localModule, undefined, false); + dep.loc = expr.loc; + parser.state.module.addPresentationalDependency(dep); + } else { + dep = this.newRequireItemDependency(request); + dep.loc = expr.loc; + dep.optional = !!parser.scope.inTry; + parser.state.current.addDependency(dep); + } + deps.push(dep); + }); + const dep = this.newRequireArrayDependency(deps, param.range); + dep.loc = expr.loc; + dep.optional = !!parser.scope.inTry; + parser.state.module.addPresentationalDependency(dep); + return true; + } + } + processItem(parser, expr, param, namedModule) { + if (param.isConditional()) { + param.options.forEach(param => { + const result = this.processItem(parser, expr, param); + if (result === undefined) { + this.processContext(parser, expr, param); + } + }); + return true; + } else if (param.isString()) { + let dep, localModule; + if (param.string === "require") { + dep = new ConstDependency("__webpack_require__", param.range, [ + RuntimeGlobals.require + ]); + } else if (param.string === "exports") { + dep = new ConstDependency("exports", param.range, [ + RuntimeGlobals.exports + ]); + } else if (param.string === "module") { + dep = new ConstDependency("module", param.range, [ + RuntimeGlobals.module + ]); + } else if ( + (localModule = getLocalModule(parser.state, param.string, namedModule)) + ) { + localModule.flagUsed(); + dep = new LocalModuleDependency(localModule, param.range, false); + } else { + dep = this.newRequireItemDependency(param.string, param.range); + dep.optional = !!parser.scope.inTry; + parser.state.current.addDependency(dep); + return true; + } + dep.loc = expr.loc; + parser.state.module.addPresentationalDependency(dep); + return true; + } + } + processContext(parser, expr, param) { + const dep = ContextDependencyHelpers.create( + AMDRequireContextDependency, + param.range, + param, + expr, + this.options, + { + category: "amd" + }, + parser + ); + if (!dep) return; + dep.loc = expr.loc; + dep.optional = !!parser.scope.inTry; + parser.state.current.addDependency(dep); + return true; + } + + processCallDefine(parser, expr) { + let array, fn, obj, namedModule; + switch (expr.arguments.length) { + case 1: + if (isCallable(expr.arguments[0])) { + // define(f() {…}) + fn = expr.arguments[0]; + } else if (expr.arguments[0].type === "ObjectExpression") { + // define({…}) + obj = expr.arguments[0]; + } else { + // define(expr) + // unclear if function or object + obj = fn = expr.arguments[0]; + } + break; + case 2: + if (expr.arguments[0].type === "Literal") { + namedModule = expr.arguments[0].value; + // define("…", …) + if (isCallable(expr.arguments[1])) { + // define("…", f() {…}) + fn = expr.arguments[1]; + } else if (expr.arguments[1].type === "ObjectExpression") { + // define("…", {…}) + obj = expr.arguments[1]; + } else { + // define("…", expr) + // unclear if function or object + obj = fn = expr.arguments[1]; + } + } else { + array = expr.arguments[0]; + if (isCallable(expr.arguments[1])) { + // define([…], f() {}) + fn = expr.arguments[1]; + } else if (expr.arguments[1].type === "ObjectExpression") { + // define([…], {…}) + obj = expr.arguments[1]; + } else { + // define([…], expr) + // unclear if function or object + obj = fn = expr.arguments[1]; + } + } + break; + case 3: + // define("…", […], f() {…}) + namedModule = expr.arguments[0].value; + array = expr.arguments[1]; + if (isCallable(expr.arguments[2])) { + // define("…", […], f() {}) + fn = expr.arguments[2]; + } else if (expr.arguments[2].type === "ObjectExpression") { + // define("…", […], {…}) + obj = expr.arguments[2]; + } else { + // define("…", […], expr) + // unclear if function or object + obj = fn = expr.arguments[2]; + } + break; + default: + return; + } + DynamicExports.bailout(parser.state); + let fnParams = null; + let fnParamsOffset = 0; + if (fn) { + if (isUnboundFunctionExpression(fn)) { + fnParams = fn.params; + } else if (isBoundFunctionExpression(fn)) { + fnParams = fn.callee.object.params; + fnParamsOffset = fn.arguments.length - 1; + if (fnParamsOffset < 0) { + fnParamsOffset = 0; + } + } + } + let fnRenames = new Map(); + if (array) { + const identifiers = {}; + const param = parser.evaluateExpression(array); + const result = this.processArray( + parser, + expr, + param, + identifiers, + namedModule + ); + if (!result) return; + if (fnParams) { + fnParams = fnParams.slice(fnParamsOffset).filter((param, idx) => { + if (identifiers[idx]) { + fnRenames.set(param.name, parser.getVariableInfo(identifiers[idx])); + return false; + } + return true; + }); + } + } else { + const identifiers = ["require", "exports", "module"]; + if (fnParams) { + fnParams = fnParams.slice(fnParamsOffset).filter((param, idx) => { + if (identifiers[idx]) { + fnRenames.set(param.name, parser.getVariableInfo(identifiers[idx])); + return false; + } + return true; + }); } } - } - switch (property) { - case "used": - return ( - moduleGraph.getExportsInfo(module).getUsed(exportName, runtime) !== - UsageState.Unused + let inTry; + if (fn && isUnboundFunctionExpression(fn)) { + inTry = parser.scope.inTry; + parser.inScope(fnParams, () => { + for (const [name, varInfo] of fnRenames) { + parser.setVariable(name, varInfo); + } + parser.scope.inTry = inTry; + if (fn.body.type === "BlockStatement") { + parser.detectMode(fn.body.body); + const prev = parser.prevStatement; + parser.preWalkStatement(fn.body); + parser.prevStatement = prev; + parser.walkStatement(fn.body); + } else { + parser.walkExpression(fn.body); + } + }); + } else if (fn && isBoundFunctionExpression(fn)) { + inTry = parser.scope.inTry; + parser.inScope( + fn.callee.object.params.filter( + i => !["require", "module", "exports"].includes(i.name) + ), + () => { + for (const [name, varInfo] of fnRenames) { + parser.setVariable(name, varInfo); + } + parser.scope.inTry = inTry; + if (fn.callee.object.body.type === "BlockStatement") { + parser.detectMode(fn.callee.object.body.body); + const prev = parser.prevStatement; + parser.preWalkStatement(fn.callee.object.body); + parser.prevStatement = prev; + parser.walkStatement(fn.callee.object.body); + } else { + parser.walkExpression(fn.callee.object.body); + } + } ); - case "useInfo": { - const state = moduleGraph - .getExportsInfo(module) - .getUsed(exportName, runtime); - switch (state) { - case UsageState.Used: - case UsageState.OnlyPropertiesUsed: - return true; - case UsageState.Unused: - return false; - case UsageState.NoInfo: - return undefined; - case UsageState.Unknown: - return null; - default: - throw new Error(`Unexpected UsageState ${state}`); + if (fn.arguments) { + parser.walkExpressions(fn.arguments); } + } else if (fn || obj) { + parser.walkExpression(fn || obj); } - case "provideInfo": - return moduleGraph.getExportsInfo(module).isExportProvided(exportName); - } - return undefined; -}; - -class ExportsInfoDependency extends NullDependency { - constructor(range, exportName, property) { - super(); - this.range = range; - this.exportName = exportName; - this.property = property; - } - - serialize(context) { - const { write } = context; - write(this.range); - write(this.exportName); - write(this.property); - super.serialize(context); - } - static deserialize(context) { - const obj = new ExportsInfoDependency( - context.read(), - context.read(), - context.read() + const dep = this.newDefineDependency( + expr.range, + array ? array.range : null, + fn ? fn.range : null, + obj ? obj.range : null, + namedModule ? namedModule : null ); - obj.deserialize(context); - return obj; + dep.loc = expr.loc; + if (namedModule) { + dep.localModule = addLocalModule(parser.state, namedModule); + } + parser.state.module.addPresentationalDependency(dep); + return true; } -} - -makeSerializable( - ExportsInfoDependency, - "webpack/lib/dependencies/ExportsInfoDependency" -); - -ExportsInfoDependency.Template = class ExportsInfoDependencyTemplate extends ( - NullDependency.Template -) { - /** - * @param {Dependency} dependency the dependency for which the template should be applied - * @param {ReplaceSource} source the current replace source which can be modified - * @param {DependencyTemplateContext} templateContext the context object - * @returns {void} - */ - apply(dependency, source, { module, moduleGraph, runtime }) { - const dep = /** @type {ExportsInfoDependency} */ (dependency); - const value = getProperty( - moduleGraph, - module, - dep.exportName, - dep.property, - runtime - ); - source.replace( - dep.range[0], - dep.range[1] - 1, - value === undefined ? "undefined" : JSON.stringify(value) + newDefineDependency( + range, + arrayRange, + functionRange, + objectRange, + namedModule + ) { + return new AMDDefineDependency( + range, + arrayRange, + functionRange, + objectRange, + namedModule ); } -}; - -module.exports = ExportsInfoDependency; + newRequireArrayDependency(depsArray, range) { + return new AMDRequireArrayDependency(depsArray, range); + } + newRequireItemDependency(request, range) { + return new AMDRequireItemDependency(request, range); + } +} +module.exports = AMDDefineDependencyParserPlugin; /***/ }), -/***/ 38421: +/***/ 82916: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; @@ -78026,181 +75563,220 @@ module.exports = ExportsInfoDependency; -const Template = __webpack_require__(92066); -const makeSerializable = __webpack_require__(26522); -const HarmonyImportDependency = __webpack_require__(19577); -const NullDependency = __webpack_require__(65845); +const RuntimeGlobals = __webpack_require__(49404); +const { + approve, + evaluateToIdentifier, + evaluateToString, + toConstantDependency +} = __webpack_require__(28723); -/** @typedef {import("webpack-sources").ReplaceSource} ReplaceSource */ -/** @typedef {import("../Dependency")} Dependency */ -/** @typedef {import("../DependencyTemplate").DependencyTemplateContext} DependencyTemplateContext */ -/** @typedef {import("./HarmonyAcceptImportDependency")} HarmonyAcceptImportDependency */ +const AMDDefineDependency = __webpack_require__(76309); +const AMDDefineDependencyParserPlugin = __webpack_require__(78237); +const AMDRequireArrayDependency = __webpack_require__(98233); +const AMDRequireContextDependency = __webpack_require__(60958); +const AMDRequireDependenciesBlockParserPlugin = __webpack_require__(78012); +const AMDRequireDependency = __webpack_require__(11311); +const AMDRequireItemDependency = __webpack_require__(90377); +const { + AMDDefineRuntimeModule, + AMDOptionsRuntimeModule +} = __webpack_require__(35469); +const ConstDependency = __webpack_require__(60864); +const LocalModuleDependency = __webpack_require__(67494); +const UnsupportedDependency = __webpack_require__(41381); -class HarmonyAcceptDependency extends NullDependency { +/** @typedef {import("../../declarations/WebpackOptions").ModuleOptionsNormalized} ModuleOptions */ +/** @typedef {import("../Compiler")} Compiler */ + +class AMDPlugin { /** - * @param {[number, number]} range expression range - * @param {HarmonyAcceptImportDependency[]} dependencies import dependencies - * @param {boolean} hasCallback true, if the range wraps an existing callback + * @param {Record} amdOptions the AMD options */ - constructor(range, dependencies, hasCallback) { - super(); - this.range = range; - this.dependencies = dependencies; - this.hasCallback = hasCallback; - } - - get type() { - return "accepted harmony modules"; - } - - serialize(context) { - const { write } = context; - write(this.range); - write(this.dependencies); - write(this.hasCallback); - super.serialize(context); - } - - deserialize(context) { - const { read } = context; - this.range = read(); - this.dependencies = read(); - this.hasCallback = read(); - super.deserialize(context); + constructor(amdOptions) { + this.amdOptions = amdOptions; } -} - -makeSerializable( - HarmonyAcceptDependency, - "webpack/lib/dependencies/HarmonyAcceptDependency" -); -HarmonyAcceptDependency.Template = class HarmonyAcceptDependencyTemplate extends ( - NullDependency.Template -) { /** - * @param {Dependency} dependency the dependency for which the template should be applied - * @param {ReplaceSource} source the current replace source which can be modified - * @param {DependencyTemplateContext} templateContext the context object + * Apply the plugin + * @param {Compiler} compiler the compiler instance * @returns {void} */ - apply(dependency, source, templateContext) { - const dep = /** @type {HarmonyAcceptDependency} */ (dependency); - const { - module, - runtime, - runtimeRequirements, - runtimeTemplate, - moduleGraph, - chunkGraph - } = templateContext; - const content = dep.dependencies - .map(dependency => { - const referencedModule = moduleGraph.getModule(dependency); - return { - dependency, - runtimeCondition: referencedModule - ? HarmonyImportDependency.Template.getImportEmittedRuntime( - module, - referencedModule - ) - : false - }; - }) - .filter(({ runtimeCondition }) => runtimeCondition !== false) - .map(({ dependency, runtimeCondition }) => { - const condition = runtimeTemplate.runtimeConditionExpression({ - chunkGraph, - runtime, - runtimeCondition, - runtimeRequirements - }); - const s = dependency.getImportStatement(true, templateContext); - const code = s[0] + s[1]; - if (condition !== "true") { - return `if (${condition}) {\n${Template.indent(code)}\n}\n`; - } - return code; - }) - .join(""); + apply(compiler) { + const amdOptions = this.amdOptions; + compiler.hooks.compilation.tap( + "AMDPlugin", + (compilation, { contextModuleFactory, normalModuleFactory }) => { + compilation.dependencyTemplates.set( + AMDRequireDependency, + new AMDRequireDependency.Template() + ); - if (dep.hasCallback) { - if (runtimeTemplate.supportsArrowFunction()) { - source.insert( - dep.range[0], - `__WEBPACK_OUTDATED_DEPENDENCIES__ => { ${content}(` + compilation.dependencyFactories.set( + AMDRequireItemDependency, + normalModuleFactory ); - source.insert(dep.range[1], ")(__WEBPACK_OUTDATED_DEPENDENCIES__); }"); - } else { - source.insert( - dep.range[0], - `function(__WEBPACK_OUTDATED_DEPENDENCIES__) { ${content}(` + compilation.dependencyTemplates.set( + AMDRequireItemDependency, + new AMDRequireItemDependency.Template() ); - source.insert( - dep.range[1], - ")(__WEBPACK_OUTDATED_DEPENDENCIES__); }.bind(this)" + + compilation.dependencyTemplates.set( + AMDRequireArrayDependency, + new AMDRequireArrayDependency.Template() ); - } - return; - } - const arrow = runtimeTemplate.supportsArrowFunction(); - source.insert( - dep.range[1] - 0.5, - `, ${arrow ? "() =>" : "function()"} { ${content} }` - ); - } -}; + compilation.dependencyFactories.set( + AMDRequireContextDependency, + contextModuleFactory + ); + compilation.dependencyTemplates.set( + AMDRequireContextDependency, + new AMDRequireContextDependency.Template() + ); -module.exports = HarmonyAcceptDependency; + compilation.dependencyTemplates.set( + AMDDefineDependency, + new AMDDefineDependency.Template() + ); + compilation.dependencyTemplates.set( + UnsupportedDependency, + new UnsupportedDependency.Template() + ); -/***/ }), + compilation.dependencyTemplates.set( + LocalModuleDependency, + new LocalModuleDependency.Template() + ); -/***/ 35316: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + compilation.hooks.runtimeRequirementInModule + .for(RuntimeGlobals.amdDefine) + .tap("AMDPlugin", (module, set) => { + set.add(RuntimeGlobals.require); + }); -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ + compilation.hooks.runtimeRequirementInModule + .for(RuntimeGlobals.amdOptions) + .tap("AMDPlugin", (module, set) => { + set.add(RuntimeGlobals.requireScope); + }); + compilation.hooks.runtimeRequirementInTree + .for(RuntimeGlobals.amdDefine) + .tap("AMDPlugin", (chunk, set) => { + compilation.addRuntimeModule(chunk, new AMDDefineRuntimeModule()); + }); + compilation.hooks.runtimeRequirementInTree + .for(RuntimeGlobals.amdOptions) + .tap("AMDPlugin", (chunk, set) => { + compilation.addRuntimeModule( + chunk, + new AMDOptionsRuntimeModule(amdOptions) + ); + }); -const makeSerializable = __webpack_require__(26522); -const HarmonyImportDependency = __webpack_require__(19577); + const handler = (parser, parserOptions) => { + if (parserOptions.amd !== undefined && !parserOptions.amd) return; -/** @typedef {import("webpack-sources").ReplaceSource} ReplaceSource */ -/** @typedef {import("../Dependency")} Dependency */ -/** @typedef {import("../DependencyTemplate").DependencyTemplateContext} DependencyTemplateContext */ + const tapOptionsHooks = (optionExpr, rootName, getMembers) => { + parser.hooks.expression + .for(optionExpr) + .tap( + "AMDPlugin", + toConstantDependency(parser, RuntimeGlobals.amdOptions, [ + RuntimeGlobals.amdOptions + ]) + ); + parser.hooks.evaluateIdentifier + .for(optionExpr) + .tap( + "AMDPlugin", + evaluateToIdentifier(optionExpr, rootName, getMembers, true) + ); + parser.hooks.evaluateTypeof + .for(optionExpr) + .tap("AMDPlugin", evaluateToString("object")); + parser.hooks.typeof + .for(optionExpr) + .tap( + "AMDPlugin", + toConstantDependency(parser, JSON.stringify("object")) + ); + }; -class HarmonyAcceptImportDependency extends HarmonyImportDependency { - constructor(request) { - super(request, NaN); - this.weak = true; - } + new AMDRequireDependenciesBlockParserPlugin(parserOptions).apply( + parser + ); + new AMDDefineDependencyParserPlugin(parserOptions).apply(parser); - get type() { - return "harmony accept"; - } -} + tapOptionsHooks("define.amd", "define", () => "amd"); + tapOptionsHooks("require.amd", "require", () => ["amd"]); + tapOptionsHooks( + "__webpack_amd_options__", + "__webpack_amd_options__", + () => [] + ); -makeSerializable( - HarmonyAcceptImportDependency, - "webpack/lib/dependencies/HarmonyAcceptImportDependency" -); + parser.hooks.expression.for("define").tap("AMDPlugin", expr => { + const dep = new ConstDependency( + RuntimeGlobals.amdDefine, + expr.range, + [RuntimeGlobals.amdDefine] + ); + dep.loc = expr.loc; + parser.state.module.addPresentationalDependency(dep); + return true; + }); + parser.hooks.typeof + .for("define") + .tap( + "AMDPlugin", + toConstantDependency(parser, JSON.stringify("function")) + ); + parser.hooks.evaluateTypeof + .for("define") + .tap("AMDPlugin", evaluateToString("function")); + parser.hooks.canRename.for("define").tap("AMDPlugin", approve); + parser.hooks.rename.for("define").tap("AMDPlugin", expr => { + const dep = new ConstDependency( + RuntimeGlobals.amdDefine, + expr.range, + [RuntimeGlobals.amdDefine] + ); + dep.loc = expr.loc; + parser.state.module.addPresentationalDependency(dep); + return false; + }); + parser.hooks.typeof + .for("require") + .tap( + "AMDPlugin", + toConstantDependency(parser, JSON.stringify("function")) + ); + parser.hooks.evaluateTypeof + .for("require") + .tap("AMDPlugin", evaluateToString("function")); + }; -HarmonyAcceptImportDependency.Template = class HarmonyAcceptImportDependencyTemplate extends ( - HarmonyImportDependency.Template -) {}; + normalModuleFactory.hooks.parser + .for("javascript/auto") + .tap("AMDPlugin", handler); + normalModuleFactory.hooks.parser + .for("javascript/dynamic") + .tap("AMDPlugin", handler); + } + ); + } +} -module.exports = HarmonyAcceptImportDependency; +module.exports = AMDPlugin; /***/ }), -/***/ 56164: +/***/ 98233: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; @@ -78211,30 +75787,56 @@ module.exports = HarmonyAcceptImportDependency; -const { UsageState } = __webpack_require__(4295); -const InitFragment = __webpack_require__(51739); -const RuntimeGlobals = __webpack_require__(49404); +const DependencyTemplate = __webpack_require__(17600); const makeSerializable = __webpack_require__(26522); const NullDependency = __webpack_require__(65845); /** @typedef {import("webpack-sources").ReplaceSource} ReplaceSource */ /** @typedef {import("../Dependency")} Dependency */ /** @typedef {import("../DependencyTemplate").DependencyTemplateContext} DependencyTemplateContext */ -/** @typedef {import("../Module")} Module */ -class HarmonyCompatibilityDependency extends NullDependency { +class AMDRequireArrayDependency extends NullDependency { + constructor(depsArray, range) { + super(); + + this.depsArray = depsArray; + this.range = range; + } + get type() { - return "harmony export header"; + return "amd require array"; + } + + get category() { + return "amd"; + } + + serialize(context) { + const { write } = context; + + write(this.depsArray); + write(this.range); + + super.serialize(context); + } + + deserialize(context) { + const { read } = context; + + this.depsArray = read(); + this.range = read(); + + super.deserialize(context); } } makeSerializable( - HarmonyCompatibilityDependency, - "webpack/lib/dependencies/HarmonyCompatibilityDependency" + AMDRequireArrayDependency, + "webpack/lib/dependencies/AMDRequireArrayDependency" ); -HarmonyCompatibilityDependency.Template = class HarmonyExportDependencyTemplate extends ( - NullDependency.Template +AMDRequireArrayDependency.Template = class AMDRequireArrayDependencyTemplate extends ( + DependencyTemplate ) { /** * @param {Dependency} dependency the dependency for which the template should be applied @@ -78242,64 +75844,46 @@ HarmonyCompatibilityDependency.Template = class HarmonyExportDependencyTemplate * @param {DependencyTemplateContext} templateContext the context object * @returns {void} */ - apply( - dependency, - source, - { - module, - runtimeTemplate, - moduleGraph, - initFragments, - runtimeRequirements, - runtime, - concatenationScope - } + apply(dependency, source, templateContext) { + const dep = /** @type {AMDRequireArrayDependency} */ (dependency); + const content = this.getContent(dep, templateContext); + source.replace(dep.range[0], dep.range[1] - 1, content); + } + + getContent(dep, templateContext) { + const requires = dep.depsArray.map(dependency => { + return this.contentForDependency(dependency, templateContext); + }); + return `[${requires.join(", ")}]`; + } + + contentForDependency( + dep, + { runtimeTemplate, moduleGraph, chunkGraph, runtimeRequirements } ) { - if (concatenationScope) return; - const exportsInfo = moduleGraph.getExportsInfo(module); - if ( - exportsInfo.getReadOnlyExportInfo("__esModule").getUsed(runtime) !== - UsageState.Unused - ) { - const content = runtimeTemplate.defineEsModuleFlagStatement({ - exportsArgument: module.exportsArgument, + if (typeof dep === "string") { + return dep; + } + + if (dep.localModule) { + return dep.localModule.variableName(); + } else { + return runtimeTemplate.moduleExports({ + module: moduleGraph.getModule(dep), + chunkGraph, + request: dep.request, runtimeRequirements }); - initFragments.push( - new InitFragment( - content, - InitFragment.STAGE_HARMONY_EXPORTS, - 0, - "harmony compatibility" - ) - ); - } - if (moduleGraph.isAsync(module)) { - runtimeRequirements.add(RuntimeGlobals.module); - runtimeRequirements.add(RuntimeGlobals.asyncModule); - initFragments.push( - new InitFragment( - runtimeTemplate.supportsArrowFunction() - ? `${RuntimeGlobals.asyncModule}(${module.moduleArgument}, async (__webpack_handle_async_dependencies__) => {\n` - : `${RuntimeGlobals.asyncModule}(${module.moduleArgument}, async function (__webpack_handle_async_dependencies__) {\n`, - InitFragment.STAGE_ASYNC_BOUNDARY, - 0, - undefined, - module.buildMeta.async - ? `\n__webpack_handle_async_dependencies__();\n}, 1);` - : "\n});" - ) - ); } } }; -module.exports = HarmonyCompatibilityDependency; +module.exports = AMDRequireArrayDependency; /***/ }), -/***/ 63683: +/***/ 60958: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; @@ -78310,101 +75894,57 @@ module.exports = HarmonyCompatibilityDependency; -const DynamicExports = __webpack_require__(87370); -const HarmonyCompatibilityDependency = __webpack_require__(56164); -const HarmonyExports = __webpack_require__(37637); +const makeSerializable = __webpack_require__(26522); +const ContextDependency = __webpack_require__(67840); -module.exports = class HarmonyDetectionParserPlugin { - constructor(options) { - const { topLevelAwait = false } = options || {}; - this.topLevelAwait = topLevelAwait; +class AMDRequireContextDependency extends ContextDependency { + constructor(options, range, valueRange) { + super(options); + + this.range = range; + this.valueRange = valueRange; } - apply(parser) { - parser.hooks.program.tap("HarmonyDetectionParserPlugin", ast => { - const isStrictHarmony = parser.state.module.type === "javascript/esm"; - const isHarmony = - isStrictHarmony || - ast.body.some( - statement => - statement.type === "ImportDeclaration" || - statement.type === "ExportDefaultDeclaration" || - statement.type === "ExportNamedDeclaration" || - statement.type === "ExportAllDeclaration" - ); - if (isHarmony) { - const module = parser.state.module; - const compatDep = new HarmonyCompatibilityDependency(); - compatDep.loc = { - start: { - line: -1, - column: 0 - }, - end: { - line: -1, - column: 0 - }, - index: -3 - }; - module.addPresentationalDependency(compatDep); - DynamicExports.bailout(parser.state); - HarmonyExports.enable(parser.state, isStrictHarmony); - parser.scope.isStrict = true; - } - }); + get type() { + return "amd require context"; + } - parser.hooks.topLevelAwait.tap("HarmonyDetectionParserPlugin", () => { - const module = parser.state.module; - if (!this.topLevelAwait) { - throw new Error( - "The top-level-await experiment is not enabled (set experiments.topLevelAwait: true to enabled it)" - ); - } - if (!HarmonyExports.isEnabled(parser.state)) { - throw new Error( - "Top-level-await is only supported in EcmaScript Modules" - ); - } - module.buildMeta.async = true; - }); + get category() { + return "amd"; + } - const skipInHarmony = () => { - if (HarmonyExports.isEnabled(parser.state)) { - return true; - } - }; + serialize(context) { + const { write } = context; - const nullInHarmony = () => { - if (HarmonyExports.isEnabled(parser.state)) { - return null; - } - }; + write(this.range); + write(this.valueRange); - const nonHarmonyIdentifiers = ["define", "exports"]; - for (const identifier of nonHarmonyIdentifiers) { - parser.hooks.evaluateTypeof - .for(identifier) - .tap("HarmonyDetectionParserPlugin", nullInHarmony); - parser.hooks.typeof - .for(identifier) - .tap("HarmonyDetectionParserPlugin", skipInHarmony); - parser.hooks.evaluate - .for(identifier) - .tap("HarmonyDetectionParserPlugin", nullInHarmony); - parser.hooks.expression - .for(identifier) - .tap("HarmonyDetectionParserPlugin", skipInHarmony); - parser.hooks.call - .for(identifier) - .tap("HarmonyDetectionParserPlugin", skipInHarmony); - } + super.serialize(context); } -}; + + deserialize(context) { + const { read } = context; + + this.range = read(); + this.valueRange = read(); + + super.deserialize(context); + } +} + +makeSerializable( + AMDRequireContextDependency, + "webpack/lib/dependencies/AMDRequireContextDependency" +); + +AMDRequireContextDependency.Template = __webpack_require__(18259); + +module.exports = AMDRequireContextDependency; /***/ }), -/***/ 70925: +/***/ 69675: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; @@ -78415,189 +75955,313 @@ module.exports = class HarmonyDetectionParserPlugin { -const InnerGraph = __webpack_require__(92886); -const ConstDependency = __webpack_require__(60864); -const HarmonyExportExpressionDependency = __webpack_require__(22705); -const HarmonyExportHeaderDependency = __webpack_require__(67159); -const HarmonyExportImportedSpecifierDependency = __webpack_require__(77952); -const HarmonyExportSpecifierDependency = __webpack_require__(59042); -const { ExportPresenceModes } = __webpack_require__(19577); -const { - harmonySpecifierTag, - getAssertions -} = __webpack_require__(76581); -const HarmonyImportSideEffectDependency = __webpack_require__(76853); +const AsyncDependenciesBlock = __webpack_require__(11315); +const makeSerializable = __webpack_require__(26522); -const { HarmonyStarExportsList } = HarmonyExportImportedSpecifierDependency; +class AMDRequireDependenciesBlock extends AsyncDependenciesBlock { + constructor(loc, request) { + super(null, loc, request); + } +} -module.exports = class HarmonyExportDependencyParserPlugin { +makeSerializable( + AMDRequireDependenciesBlock, + "webpack/lib/dependencies/AMDRequireDependenciesBlock" +); + +module.exports = AMDRequireDependenciesBlock; + + +/***/ }), + +/***/ 78012: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ + + + +const RuntimeGlobals = __webpack_require__(49404); +const UnsupportedFeatureWarning = __webpack_require__(9532); +const AMDRequireArrayDependency = __webpack_require__(98233); +const AMDRequireContextDependency = __webpack_require__(60958); +const AMDRequireDependenciesBlock = __webpack_require__(69675); +const AMDRequireDependency = __webpack_require__(11311); +const AMDRequireItemDependency = __webpack_require__(90377); +const ConstDependency = __webpack_require__(60864); +const ContextDependencyHelpers = __webpack_require__(7114); +const LocalModuleDependency = __webpack_require__(67494); +const { getLocalModule } = __webpack_require__(6311); +const UnsupportedDependency = __webpack_require__(41381); +const getFunctionExpression = __webpack_require__(70108); + +class AMDRequireDependenciesBlockParserPlugin { constructor(options) { - this.exportPresenceMode = - options.reexportExportsPresence !== undefined - ? ExportPresenceModes.fromUserOption(options.reexportExportsPresence) - : options.exportsPresence !== undefined - ? ExportPresenceModes.fromUserOption(options.exportsPresence) - : options.strictExportPresence - ? ExportPresenceModes.ERROR - : ExportPresenceModes.AUTO; + this.options = options; + } + + processFunctionArgument(parser, expression) { + let bindThis = true; + const fnData = getFunctionExpression(expression); + if (fnData) { + parser.inScope( + fnData.fn.params.filter(i => { + return !["require", "module", "exports"].includes(i.name); + }), + () => { + if (fnData.fn.body.type === "BlockStatement") { + parser.walkStatement(fnData.fn.body); + } else { + parser.walkExpression(fnData.fn.body); + } + } + ); + parser.walkExpressions(fnData.expressions); + if (fnData.needThis === false) { + bindThis = false; + } + } else { + parser.walkExpression(expression); + } + return bindThis; } apply(parser) { - const { exportPresenceMode } = this; - parser.hooks.export.tap( - "HarmonyExportDependencyParserPlugin", - statement => { - const dep = new HarmonyExportHeaderDependency( - statement.declaration && statement.declaration.range, - statement.range - ); - dep.loc = Object.create(statement.loc); - dep.loc.index = -1; - parser.state.module.addPresentationalDependency(dep); - return true; + parser.hooks.call + .for("require") + .tap( + "AMDRequireDependenciesBlockParserPlugin", + this.processCallRequire.bind(this, parser) + ); + } + + processArray(parser, expr, param) { + if (param.isArray()) { + for (const p of param.items) { + const result = this.processItem(parser, expr, p); + if (result === undefined) { + this.processContext(parser, expr, p); + } } - ); - parser.hooks.exportImport.tap( - "HarmonyExportDependencyParserPlugin", - (statement, source) => { - parser.state.lastHarmonyImportOrder = - (parser.state.lastHarmonyImportOrder || 0) + 1; - const clearDep = new ConstDependency("", statement.range); - clearDep.loc = Object.create(statement.loc); - clearDep.loc.index = -1; - parser.state.module.addPresentationalDependency(clearDep); - const sideEffectDep = new HarmonyImportSideEffectDependency( - source, - parser.state.lastHarmonyImportOrder, - getAssertions(statement) - ); - sideEffectDep.loc = Object.create(statement.loc); - sideEffectDep.loc.index = -1; - parser.state.current.addDependency(sideEffectDep); - return true; + return true; + } else if (param.isConstArray()) { + const deps = []; + for (const request of param.array) { + let dep, localModule; + if (request === "require") { + dep = "__webpack_require__"; + } else if (["exports", "module"].includes(request)) { + dep = request; + } else if ((localModule = getLocalModule(parser.state, request))) { + localModule.flagUsed(); + dep = new LocalModuleDependency(localModule, undefined, false); + dep.loc = expr.loc; + parser.state.module.addPresentationalDependency(dep); + } else { + dep = this.newRequireItemDependency(request); + dep.loc = expr.loc; + dep.optional = !!parser.scope.inTry; + parser.state.current.addDependency(dep); + } + deps.push(dep); } - ); - parser.hooks.exportExpression.tap( - "HarmonyExportDependencyParserPlugin", - (statement, expr) => { - const isFunctionDeclaration = expr.type === "FunctionDeclaration"; - const comments = parser.getComments([ - statement.range[0], - expr.range[0] + const dep = this.newRequireArrayDependency(deps, param.range); + dep.loc = expr.loc; + dep.optional = !!parser.scope.inTry; + parser.state.module.addPresentationalDependency(dep); + return true; + } + } + processItem(parser, expr, param) { + if (param.isConditional()) { + for (const p of param.options) { + const result = this.processItem(parser, expr, p); + if (result === undefined) { + this.processContext(parser, expr, p); + } + } + return true; + } else if (param.isString()) { + let dep, localModule; + if (param.string === "require") { + dep = new ConstDependency("__webpack_require__", param.string, [ + RuntimeGlobals.require ]); - const dep = new HarmonyExportExpressionDependency( - expr.range, - statement.range, - comments - .map(c => { - switch (c.type) { - case "Block": - return `/*${c.value}*/`; - case "Line": - return `//${c.value}\n`; - } - return ""; - }) - .join(""), - expr.type.endsWith("Declaration") && expr.id - ? expr.id.name - : isFunctionDeclaration - ? { - id: expr.id ? expr.id.name : undefined, - range: [ - expr.range[0], - expr.params.length > 0 - ? expr.params[0].range[0] - : expr.body.range[0] - ], - prefix: `${expr.async ? "async " : ""}function${ - expr.generator ? "*" : "" - } `, - suffix: `(${expr.params.length > 0 ? "" : ") "}` - } - : undefined - ); - dep.loc = Object.create(statement.loc); - dep.loc.index = -1; - parser.state.current.addDependency(dep); - InnerGraph.addVariableUsage( - parser, - expr.type.endsWith("Declaration") && expr.id - ? expr.id.name - : "*default*", - "default" + } else if (param.string === "module") { + dep = new ConstDependency( + parser.state.module.buildInfo.moduleArgument, + param.range, + [RuntimeGlobals.module] ); - return true; - } - ); - parser.hooks.exportSpecifier.tap( - "HarmonyExportDependencyParserPlugin", - (statement, id, name, idx) => { - const settings = parser.getTagData(id, harmonySpecifierTag); - let dep; - const harmonyNamedExports = (parser.state.harmonyNamedExports = - parser.state.harmonyNamedExports || new Set()); - harmonyNamedExports.add(name); - InnerGraph.addVariableUsage(parser, id, name); - if (settings) { - dep = new HarmonyExportImportedSpecifierDependency( - settings.source, - settings.sourceOrder, - settings.ids, - name, - harmonyNamedExports, - null, - exportPresenceMode, - null, - settings.assertions - ); - } else { - dep = new HarmonyExportSpecifierDependency(id, name); - } - dep.loc = Object.create(statement.loc); - dep.loc.index = idx; + } else if (param.string === "exports") { + dep = new ConstDependency( + parser.state.module.buildInfo.exportsArgument, + param.range, + [RuntimeGlobals.exports] + ); + } else if ((localModule = getLocalModule(parser.state, param.string))) { + localModule.flagUsed(); + dep = new LocalModuleDependency(localModule, param.range, false); + } else { + dep = this.newRequireItemDependency(param.string, param.range); + dep.loc = expr.loc; + dep.optional = !!parser.scope.inTry; parser.state.current.addDependency(dep); return true; } + dep.loc = expr.loc; + parser.state.module.addPresentationalDependency(dep); + return true; + } + } + processContext(parser, expr, param) { + const dep = ContextDependencyHelpers.create( + AMDRequireContextDependency, + param.range, + param, + expr, + this.options, + { + category: "amd" + }, + parser ); - parser.hooks.exportImportSpecifier.tap( - "HarmonyExportDependencyParserPlugin", - (statement, source, id, name, idx) => { - const harmonyNamedExports = (parser.state.harmonyNamedExports = - parser.state.harmonyNamedExports || new Set()); - let harmonyStarExports = null; - if (name) { - harmonyNamedExports.add(name); - } else { - harmonyStarExports = parser.state.harmonyStarExports = - parser.state.harmonyStarExports || new HarmonyStarExportsList(); + if (!dep) return; + dep.loc = expr.loc; + dep.optional = !!parser.scope.inTry; + parser.state.current.addDependency(dep); + return true; + } + + processArrayForRequestString(param) { + if (param.isArray()) { + const result = param.items.map(item => + this.processItemForRequestString(item) + ); + if (result.every(Boolean)) return result.join(" "); + } else if (param.isConstArray()) { + return param.array.join(" "); + } + } + + processItemForRequestString(param) { + if (param.isConditional()) { + const result = param.options.map(item => + this.processItemForRequestString(item) + ); + if (result.every(Boolean)) return result.join("|"); + } else if (param.isString()) { + return param.string; + } + } + + processCallRequire(parser, expr) { + let param; + let depBlock; + let dep; + let result; + + const old = parser.state.current; + + if (expr.arguments.length >= 1) { + param = parser.evaluateExpression(expr.arguments[0]); + depBlock = this.newRequireDependenciesBlock( + expr.loc, + this.processArrayForRequestString(param) + ); + dep = this.newRequireDependency( + expr.range, + param.range, + expr.arguments.length > 1 ? expr.arguments[1].range : null, + expr.arguments.length > 2 ? expr.arguments[2].range : null + ); + dep.loc = expr.loc; + depBlock.addDependency(dep); + + parser.state.current = depBlock; + } + + if (expr.arguments.length === 1) { + parser.inScope([], () => { + result = this.processArray(parser, expr, param); + }); + parser.state.current = old; + if (!result) return; + parser.state.current.addBlock(depBlock); + return true; + } + + if (expr.arguments.length === 2 || expr.arguments.length === 3) { + try { + parser.inScope([], () => { + result = this.processArray(parser, expr, param); + }); + if (!result) { + const dep = new UnsupportedDependency("unsupported", expr.range); + old.addPresentationalDependency(dep); + if (parser.state.module) { + parser.state.module.addError( + new UnsupportedFeatureWarning( + "Cannot statically analyse 'require(…, …)' in line " + + expr.loc.start.line, + expr.loc + ) + ); + } + depBlock = null; + return true; } - const dep = new HarmonyExportImportedSpecifierDependency( - source, - parser.state.lastHarmonyImportOrder, - id ? [id] : [], - name, - harmonyNamedExports, - harmonyStarExports && harmonyStarExports.slice(), - exportPresenceMode, - harmonyStarExports + dep.functionBindThis = this.processFunctionArgument( + parser, + expr.arguments[1] ); - if (harmonyStarExports) { - harmonyStarExports.push(dep); + if (expr.arguments.length === 3) { + dep.errorCallbackBindThis = this.processFunctionArgument( + parser, + expr.arguments[2] + ); } - dep.loc = Object.create(statement.loc); - dep.loc.index = idx; - parser.state.current.addDependency(dep); - return true; + } finally { + parser.state.current = old; + if (depBlock) parser.state.current.addBlock(depBlock); } + return true; + } + } + + newRequireDependenciesBlock(loc, request) { + return new AMDRequireDependenciesBlock(loc, request); + } + newRequireDependency( + outerRange, + arrayRange, + functionRange, + errorCallbackRange + ) { + return new AMDRequireDependency( + outerRange, + arrayRange, + functionRange, + errorCallbackRange ); } -}; + newRequireItemDependency(request, range) { + return new AMDRequireItemDependency(request, range); + } + newRequireArrayDependency(depsArray, range) { + return new AMDRequireArrayDependency(depsArray, range); + } +} +module.exports = AMDRequireDependenciesBlockParserPlugin; /***/ }), -/***/ 22705: +/***/ 11311: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; @@ -78608,80 +76272,64 @@ module.exports = class HarmonyExportDependencyParserPlugin { -const ConcatenationScope = __webpack_require__(14067); const RuntimeGlobals = __webpack_require__(49404); const makeSerializable = __webpack_require__(26522); -const HarmonyExportInitFragment = __webpack_require__(68664); const NullDependency = __webpack_require__(65845); /** @typedef {import("webpack-sources").ReplaceSource} ReplaceSource */ +/** @typedef {import("../AsyncDependenciesBlock")} AsyncDependenciesBlock */ /** @typedef {import("../Dependency")} Dependency */ -/** @typedef {import("../Dependency").ExportsSpec} ExportsSpec */ /** @typedef {import("../DependencyTemplate").DependencyTemplateContext} DependencyTemplateContext */ -/** @typedef {import("../ModuleGraph")} ModuleGraph */ -/** @typedef {import("../ModuleGraphConnection").ConnectionState} ConnectionState */ -class HarmonyExportExpressionDependency extends NullDependency { - constructor(range, rangeStatement, prefix, declarationId) { +class AMDRequireDependency extends NullDependency { + constructor(outerRange, arrayRange, functionRange, errorCallbackRange) { super(); - this.range = range; - this.rangeStatement = rangeStatement; - this.prefix = prefix; - this.declarationId = declarationId; - } - - get type() { - return "harmony export expression"; - } - /** - * Returns the exported names - * @param {ModuleGraph} moduleGraph module graph - * @returns {ExportsSpec | undefined} export names - */ - getExports(moduleGraph) { - return { - exports: ["default"], - priority: 1, - terminalBinding: true, - dependencies: undefined - }; + this.outerRange = outerRange; + this.arrayRange = arrayRange; + this.functionRange = functionRange; + this.errorCallbackRange = errorCallbackRange; + this.functionBindThis = false; + this.errorCallbackBindThis = false; } - /** - * @param {ModuleGraph} moduleGraph the module graph - * @returns {ConnectionState} how this dependency connects the module to referencing modules - */ - getModuleEvaluationSideEffectsState(moduleGraph) { - // The expression/declaration is already covered by SideEffectsFlagPlugin - return false; + get category() { + return "amd"; } serialize(context) { const { write } = context; - write(this.range); - write(this.rangeStatement); - write(this.prefix); - write(this.declarationId); + + write(this.outerRange); + write(this.arrayRange); + write(this.functionRange); + write(this.errorCallbackRange); + write(this.functionBindThis); + write(this.errorCallbackBindThis); + super.serialize(context); } deserialize(context) { const { read } = context; - this.range = read(); - this.rangeStatement = read(); - this.prefix = read(); - this.declarationId = read(); + + this.outerRange = read(); + this.arrayRange = read(); + this.functionRange = read(); + this.errorCallbackRange = read(); + this.functionBindThis = read(); + this.errorCallbackBindThis = read(); + super.deserialize(context); } } makeSerializable( - HarmonyExportExpressionDependency, - "webpack/lib/dependencies/HarmonyExportExpressionDependency" + AMDRequireDependency, + "webpack/lib/dependencies/AMDRequireDependency" ); -HarmonyExportExpressionDependency.Template = class HarmonyExportDependencyTemplate extends ( +AMDRequireDependency.Template = class AMDRequireDependencyTemplate extends ( NullDependency.Template ) { /** @@ -78693,159 +76341,283 @@ HarmonyExportExpressionDependency.Template = class HarmonyExportDependencyTempla apply( dependency, source, - { - module, - moduleGraph, - runtimeTemplate, - runtimeRequirements, - initFragments, - runtime, - concatenationScope - } + { runtimeTemplate, moduleGraph, chunkGraph, runtimeRequirements } ) { - const dep = /** @type {HarmonyExportExpressionDependency} */ (dependency); - const { declarationId } = dep; - const exportsName = module.exportsArgument; - if (declarationId) { - let name; - if (typeof declarationId === "string") { - name = declarationId; - } else { - name = ConcatenationScope.DEFAULT_EXPORT; - source.replace( - declarationId.range[0], - declarationId.range[1] - 1, - `${declarationId.prefix}${name}${declarationId.suffix}` - ); - } + const dep = /** @type {AMDRequireDependency} */ (dependency); + const depBlock = /** @type {AsyncDependenciesBlock} */ ( + moduleGraph.getParentBlock(dep) + ); + const promise = runtimeTemplate.blockPromise({ + chunkGraph, + block: depBlock, + message: "AMD require", + runtimeRequirements + }); - if (concatenationScope) { - concatenationScope.registerExport("default", name); - } else { - const used = moduleGraph - .getExportsInfo(module) - .getUsedName("default", runtime); - if (used) { - const map = new Map(); - map.set(used, `/* export default binding */ ${name}`); - initFragments.push(new HarmonyExportInitFragment(exportsName, map)); - } - } + // has array range but no function range + if (dep.arrayRange && !dep.functionRange) { + const startBlock = `${promise}.then(function() {`; + const endBlock = `;})['catch'](${RuntimeGlobals.uncaughtErrorHandler})`; + runtimeRequirements.add(RuntimeGlobals.uncaughtErrorHandler); + + source.replace(dep.outerRange[0], dep.arrayRange[0] - 1, startBlock); + + source.replace(dep.arrayRange[1], dep.outerRange[1] - 1, endBlock); + + return; + } + + // has function range but no array range + if (dep.functionRange && !dep.arrayRange) { + const startBlock = `${promise}.then((`; + const endBlock = `).bind(exports, __webpack_require__, exports, module))['catch'](${RuntimeGlobals.uncaughtErrorHandler})`; + runtimeRequirements.add(RuntimeGlobals.uncaughtErrorHandler); + + source.replace(dep.outerRange[0], dep.functionRange[0] - 1, startBlock); + + source.replace(dep.functionRange[1], dep.outerRange[1] - 1, endBlock); + + return; + } + + // has array range, function range, and errorCallbackRange + if (dep.arrayRange && dep.functionRange && dep.errorCallbackRange) { + const startBlock = `${promise}.then(function() { `; + const errorRangeBlock = `}${ + dep.functionBindThis ? ".bind(this)" : "" + })['catch'](`; + const endBlock = `${dep.errorCallbackBindThis ? ".bind(this)" : ""})`; + + source.replace(dep.outerRange[0], dep.arrayRange[0] - 1, startBlock); + + source.insert(dep.arrayRange[0], "var __WEBPACK_AMD_REQUIRE_ARRAY__ = "); + + source.replace(dep.arrayRange[1], dep.functionRange[0] - 1, "; ("); + + source.insert( + dep.functionRange[1], + ").apply(null, __WEBPACK_AMD_REQUIRE_ARRAY__);" + ); source.replace( - dep.rangeStatement[0], - dep.range[0] - 1, - `/* harmony default export */ ${dep.prefix}` + dep.functionRange[1], + dep.errorCallbackRange[0] - 1, + errorRangeBlock ); - } else { - let content; - const name = ConcatenationScope.DEFAULT_EXPORT; - if (runtimeTemplate.supportsConst()) { - content = `/* harmony default export */ const ${name} = `; - if (concatenationScope) { - concatenationScope.registerExport("default", name); - } else { - const used = moduleGraph - .getExportsInfo(module) - .getUsedName("default", runtime); - if (used) { - runtimeRequirements.add(RuntimeGlobals.exports); - const map = new Map(); - map.set(used, name); - initFragments.push(new HarmonyExportInitFragment(exportsName, map)); - } else { - content = `/* unused harmony default export */ var ${name} = `; - } - } - } else if (concatenationScope) { - content = `/* harmony default export */ var ${name} = `; - concatenationScope.registerExport("default", name); - } else { - const used = moduleGraph - .getExportsInfo(module) - .getUsedName("default", runtime); - if (used) { - runtimeRequirements.add(RuntimeGlobals.exports); - // This is a little bit incorrect as TDZ is not correct, but we can't use const. - content = `/* harmony default export */ ${exportsName}[${JSON.stringify( - used - )}] = `; - } else { - content = `/* unused harmony default export */ var ${name} = `; - } - } - if (dep.range) { - source.replace( - dep.rangeStatement[0], - dep.range[0] - 1, - content + "(" + dep.prefix - ); - source.replace(dep.range[1], dep.rangeStatement[1] - 0.5, ");"); - return; - } + source.replace( + dep.errorCallbackRange[1], + dep.outerRange[1] - 1, + endBlock + ); + + return; + } + + // has array range, function range, but no errorCallbackRange + if (dep.arrayRange && dep.functionRange) { + const startBlock = `${promise}.then(function() { `; + const endBlock = `}${ + dep.functionBindThis ? ".bind(this)" : "" + })['catch'](${RuntimeGlobals.uncaughtErrorHandler})`; + runtimeRequirements.add(RuntimeGlobals.uncaughtErrorHandler); + + source.replace(dep.outerRange[0], dep.arrayRange[0] - 1, startBlock); + + source.insert(dep.arrayRange[0], "var __WEBPACK_AMD_REQUIRE_ARRAY__ = "); + + source.replace(dep.arrayRange[1], dep.functionRange[0] - 1, "; ("); + + source.insert( + dep.functionRange[1], + ").apply(null, __WEBPACK_AMD_REQUIRE_ARRAY__);" + ); + + source.replace(dep.functionRange[1], dep.outerRange[1] - 1, endBlock); + } + } +}; + +module.exports = AMDRequireDependency; + + +/***/ }), + +/***/ 90377: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ + + + +const makeSerializable = __webpack_require__(26522); +const ModuleDependency = __webpack_require__(80944); +const ModuleDependencyTemplateAsRequireId = __webpack_require__(77802); + +class AMDRequireItemDependency extends ModuleDependency { + constructor(request, range) { + super(request); + + this.range = range; + } + + get type() { + return "amd require"; + } + + get category() { + return "amd"; + } +} + +makeSerializable( + AMDRequireItemDependency, + "webpack/lib/dependencies/AMDRequireItemDependency" +); + +AMDRequireItemDependency.Template = ModuleDependencyTemplateAsRequireId; + +module.exports = AMDRequireItemDependency; + + +/***/ }), + +/***/ 35469: +/***/ (function(__unused_webpack_module, exports, __webpack_require__) { + +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php +*/ + + + +const RuntimeGlobals = __webpack_require__(49404); +const RuntimeModule = __webpack_require__(61439); +const Template = __webpack_require__(92066); + +class AMDDefineRuntimeModule extends RuntimeModule { + constructor() { + super("amd define"); + } + + /** + * @returns {string} runtime code + */ + generate() { + return Template.asString([ + `${RuntimeGlobals.amdDefine} = function () {`, + Template.indent("throw new Error('define cannot be used indirect');"), + "};" + ]); + } +} + +class AMDOptionsRuntimeModule extends RuntimeModule { + /** + * @param {Record} options the AMD options + */ + constructor(options) { + super("amd options"); + this.options = options; + } - source.replace(dep.rangeStatement[0], dep.rangeStatement[1] - 1, content); - } + /** + * @returns {string} runtime code + */ + generate() { + return Template.asString([ + `${RuntimeGlobals.amdOptions} = ${JSON.stringify(this.options)};` + ]); } -}; +} -module.exports = HarmonyExportExpressionDependency; +exports.AMDDefineRuntimeModule = AMDDefineRuntimeModule; +exports.AMDOptionsRuntimeModule = AMDOptionsRuntimeModule; /***/ }), -/***/ 67159: +/***/ 64177: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; /* MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra + Author Florent Cailhol @ooflorent */ +const DependencyTemplate = __webpack_require__(17600); +const InitFragment = __webpack_require__(51739); const makeSerializable = __webpack_require__(26522); const NullDependency = __webpack_require__(65845); /** @typedef {import("webpack-sources").ReplaceSource} ReplaceSource */ +/** @typedef {import("../ChunkGraph")} ChunkGraph */ /** @typedef {import("../Dependency")} Dependency */ +/** @typedef {import("../Dependency").UpdateHashContext} UpdateHashContext */ /** @typedef {import("../DependencyTemplate").DependencyTemplateContext} DependencyTemplateContext */ +/** @typedef {import("../DependencyTemplates")} DependencyTemplates */ +/** @typedef {import("../ModuleGraph")} ModuleGraph */ +/** @typedef {import("../RuntimeTemplate")} RuntimeTemplate */ +/** @typedef {import("../util/Hash")} Hash */ -class HarmonyExportHeaderDependency extends NullDependency { - constructor(range, rangeStatement) { +class CachedConstDependency extends NullDependency { + constructor(expression, range, identifier) { super(); + + this.expression = expression; this.range = range; - this.rangeStatement = rangeStatement; + this.identifier = identifier; + this._hashUpdate = undefined; } - get type() { - return "harmony export header"; + /** + * Update the hash + * @param {Hash} hash hash to be updated + * @param {UpdateHashContext} context context + * @returns {void} + */ + updateHash(hash, context) { + if (this._hashUpdate === undefined) + this._hashUpdate = "" + this.identifier + this.range + this.expression; + hash.update(this._hashUpdate); } serialize(context) { const { write } = context; + + write(this.expression); write(this.range); - write(this.rangeStatement); + write(this.identifier); + super.serialize(context); } deserialize(context) { const { read } = context; + + this.expression = read(); this.range = read(); - this.rangeStatement = read(); + this.identifier = read(); + super.deserialize(context); } } makeSerializable( - HarmonyExportHeaderDependency, - "webpack/lib/dependencies/HarmonyExportHeaderDependency" + CachedConstDependency, + "webpack/lib/dependencies/CachedConstDependency" ); -HarmonyExportHeaderDependency.Template = class HarmonyExportDependencyTemplate extends ( - NullDependency.Template +CachedConstDependency.Template = class CachedConstDependencyTemplate extends ( + DependencyTemplate ) { /** * @param {Dependency} dependency the dependency for which the template should be applied @@ -78853,22 +76625,95 @@ HarmonyExportHeaderDependency.Template = class HarmonyExportDependencyTemplate e * @param {DependencyTemplateContext} templateContext the context object * @returns {void} */ - apply(dependency, source, templateContext) { - const dep = /** @type {HarmonyExportHeaderDependency} */ (dependency); - const content = ""; - const replaceUntil = dep.range - ? dep.range[0] - 1 - : dep.rangeStatement[1] - 1; - source.replace(dep.rangeStatement[0], replaceUntil, content); + apply( + dependency, + source, + { runtimeTemplate, dependencyTemplates, initFragments } + ) { + const dep = /** @type {CachedConstDependency} */ (dependency); + + initFragments.push( + new InitFragment( + `var ${dep.identifier} = ${dep.expression};\n`, + InitFragment.STAGE_CONSTANTS, + 0, + `const ${dep.identifier}` + ) + ); + + if (typeof dep.range === "number") { + source.insert(dep.range, dep.identifier); + + return; + } + + source.replace(dep.range[0], dep.range[1] - 1, dep.identifier); } }; -module.exports = HarmonyExportHeaderDependency; +module.exports = CachedConstDependency; /***/ }), -/***/ 77952: +/***/ 95217: +/***/ (function(__unused_webpack_module, exports, __webpack_require__) { + +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ + + + +const RuntimeGlobals = __webpack_require__(49404); + +exports.handleDependencyBase = (depBase, module, runtimeRequirements) => { + let base = undefined; + let type; + switch (depBase) { + case "exports": + runtimeRequirements.add(RuntimeGlobals.exports); + base = module.exportsArgument; + type = "expression"; + break; + case "module.exports": + runtimeRequirements.add(RuntimeGlobals.module); + base = `${module.moduleArgument}.exports`; + type = "expression"; + break; + case "this": + runtimeRequirements.add(RuntimeGlobals.thisAsExports); + base = "this"; + type = "expression"; + break; + case "Object.defineProperty(exports)": + runtimeRequirements.add(RuntimeGlobals.exports); + base = module.exportsArgument; + type = "Object.defineProperty"; + break; + case "Object.defineProperty(module.exports)": + runtimeRequirements.add(RuntimeGlobals.module); + base = `${module.moduleArgument}.exports`; + type = "Object.defineProperty"; + break; + case "Object.defineProperty(this)": + runtimeRequirements.add(RuntimeGlobals.thisAsExports); + base = "this"; + type = "Object.defineProperty"; + break; + default: + throw new Error(`Unsupported base ${depBase}`); + } + + return [type, base]; +}; + + +/***/ }), + +/***/ 76922: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; @@ -78881,375 +76726,48 @@ module.exports = HarmonyExportHeaderDependency; const Dependency = __webpack_require__(50384); const { UsageState } = __webpack_require__(4295); -const HarmonyLinkingError = __webpack_require__(42766); -const InitFragment = __webpack_require__(51739); -const RuntimeGlobals = __webpack_require__(49404); const Template = __webpack_require__(92066); -const { countIterable } = __webpack_require__(31065); -const { first, combine } = __webpack_require__(34715); +const { equals } = __webpack_require__(21537); const makeSerializable = __webpack_require__(26522); const propertyAccess = __webpack_require__(86709); -const { getRuntimeKey, keyToRuntime } = __webpack_require__(19655); -const HarmonyExportInitFragment = __webpack_require__(68664); -const HarmonyImportDependency = __webpack_require__(19577); +const { handleDependencyBase } = __webpack_require__(95217); +const ModuleDependency = __webpack_require__(80944); const processExportInfo = __webpack_require__(35873); /** @typedef {import("webpack-sources").ReplaceSource} ReplaceSource */ -/** @typedef {import("../ChunkGraph")} ChunkGraph */ /** @typedef {import("../Dependency").ExportsSpec} ExportsSpec */ /** @typedef {import("../Dependency").ReferencedExport} ReferencedExport */ /** @typedef {import("../Dependency").TRANSITIVE} TRANSITIVE */ -/** @typedef {import("../Dependency").UpdateHashContext} UpdateHashContext */ /** @typedef {import("../DependencyTemplate").DependencyTemplateContext} DependencyTemplateContext */ -/** @typedef {import("../ExportsInfo")} ExportsInfo */ -/** @typedef {import("../ExportsInfo").ExportInfo} ExportInfo */ /** @typedef {import("../Module")} Module */ /** @typedef {import("../ModuleGraph")} ModuleGraph */ -/** @typedef {import("../ModuleGraphConnection")} ModuleGraphConnection */ -/** @typedef {import("../ModuleGraphConnection").ConnectionState} ConnectionState */ -/** @typedef {import("../RuntimeTemplate")} RuntimeTemplate */ -/** @typedef {import("../WebpackError")} WebpackError */ -/** @typedef {import("../util/Hash")} Hash */ /** @typedef {import("../util/runtime").RuntimeSpec} RuntimeSpec */ -/** @typedef {"missing"|"unused"|"empty-star"|"reexport-dynamic-default"|"reexport-named-default"|"reexport-namespace-object"|"reexport-fake-namespace-object"|"reexport-undefined"|"normal-reexport"|"dynamic-reexport"} ExportModeType */ - -const { ExportPresenceModes } = HarmonyImportDependency; - -const idsSymbol = Symbol("HarmonyExportImportedSpecifierDependency.ids"); - -class NormalReexportItem { - /** - * @param {string} name export name - * @param {string[]} ids reexported ids from other module - * @param {ExportInfo} exportInfo export info from other module - * @param {boolean} checked true, if it should be checked at runtime if this export exists - * @param {boolean} hidden true, if it is hidden behind another active export in the same module - */ - constructor(name, ids, exportInfo, checked, hidden) { - this.name = name; - this.ids = ids; - this.exportInfo = exportInfo; - this.checked = checked; - this.hidden = hidden; - } -} - -class ExportMode { - /** - * @param {ExportModeType} type type of the mode - */ - constructor(type) { - /** @type {ExportModeType} */ - this.type = type; - - // for "normal-reexport": - /** @type {NormalReexportItem[] | null} */ - this.items = null; - - // for "reexport-named-default" | "reexport-fake-namespace-object" | "reexport-namespace-object" - /** @type {string|null} */ - this.name = null; - /** @type {ExportInfo | null} */ - this.partialNamespaceExportInfo = null; - - // for "dynamic-reexport": - /** @type {Set | null} */ - this.ignored = null; - - // for "dynamic-reexport" | "empty-star": - /** @type {Set | null} */ - this.hidden = null; - - // for "missing": - /** @type {string | null} */ - this.userRequest = null; - - // for "reexport-fake-namespace-object": - /** @type {number} */ - this.fakeType = 0; - } -} - -const determineExportAssignments = ( - moduleGraph, - dependencies, - additionalDependency -) => { - const names = new Set(); - const dependencyIndices = []; - - if (additionalDependency) { - dependencies = dependencies.concat(additionalDependency); - } - - for (const dep of dependencies) { - const i = dependencyIndices.length; - dependencyIndices[i] = names.size; - const otherImportedModule = moduleGraph.getModule(dep); - if (otherImportedModule) { - const exportsInfo = moduleGraph.getExportsInfo(otherImportedModule); - for (const exportInfo of exportsInfo.exports) { - if ( - exportInfo.provided === true && - exportInfo.name !== "default" && - !names.has(exportInfo.name) - ) { - names.add(exportInfo.name); - dependencyIndices[i] = names.size; - } - } - } - } - dependencyIndices.push(names.size); - - return { names: Array.from(names), dependencyIndices }; -}; - -const findDependencyForName = ( - { names, dependencyIndices }, - name, - dependencies -) => { - const dependenciesIt = dependencies[Symbol.iterator](); - const dependencyIndicesIt = dependencyIndices[Symbol.iterator](); - let dependenciesItResult = dependenciesIt.next(); - let dependencyIndicesItResult = dependencyIndicesIt.next(); - if (dependencyIndicesItResult.done) return; - for (let i = 0; i < names.length; i++) { - while (i >= dependencyIndicesItResult.value) { - dependenciesItResult = dependenciesIt.next(); - dependencyIndicesItResult = dependencyIndicesIt.next(); - if (dependencyIndicesItResult.done) return; - } - if (names[i] === name) return dependenciesItResult.value; - } - return undefined; -}; - -/** - * @param {ModuleGraph} moduleGraph the module graph - * @param {HarmonyExportImportedSpecifierDependency} dep the dependency - * @param {string} runtimeKey the runtime key - * @returns {ExportMode} the export mode - */ -const getMode = (moduleGraph, dep, runtimeKey) => { - const importedModule = moduleGraph.getModule(dep); - - if (!importedModule) { - const mode = new ExportMode("missing"); - - mode.userRequest = dep.userRequest; - - return mode; - } - - const name = dep.name; - const runtime = keyToRuntime(runtimeKey); - const parentModule = moduleGraph.getParentModule(dep); - const exportsInfo = moduleGraph.getExportsInfo(parentModule); - - if ( - name - ? exportsInfo.getUsed(name, runtime) === UsageState.Unused - : exportsInfo.isUsed(runtime) === false - ) { - const mode = new ExportMode("unused"); - - mode.name = name || "*"; - - return mode; - } - - const importedExportsType = importedModule.getExportsType( - moduleGraph, - parentModule.buildMeta.strictHarmonyModule - ); - - const ids = dep.getIds(moduleGraph); - - // Special handling for reexporting the default export - // from non-namespace modules - if (name && ids.length > 0 && ids[0] === "default") { - switch (importedExportsType) { - case "dynamic": { - const mode = new ExportMode("reexport-dynamic-default"); - - mode.name = name; - - return mode; - } - case "default-only": - case "default-with-named": { - const exportInfo = exportsInfo.getReadOnlyExportInfo(name); - const mode = new ExportMode("reexport-named-default"); - - mode.name = name; - mode.partialNamespaceExportInfo = exportInfo; - - return mode; - } - } - } - - // reexporting with a fixed name - if (name) { - let mode; - const exportInfo = exportsInfo.getReadOnlyExportInfo(name); - - if (ids.length > 0) { - // export { name as name } - switch (importedExportsType) { - case "default-only": - mode = new ExportMode("reexport-undefined"); - mode.name = name; - break; - default: - mode = new ExportMode("normal-reexport"); - mode.items = [ - new NormalReexportItem(name, ids, exportInfo, false, false) - ]; - break; - } - } else { - // export * as name - switch (importedExportsType) { - case "default-only": - mode = new ExportMode("reexport-fake-namespace-object"); - mode.name = name; - mode.partialNamespaceExportInfo = exportInfo; - mode.fakeType = 0; - break; - case "default-with-named": - mode = new ExportMode("reexport-fake-namespace-object"); - mode.name = name; - mode.partialNamespaceExportInfo = exportInfo; - mode.fakeType = 2; - break; - case "dynamic": - default: - mode = new ExportMode("reexport-namespace-object"); - mode.name = name; - mode.partialNamespaceExportInfo = exportInfo; - } - } - - return mode; - } - - // Star reexporting - - const { ignoredExports, exports, checked, hidden } = dep.getStarReexports( - moduleGraph, - runtime, - exportsInfo, - importedModule - ); - if (!exports) { - // We have too few info about the modules - // Delegate the logic to the runtime code - - const mode = new ExportMode("dynamic-reexport"); - mode.ignored = ignoredExports; - mode.hidden = hidden; - - return mode; - } - - if (exports.size === 0) { - const mode = new ExportMode("empty-star"); - mode.hidden = hidden; - - return mode; - } - - const mode = new ExportMode("normal-reexport"); - - mode.items = Array.from( - exports, - exportName => - new NormalReexportItem( - exportName, - [exportName], - exportsInfo.getReadOnlyExportInfo(exportName), - checked.has(exportName), - false - ) - ); - if (hidden !== undefined) { - for (const exportName of hidden) { - mode.items.push( - new NormalReexportItem( - exportName, - [exportName], - exportsInfo.getReadOnlyExportInfo(exportName), - false, - true - ) - ); - } - } - - return mode; -}; - -class HarmonyExportImportedSpecifierDependency extends HarmonyImportDependency { - /** - * @param {string} request the request string - * @param {number} sourceOrder the order in the original source file - * @param {string[]} ids the requested export name of the imported module - * @param {string | null} name the export name of for this module - * @param {Set} activeExports other named exports in the module - * @param {ReadonlyArray | Iterable} otherStarExports other star exports in the module before this import - * @param {number} exportPresenceMode mode of checking export names - * @param {HarmonyStarExportsList} allStarExports all star exports in the module - * @param {Record=} assertions import assertions - */ - constructor( - request, - sourceOrder, - ids, - name, - activeExports, - otherStarExports, - exportPresenceMode, - allStarExports, - assertions - ) { - super(request, sourceOrder, assertions); - - this.ids = ids; - this.name = name; - this.activeExports = activeExports; - this.otherStarExports = otherStarExports; - this.exportPresenceMode = exportPresenceMode; - this.allStarExports = allStarExports; - } - - /** - * @returns {boolean | TRANSITIVE} true, when changes to the referenced module could affect the referencing module; TRANSITIVE, when changes to the referenced module could affect referencing modules of the referencing module - */ - couldAffectReferencingModule() { - return Dependency.TRANSITIVE; - } +const idsSymbol = Symbol("CommonJsExportRequireDependency.ids"); - // TODO webpack 6 remove - get id() { - throw new Error("id was renamed to ids and type changed to string[]"); - } +const EMPTY_OBJECT = {}; - // TODO webpack 6 remove - getId() { - throw new Error("id was renamed to ids and type changed to string[]"); +class CommonJsExportRequireDependency extends ModuleDependency { + constructor(range, valueRange, base, names, request, ids, resultUsed) { + super(request); + this.range = range; + this.valueRange = valueRange; + this.base = base; + this.names = names; + this.ids = ids; + this.resultUsed = resultUsed; + this.asiSafe = undefined; } - // TODO webpack 6 remove - setId() { - throw new Error("id was renamed to ids and type changed to string[]"); + get type() { + return "cjs export require"; } - get type() { - return "harmony export imported specifier"; + /** + * @returns {boolean | TRANSITIVE} true, when changes to the referenced module could affect the referencing module; TRANSITIVE, when changes to the referenced module could affect referencing modules of the referencing module + */ + couldAffectReferencingModule() { + return Dependency.TRANSITIVE; } /** @@ -79270,504 +76788,398 @@ class HarmonyExportImportedSpecifierDependency extends HarmonyImportDependency { } /** - * @param {ModuleGraph} moduleGraph the module graph - * @param {RuntimeSpec} runtime the runtime - * @returns {ExportMode} the export mode + * Returns list of exports referenced by this dependency + * @param {ModuleGraph} moduleGraph module graph + * @param {RuntimeSpec} runtime the runtime for which the module is analysed + * @returns {(string[] | ReferencedExport)[]} referenced exports */ - getMode(moduleGraph, runtime) { - return moduleGraph.dependencyCacheProvide( - this, - getRuntimeKey(runtime), - getMode + getReferencedExports(moduleGraph, runtime) { + const ids = this.getIds(moduleGraph); + const getFullResult = () => { + if (ids.length === 0) { + return Dependency.EXPORTS_OBJECT_REFERENCED; + } else { + return [ + { + name: ids, + canMangle: false + } + ]; + } + }; + if (this.resultUsed) return getFullResult(); + let exportsInfo = moduleGraph.getExportsInfo( + moduleGraph.getParentModule(this) ); + for (const name of this.names) { + const exportInfo = exportsInfo.getReadOnlyExportInfo(name); + const used = exportInfo.getUsed(runtime); + if (used === UsageState.Unused) return Dependency.NO_EXPORTS_REFERENCED; + if (used !== UsageState.OnlyPropertiesUsed) return getFullResult(); + exportsInfo = exportInfo.exportsInfo; + if (!exportsInfo) return getFullResult(); + } + if (exportsInfo.otherExportsInfo.getUsed(runtime) !== UsageState.Unused) { + return getFullResult(); + } + /** @type {string[][]} */ + const referencedExports = []; + for (const exportInfo of exportsInfo.orderedExports) { + processExportInfo( + runtime, + referencedExports, + ids.concat(exportInfo.name), + exportInfo, + false + ); + } + return referencedExports.map(name => ({ + name, + canMangle: false + })); + } + + /** + * Returns the exported names + * @param {ModuleGraph} moduleGraph module graph + * @returns {ExportsSpec | undefined} export names + */ + getExports(moduleGraph) { + const ids = this.getIds(moduleGraph); + if (this.names.length === 1) { + const name = this.names[0]; + const from = moduleGraph.getConnection(this); + if (!from) return; + return { + exports: [ + { + name, + from, + export: ids.length === 0 ? null : ids, + // we can't mangle names that are in an empty object + // because one could access the prototype property + // when export isn't set yet + canMangle: !(name in EMPTY_OBJECT) && false + } + ], + dependencies: [from.module] + }; + } else if (this.names.length > 0) { + const name = this.names[0]; + return { + exports: [ + { + name, + // we can't mangle names that are in an empty object + // because one could access the prototype property + // when export isn't set yet + canMangle: !(name in EMPTY_OBJECT) && false + } + ], + dependencies: undefined + }; + } else { + const from = moduleGraph.getConnection(this); + if (!from) return; + const reexportInfo = this.getStarReexports( + moduleGraph, + undefined, + from.module + ); + if (reexportInfo) { + return { + exports: Array.from(reexportInfo.exports, name => { + return { + name, + from, + export: ids.concat(name), + canMangle: !(name in EMPTY_OBJECT) && false + }; + }), + // TODO handle deep reexports + dependencies: [from.module] + }; + } else { + return { + exports: true, + from: ids.length === 0 ? from : undefined, + canMangle: false, + dependencies: [from.module] + }; + } + } } /** * @param {ModuleGraph} moduleGraph the module graph * @param {RuntimeSpec} runtime the runtime - * @param {ExportsInfo} exportsInfo exports info about the current module (optional) * @param {Module} importedModule the imported module (optional) - * @returns {{exports?: Set, checked?: Set, ignoredExports: Set, hidden?: Set}} information + * @returns {{exports?: Set, checked?: Set}} information */ getStarReexports( moduleGraph, runtime, - exportsInfo = moduleGraph.getExportsInfo(moduleGraph.getParentModule(this)), importedModule = moduleGraph.getModule(this) ) { - const importedExportsInfo = moduleGraph.getExportsInfo(importedModule); + let importedExportsInfo = moduleGraph.getExportsInfo(importedModule); + const ids = this.getIds(moduleGraph); + if (ids.length > 0) + importedExportsInfo = importedExportsInfo.getNestedExportsInfo(ids); + let exportsInfo = moduleGraph.getExportsInfo( + moduleGraph.getParentModule(this) + ); + if (this.names.length > 0) + exportsInfo = exportsInfo.getNestedExportsInfo(this.names); const noExtraExports = + importedExportsInfo && importedExportsInfo.otherExportsInfo.provided === false; const noExtraImports = + exportsInfo && exportsInfo.otherExportsInfo.getUsed(runtime) === UsageState.Unused; - const ignoredExports = new Set(["default", ...this.activeExports]); - - let hiddenExports = undefined; - const otherStarExports = - this._discoverActiveExportsFromOtherStarExports(moduleGraph); - if (otherStarExports !== undefined) { - hiddenExports = new Set(); - for (let i = 0; i < otherStarExports.namesSlice; i++) { - hiddenExports.add(otherStarExports.names[i]); - } - for (const e of ignoredExports) hiddenExports.delete(e); - } - if (!noExtraExports && !noExtraImports) { - return { - ignoredExports, - hidden: hiddenExports - }; + return; } + const isNamespaceImport = + importedModule.getExportsType(moduleGraph, false) === "namespace"; + /** @type {Set} */ const exports = new Set(); /** @type {Set} */ const checked = new Set(); - /** @type {Set} */ - const hidden = hiddenExports !== undefined ? new Set() : undefined; if (noExtraImports) { for (const exportInfo of exportsInfo.orderedExports) { const name = exportInfo.name; - if (ignoredExports.has(name)) continue; if (exportInfo.getUsed(runtime) === UsageState.Unused) continue; - const importedExportInfo = - importedExportsInfo.getReadOnlyExportInfo(name); - if (importedExportInfo.provided === false) continue; - if (hiddenExports !== undefined && hiddenExports.has(name)) { - hidden.add(name); - continue; + if (name === "__esModule" && isNamespaceImport) { + exports.add(name); + } else if (importedExportsInfo) { + const importedExportInfo = + importedExportsInfo.getReadOnlyExportInfo(name); + if (importedExportInfo.provided === false) continue; + exports.add(name); + if (importedExportInfo.provided === true) continue; + checked.add(name); + } else { + exports.add(name); + checked.add(name); } - exports.add(name); - if (importedExportInfo.provided === true) continue; - checked.add(name); } } else if (noExtraExports) { for (const importedExportInfo of importedExportsInfo.orderedExports) { const name = importedExportInfo.name; - if (ignoredExports.has(name)) continue; if (importedExportInfo.provided === false) continue; - const exportInfo = exportsInfo.getReadOnlyExportInfo(name); - if (exportInfo.getUsed(runtime) === UsageState.Unused) continue; - if (hiddenExports !== undefined && hiddenExports.has(name)) { - hidden.add(name); - continue; + if (exportsInfo) { + const exportInfo = exportsInfo.getReadOnlyExportInfo(name); + if (exportInfo.getUsed(runtime) === UsageState.Unused) continue; } exports.add(name); if (importedExportInfo.provided === true) continue; checked.add(name); } + if (isNamespaceImport) { + exports.add("__esModule"); + checked.delete("__esModule"); + } } - return { ignoredExports, exports, checked, hidden }; + return { exports, checked }; } - /** - * @param {ModuleGraph} moduleGraph module graph - * @returns {null | false | function(ModuleGraphConnection, RuntimeSpec): ConnectionState} function to determine if the connection is active - */ - getCondition(moduleGraph) { - return (connection, runtime) => { - const mode = this.getMode(moduleGraph, runtime); - return mode.type !== "unused" && mode.type !== "empty-star"; - }; + serialize(context) { + const { write } = context; + write(this.asiSafe); + write(this.range); + write(this.valueRange); + write(this.base); + write(this.names); + write(this.ids); + write(this.resultUsed); + super.serialize(context); } - /** - * @param {ModuleGraph} moduleGraph the module graph - * @returns {ConnectionState} how this dependency connects the module to referencing modules - */ - getModuleEvaluationSideEffectsState(moduleGraph) { - return false; + deserialize(context) { + const { read } = context; + this.asiSafe = read(); + this.range = read(); + this.valueRange = read(); + this.base = read(); + this.names = read(); + this.ids = read(); + this.resultUsed = read(); + super.deserialize(context); } +} - /** - * Returns list of exports referenced by this dependency - * @param {ModuleGraph} moduleGraph module graph - * @param {RuntimeSpec} runtime the runtime for which the module is analysed - * @returns {(string[] | ReferencedExport)[]} referenced exports - */ - getReferencedExports(moduleGraph, runtime) { - const mode = this.getMode(moduleGraph, runtime); - - switch (mode.type) { - case "missing": - case "unused": - case "empty-star": - case "reexport-undefined": - return Dependency.NO_EXPORTS_REFERENCED; - - case "reexport-dynamic-default": - return Dependency.EXPORTS_OBJECT_REFERENCED; - - case "reexport-named-default": { - if (!mode.partialNamespaceExportInfo) - return Dependency.EXPORTS_OBJECT_REFERENCED; - /** @type {string[][]} */ - const referencedExports = []; - processExportInfo( - runtime, - referencedExports, - [], - /** @type {ExportInfo} */ (mode.partialNamespaceExportInfo) - ); - return referencedExports; - } - - case "reexport-namespace-object": - case "reexport-fake-namespace-object": { - if (!mode.partialNamespaceExportInfo) - return Dependency.EXPORTS_OBJECT_REFERENCED; - /** @type {string[][]} */ - const referencedExports = []; - processExportInfo( - runtime, - referencedExports, - [], - /** @type {ExportInfo} */ (mode.partialNamespaceExportInfo), - mode.type === "reexport-fake-namespace-object" - ); - return referencedExports; - } - - case "dynamic-reexport": - return Dependency.EXPORTS_OBJECT_REFERENCED; - - case "normal-reexport": { - const referencedExports = []; - for (const { ids, exportInfo, hidden } of mode.items) { - if (hidden) continue; - processExportInfo(runtime, referencedExports, ids, exportInfo, false); - } - return referencedExports; - } - - default: - throw new Error(`Unknown mode ${mode.type}`); - } - } +makeSerializable( + CommonJsExportRequireDependency, + "webpack/lib/dependencies/CommonJsExportRequireDependency" +); +CommonJsExportRequireDependency.Template = class CommonJsExportRequireDependencyTemplate extends ( + ModuleDependency.Template +) { /** - * @param {ModuleGraph} moduleGraph the module graph - * @returns {{ names: string[], namesSlice: number, dependencyIndices: number[], dependencyIndex: number } | undefined} exported names and their origin dependency + * @param {Dependency} dependency the dependency for which the template should be applied + * @param {ReplaceSource} source the current replace source which can be modified + * @param {DependencyTemplateContext} templateContext the context object + * @returns {void} */ - _discoverActiveExportsFromOtherStarExports(moduleGraph) { - if (!this.otherStarExports) return undefined; - - const i = - "length" in this.otherStarExports - ? this.otherStarExports.length - : countIterable(this.otherStarExports); - if (i === 0) return undefined; - - if (this.allStarExports) { - const { names, dependencyIndices } = moduleGraph.cached( - determineExportAssignments, - this.allStarExports.dependencies - ); - - return { - names, - namesSlice: dependencyIndices[i - 1], - dependencyIndices, - dependencyIndex: i - }; + apply( + dependency, + source, + { + module, + runtimeTemplate, + chunkGraph, + moduleGraph, + runtimeRequirements, + runtime } + ) { + const dep = /** @type {CommonJsExportRequireDependency} */ (dependency); + const used = moduleGraph + .getExportsInfo(module) + .getUsedName(dep.names, runtime); - const { names, dependencyIndices } = moduleGraph.cached( - determineExportAssignments, - this.otherStarExports, - this + const [type, base] = handleDependencyBase( + dep.base, + module, + runtimeRequirements ); - return { - names, - namesSlice: dependencyIndices[i - 1], - dependencyIndices, - dependencyIndex: i - }; - } - - /** - * Returns the exported names - * @param {ModuleGraph} moduleGraph module graph - * @returns {ExportsSpec | undefined} export names - */ - getExports(moduleGraph) { - const mode = this.getMode(moduleGraph, undefined); - - switch (mode.type) { - case "missing": - return undefined; - case "dynamic-reexport": { - const from = moduleGraph.getConnection(this); - return { - exports: true, - from, - canMangle: false, - excludeExports: mode.hidden - ? combine(mode.ignored, mode.hidden) - : mode.ignored, - hideExports: mode.hidden, - dependencies: [from.module] - }; - } - case "empty-star": - return { - exports: [], - hideExports: mode.hidden, - dependencies: [moduleGraph.getModule(this)] - }; - // falls through - case "normal-reexport": { - const from = moduleGraph.getConnection(this); - return { - exports: Array.from(mode.items, item => ({ - name: item.name, - from, - export: item.ids, - hidden: item.hidden - })), - priority: 1, - dependencies: [from.module] - }; - } - case "reexport-dynamic-default": { - { - const from = moduleGraph.getConnection(this); - return { - exports: [ - { - name: mode.name, - from, - export: ["default"] - } - ], - priority: 1, - dependencies: [from.module] - }; - } - } - case "reexport-undefined": - return { - exports: [mode.name], - dependencies: [moduleGraph.getModule(this)] - }; - case "reexport-fake-namespace-object": { - const from = moduleGraph.getConnection(this); - return { - exports: [ - { - name: mode.name, - from, - export: null, - exports: [ - { - name: "default", - canMangle: false, - from, - export: null - } - ] - } - ], - priority: 1, - dependencies: [from.module] - }; - } - case "reexport-namespace-object": { - const from = moduleGraph.getConnection(this); - return { - exports: [ - { - name: mode.name, - from, - export: null - } - ], - priority: 1, - dependencies: [from.module] - }; - } - case "reexport-named-default": { - const from = moduleGraph.getConnection(this); - return { - exports: [ - { - name: mode.name, - from, - export: ["default"] - } - ], - priority: 1, - dependencies: [from.module] - }; + const importedModule = moduleGraph.getModule(dep); + let requireExpr = runtimeTemplate.moduleExports({ + module: importedModule, + chunkGraph, + request: dep.request, + weak: dep.weak, + runtimeRequirements + }); + if (importedModule) { + const ids = dep.getIds(moduleGraph); + const usedImported = moduleGraph + .getExportsInfo(importedModule) + .getUsedName(ids, runtime); + if (usedImported) { + const comment = equals(usedImported, ids) + ? "" + : Template.toNormalComment(propertyAccess(ids)) + " "; + requireExpr += `${comment}${propertyAccess(usedImported)}`; } + } + + switch (type) { + case "expression": + source.replace( + dep.range[0], + dep.range[1] - 1, + used + ? `${base}${propertyAccess(used)} = ${requireExpr}` + : `/* unused reexport */ ${requireExpr}` + ); + return; + case "Object.defineProperty": + throw new Error("TODO"); default: - throw new Error(`Unknown mode ${mode.type}`); + throw new Error("Unexpected type"); } } +}; - /** - * @param {ModuleGraph} moduleGraph module graph - * @returns {number} effective mode - */ - _getEffectiveExportPresenceLevel(moduleGraph) { - if (this.exportPresenceMode !== ExportPresenceModes.AUTO) - return this.exportPresenceMode; - return moduleGraph.getParentModule(this).buildMeta.strictHarmonyModule - ? ExportPresenceModes.ERROR - : ExportPresenceModes.WARN; - } +module.exports = CommonJsExportRequireDependency; - /** - * Returns warnings - * @param {ModuleGraph} moduleGraph module graph - * @returns {WebpackError[]} warnings - */ - getWarnings(moduleGraph) { - const exportsPresence = this._getEffectiveExportPresenceLevel(moduleGraph); - if (exportsPresence === ExportPresenceModes.WARN) { - return this._getErrors(moduleGraph); - } - return null; + +/***/ }), + +/***/ 9585: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ + + + +const InitFragment = __webpack_require__(51739); +const makeSerializable = __webpack_require__(26522); +const propertyAccess = __webpack_require__(86709); +const { handleDependencyBase } = __webpack_require__(95217); +const NullDependency = __webpack_require__(65845); + +/** @typedef {import("webpack-sources").ReplaceSource} ReplaceSource */ +/** @typedef {import("../Dependency")} Dependency */ +/** @typedef {import("../Dependency").ExportsSpec} ExportsSpec */ +/** @typedef {import("../DependencyTemplate").DependencyTemplateContext} DependencyTemplateContext */ +/** @typedef {import("../ModuleGraph")} ModuleGraph */ + +const EMPTY_OBJECT = {}; + +class CommonJsExportsDependency extends NullDependency { + constructor(range, valueRange, base, names) { + super(); + this.range = range; + this.valueRange = valueRange; + this.base = base; + this.names = names; } - /** - * Returns errors - * @param {ModuleGraph} moduleGraph module graph - * @returns {WebpackError[]} errors - */ - getErrors(moduleGraph) { - const exportsPresence = this._getEffectiveExportPresenceLevel(moduleGraph); - if (exportsPresence === ExportPresenceModes.ERROR) { - return this._getErrors(moduleGraph); - } - return null; + get type() { + return "cjs exports"; } /** + * Returns the exported names * @param {ModuleGraph} moduleGraph module graph - * @returns {WebpackError[] | undefined} errors + * @returns {ExportsSpec | undefined} export names */ - _getErrors(moduleGraph) { - const ids = this.getIds(moduleGraph); - let errors = this.getLinkingErrors( - moduleGraph, - ids, - `(reexported as '${this.name}')` - ); - if (ids.length === 0 && this.name === null) { - const potentialConflicts = - this._discoverActiveExportsFromOtherStarExports(moduleGraph); - if (potentialConflicts && potentialConflicts.namesSlice > 0) { - const ownNames = new Set( - potentialConflicts.names.slice( - potentialConflicts.namesSlice, - potentialConflicts.dependencyIndices[ - potentialConflicts.dependencyIndex - ] - ) - ); - const importedModule = moduleGraph.getModule(this); - if (importedModule) { - const exportsInfo = moduleGraph.getExportsInfo(importedModule); - const conflicts = new Map(); - for (const exportInfo of exportsInfo.orderedExports) { - if (exportInfo.provided !== true) continue; - if (exportInfo.name === "default") continue; - if (this.activeExports.has(exportInfo.name)) continue; - if (ownNames.has(exportInfo.name)) continue; - const conflictingDependency = findDependencyForName( - potentialConflicts, - exportInfo.name, - this.allStarExports - ? this.allStarExports.dependencies - : [...this.otherStarExports, this] - ); - if (!conflictingDependency) continue; - const target = exportInfo.getTerminalBinding(moduleGraph); - if (!target) continue; - const conflictingModule = moduleGraph.getModule( - conflictingDependency - ); - if (conflictingModule === importedModule) continue; - const conflictingExportInfo = moduleGraph.getExportInfo( - conflictingModule, - exportInfo.name - ); - const conflictingTarget = - conflictingExportInfo.getTerminalBinding(moduleGraph); - if (!conflictingTarget) continue; - if (target === conflictingTarget) continue; - const list = conflicts.get(conflictingDependency.request); - if (list === undefined) { - conflicts.set(conflictingDependency.request, [exportInfo.name]); - } else { - list.push(exportInfo.name); - } - } - for (const [request, exports] of conflicts) { - if (!errors) errors = []; - errors.push( - new HarmonyLinkingError( - `The requested module '${ - this.request - }' contains conflicting star exports for the ${ - exports.length > 1 ? "names" : "name" - } ${exports - .map(e => `'${e}'`) - .join(", ")} with the previous requested module '${request}'` - ) - ); - } + getExports(moduleGraph) { + const name = this.names[0]; + return { + exports: [ + { + name, + // we can't mangle names that are in an empty object + // because one could access the prototype property + // when export isn't set yet + canMangle: !(name in EMPTY_OBJECT) } - } - } - return errors; + ], + dependencies: undefined + }; } serialize(context) { - const { write, setCircularReference } = context; - - setCircularReference(this); - write(this.ids); - write(this.name); - write(this.activeExports); - write(this.otherStarExports); - write(this.exportPresenceMode); - write(this.allStarExports); - + const { write } = context; + write(this.range); + write(this.valueRange); + write(this.base); + write(this.names); super.serialize(context); } deserialize(context) { - const { read, setCircularReference } = context; - - setCircularReference(this); - this.ids = read(); - this.name = read(); - this.activeExports = read(); - this.otherStarExports = read(); - this.exportPresenceMode = read(); - this.allStarExports = read(); - + const { read } = context; + this.range = read(); + this.valueRange = read(); + this.base = read(); + this.names = read(); super.deserialize(context); } } makeSerializable( - HarmonyExportImportedSpecifierDependency, - "webpack/lib/dependencies/HarmonyExportImportedSpecifierDependency" + CommonJsExportsDependency, + "webpack/lib/dependencies/CommonJsExportsDependency" ); -module.exports = HarmonyExportImportedSpecifierDependency; - -HarmonyExportImportedSpecifierDependency.Template = class HarmonyExportImportedSpecifierDependencyTemplate extends ( - HarmonyImportDependency.Template +CommonJsExportsDependency.Template = class CommonJsExportsDependencyTemplate extends ( + NullDependency.Template ) { /** * @param {Dependency} dependency the dependency for which the template should be applied @@ -79775,379 +77187,571 @@ HarmonyExportImportedSpecifierDependency.Template = class HarmonyExportImportedS * @param {DependencyTemplateContext} templateContext the context object * @returns {void} */ - apply(dependency, source, templateContext) { - const { moduleGraph, runtime, concatenationScope } = templateContext; + apply( + dependency, + source, + { module, moduleGraph, initFragments, runtimeRequirements, runtime } + ) { + const dep = /** @type {CommonJsExportsDependency} */ (dependency); + const used = moduleGraph + .getExportsInfo(module) + .getUsedName(dep.names, runtime); - const dep = /** @type {HarmonyExportImportedSpecifierDependency} */ ( - dependency + const [type, base] = handleDependencyBase( + dep.base, + module, + runtimeRequirements ); - const mode = dep.getMode(moduleGraph, runtime); - - if (concatenationScope) { - switch (mode.type) { - case "reexport-undefined": - concatenationScope.registerRawExport( - mode.name, - "/* reexport non-default export from non-harmony */ undefined" + switch (type) { + case "expression": + if (!used) { + initFragments.push( + new InitFragment( + "var __webpack_unused_export__;\n", + InitFragment.STAGE_CONSTANTS, + 0, + "__webpack_unused_export__" + ) ); - } - return; + source.replace( + dep.range[0], + dep.range[1] - 1, + "__webpack_unused_export__" + ); + return; + } + source.replace( + dep.range[0], + dep.range[1] - 1, + `${base}${propertyAccess(used)}` + ); + return; + case "Object.defineProperty": + if (!used) { + initFragments.push( + new InitFragment( + "var __webpack_unused_export__;\n", + InitFragment.STAGE_CONSTANTS, + 0, + "__webpack_unused_export__" + ) + ); + source.replace( + dep.range[0], + dep.valueRange[0] - 1, + "__webpack_unused_export__ = (" + ); + source.replace(dep.valueRange[1], dep.range[1] - 1, ")"); + return; + } + source.replace( + dep.range[0], + dep.valueRange[0] - 1, + `Object.defineProperty(${base}${propertyAccess( + used.slice(0, -1) + )}, ${JSON.stringify(used[used.length - 1])}, (` + ); + source.replace(dep.valueRange[1], dep.range[1] - 1, "))"); + return; } + } +}; - if (mode.type !== "unused" && mode.type !== "empty-star") { - super.apply(dependency, source, templateContext); +module.exports = CommonJsExportsDependency; - this._addExportFragments( - templateContext.initFragments, - dep, - mode, - templateContext.module, - moduleGraph, - runtime, - templateContext.runtimeTemplate, - templateContext.runtimeRequirements - ); - } - } - /** - * @param {InitFragment[]} initFragments target array for init fragments - * @param {HarmonyExportImportedSpecifierDependency} dep dependency - * @param {ExportMode} mode the export mode - * @param {Module} module the current module - * @param {ModuleGraph} moduleGraph the module graph - * @param {RuntimeSpec} runtime the runtime - * @param {RuntimeTemplate} runtimeTemplate the runtime template - * @param {Set} runtimeRequirements runtime requirements - * @returns {void} - */ - _addExportFragments( - initFragments, - dep, - mode, - module, - moduleGraph, - runtime, - runtimeTemplate, - runtimeRequirements - ) { - const importedModule = moduleGraph.getModule(dep); - const importVar = dep.getImportVar(moduleGraph); +/***/ }), - switch (mode.type) { - case "missing": - case "empty-star": - initFragments.push( - new InitFragment( - "/* empty/unused harmony star reexport */\n", - InitFragment.STAGE_HARMONY_EXPORTS, - 1 - ) - ); - break; +/***/ 49577: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - case "unused": - initFragments.push( - new InitFragment( - `${Template.toNormalComment( - `unused harmony reexport ${mode.name}` - )}\n`, - InitFragment.STAGE_HARMONY_EXPORTS, - 1 - ) - ); - break; +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ - case "reexport-dynamic-default": - initFragments.push( - this.getReexportFragment( - module, - "reexport default from dynamic", - moduleGraph.getExportsInfo(module).getUsedName(mode.name, runtime), - importVar, - null, - runtimeRequirements - ) - ); - break; - case "reexport-fake-namespace-object": - initFragments.push( - ...this.getReexportFakeNamespaceObjectFragments( - module, - moduleGraph.getExportsInfo(module).getUsedName(mode.name, runtime), - importVar, - mode.fakeType, - runtimeRequirements - ) - ); - break; - case "reexport-undefined": - initFragments.push( - this.getReexportFragment( - module, - "reexport non-default export from non-harmony", - moduleGraph.getExportsInfo(module).getUsedName(mode.name, runtime), - "undefined", - "", - runtimeRequirements - ) - ); - break; +const RuntimeGlobals = __webpack_require__(49404); +const formatLocation = __webpack_require__(57261); +const { evaluateToString } = __webpack_require__(28723); +const propertyAccess = __webpack_require__(86709); +const CommonJsExportRequireDependency = __webpack_require__(76922); +const CommonJsExportsDependency = __webpack_require__(9585); +const CommonJsSelfReferenceDependency = __webpack_require__(69217); +const DynamicExports = __webpack_require__(87370); +const HarmonyExports = __webpack_require__(37637); +const ModuleDecoratorDependency = __webpack_require__(58969); - case "reexport-named-default": - initFragments.push( - this.getReexportFragment( - module, - "reexport default export from named module", - moduleGraph.getExportsInfo(module).getUsedName(mode.name, runtime), - importVar, - "", - runtimeRequirements - ) - ); - break; +/** @typedef {import("estree").Expression} ExpressionNode */ +/** @typedef {import("../NormalModule")} NormalModule */ +/** @typedef {import("../javascript/BasicEvaluatedExpression")} BasicEvaluatedExpression */ +/** @typedef {import("../javascript/JavascriptParser")} JavascriptParser */ - case "reexport-namespace-object": - initFragments.push( - this.getReexportFragment( - module, - "reexport module object", - moduleGraph.getExportsInfo(module).getUsedName(mode.name, runtime), - importVar, - "", - runtimeRequirements - ) - ); - break; +const getValueOfPropertyDescription = expr => { + if (expr.type !== "ObjectExpression") return; + for (const property of expr.properties) { + if (property.computed) continue; + const key = property.key; + if (key.type !== "Identifier" || key.name !== "value") continue; + return property.value; + } +}; - case "normal-reexport": - for (const { name, ids, checked, hidden } of mode.items) { - if (hidden) continue; - if (checked) { - initFragments.push( - new InitFragment( - "/* harmony reexport (checked) */ " + - this.getConditionalReexportStatement( - module, - name, - importVar, - ids, - runtimeRequirements - ), - moduleGraph.isAsync(importedModule) - ? InitFragment.STAGE_ASYNC_HARMONY_IMPORTS - : InitFragment.STAGE_HARMONY_IMPORTS, - dep.sourceOrder - ) - ); - } else { - initFragments.push( - this.getReexportFragment( - module, - "reexport safe", - moduleGraph.getExportsInfo(module).getUsedName(name, runtime), - importVar, - moduleGraph - .getExportsInfo(importedModule) - .getUsedName(ids, runtime), - runtimeRequirements - ) - ); - } - } - break; +const isTruthyLiteral = expr => { + switch (expr.type) { + case "Literal": + return !!expr.value; + case "UnaryExpression": + if (expr.operator === "!") return isFalsyLiteral(expr.argument); + } + return false; +}; - case "dynamic-reexport": { - const ignored = mode.hidden - ? combine(mode.ignored, mode.hidden) - : mode.ignored; - const modern = - runtimeTemplate.supportsConst() && - runtimeTemplate.supportsArrowFunction(); - let content = - "/* harmony reexport (unknown) */ var __WEBPACK_REEXPORT_OBJECT__ = {};\n" + - `/* harmony reexport (unknown) */ for(${ - modern ? "const" : "var" - } __WEBPACK_IMPORT_KEY__ in ${importVar}) `; +const isFalsyLiteral = expr => { + switch (expr.type) { + case "Literal": + return !expr.value; + case "UnaryExpression": + if (expr.operator === "!") return isTruthyLiteral(expr.argument); + } + return false; +}; - // Filter out exports which are defined by other exports - // and filter out default export because it cannot be reexported with * - if (ignored.size > 1) { - content += - "if(" + - JSON.stringify(Array.from(ignored)) + - ".indexOf(__WEBPACK_IMPORT_KEY__) < 0) "; - } else if (ignored.size === 1) { - content += `if(__WEBPACK_IMPORT_KEY__ !== ${JSON.stringify( - first(ignored) - )}) `; - } +/** + * @param {JavascriptParser} parser the parser + * @param {ExpressionNode} expr expression + * @returns {{ argument: BasicEvaluatedExpression, ids: string[] } | undefined} parsed call + */ +const parseRequireCall = (parser, expr) => { + const ids = []; + while (expr.type === "MemberExpression") { + if (expr.object.type === "Super") return; + if (!expr.property) return; + const prop = expr.property; + if (expr.computed) { + if (prop.type !== "Literal") return; + ids.push(`${prop.value}`); + } else { + if (prop.type !== "Identifier") return; + ids.push(prop.name); + } + expr = expr.object; + } + if (expr.type !== "CallExpression" || expr.arguments.length !== 1) return; + const callee = expr.callee; + if ( + callee.type !== "Identifier" || + parser.getVariableInfo(callee.name) !== "require" + ) { + return; + } + const arg = expr.arguments[0]; + if (arg.type === "SpreadElement") return; + const argValue = parser.evaluateExpression(arg); + return { argument: argValue, ids: ids.reverse() }; +}; - content += `__WEBPACK_REEXPORT_OBJECT__[__WEBPACK_IMPORT_KEY__] = `; - if (modern) { - content += `() => ${importVar}[__WEBPACK_IMPORT_KEY__]`; +class CommonJsExportsParserPlugin { + constructor(moduleGraph) { + this.moduleGraph = moduleGraph; + } + + /** + * @param {JavascriptParser} parser the parser + */ + apply(parser) { + const enableStructuredExports = () => { + DynamicExports.enable(parser.state); + }; + const checkNamespace = (topLevel, members, valueExpr) => { + if (!DynamicExports.isEnabled(parser.state)) return; + if (members.length > 0 && members[0] === "__esModule") { + if (valueExpr && isTruthyLiteral(valueExpr) && topLevel) { + DynamicExports.setFlagged(parser.state); } else { - content += `function(key) { return ${importVar}[key]; }.bind(0, __WEBPACK_IMPORT_KEY__)`; + DynamicExports.setDynamic(parser.state); } + } + }; + const bailout = reason => { + DynamicExports.bailout(parser.state); + if (reason) bailoutHint(reason); + }; + const bailoutHint = reason => { + this.moduleGraph + .getOptimizationBailout(parser.state.module) + .push(`CommonJS bailout: ${reason}`); + }; - runtimeRequirements.add(RuntimeGlobals.exports); - runtimeRequirements.add(RuntimeGlobals.definePropertyGetters); + // metadata // + parser.hooks.evaluateTypeof + .for("module") + .tap("CommonJsExportsParserPlugin", evaluateToString("object")); + parser.hooks.evaluateTypeof + .for("exports") + .tap("CommonJsPlugin", evaluateToString("object")); - const exportsName = module.exportsArgument; - initFragments.push( - new InitFragment( - `${content}\n/* harmony reexport (unknown) */ ${RuntimeGlobals.definePropertyGetters}(${exportsName}, __WEBPACK_REEXPORT_OBJECT__);\n`, - moduleGraph.isAsync(importedModule) - ? InitFragment.STAGE_ASYNC_HARMONY_IMPORTS - : InitFragment.STAGE_HARMONY_IMPORTS, - dep.sourceOrder - ) + // exporting // + const handleAssignExport = (expr, base, members) => { + if (HarmonyExports.isEnabled(parser.state)) return; + // Handle reexporting + const requireCall = parseRequireCall(parser, expr.right); + if ( + requireCall && + requireCall.argument.isString() && + (members.length === 0 || members[0] !== "__esModule") + ) { + enableStructuredExports(); + // It's possible to reexport __esModule, so we must convert to a dynamic module + if (members.length === 0) DynamicExports.setDynamic(parser.state); + const dep = new CommonJsExportRequireDependency( + expr.range, + null, + base, + members, + requireCall.argument.string, + requireCall.ids, + !parser.isStatementLevelExpression(expr) ); - break; + dep.loc = expr.loc; + dep.optional = !!parser.scope.inTry; + parser.state.module.addDependency(dep); + return true; } + if (members.length === 0) return; + enableStructuredExports(); + const remainingMembers = members; + checkNamespace( + parser.statementPath.length === 1 && + parser.isStatementLevelExpression(expr), + remainingMembers, + expr.right + ); + const dep = new CommonJsExportsDependency( + expr.left.range, + null, + base, + remainingMembers + ); + dep.loc = expr.loc; + parser.state.module.addDependency(dep); + parser.walkExpression(expr.right); + return true; + }; + parser.hooks.assignMemberChain + .for("exports") + .tap("CommonJsExportsParserPlugin", (expr, members) => { + return handleAssignExport(expr, "exports", members); + }); + parser.hooks.assignMemberChain + .for("this") + .tap("CommonJsExportsParserPlugin", (expr, members) => { + if (!parser.scope.topLevelScope) return; + return handleAssignExport(expr, "this", members); + }); + parser.hooks.assignMemberChain + .for("module") + .tap("CommonJsExportsParserPlugin", (expr, members) => { + if (members[0] !== "exports") return; + return handleAssignExport(expr, "module.exports", members.slice(1)); + }); + parser.hooks.call + .for("Object.defineProperty") + .tap("CommonJsExportsParserPlugin", expression => { + const expr = /** @type {import("estree").CallExpression} */ ( + expression + ); + if (!parser.isStatementLevelExpression(expr)) return; + if (expr.arguments.length !== 3) return; + if (expr.arguments[0].type === "SpreadElement") return; + if (expr.arguments[1].type === "SpreadElement") return; + if (expr.arguments[2].type === "SpreadElement") return; + const exportsArg = parser.evaluateExpression(expr.arguments[0]); + if (!exportsArg || !exportsArg.isIdentifier()) return; + if ( + exportsArg.identifier !== "exports" && + exportsArg.identifier !== "module.exports" && + (exportsArg.identifier !== "this" || !parser.scope.topLevelScope) + ) { + return; + } + const propertyArg = parser.evaluateExpression(expr.arguments[1]); + if (!propertyArg) return; + const property = propertyArg.asString(); + if (typeof property !== "string") return; + enableStructuredExports(); + const descArg = expr.arguments[2]; + checkNamespace( + parser.statementPath.length === 1, + [property], + getValueOfPropertyDescription(descArg) + ); + const dep = new CommonJsExportsDependency( + expr.range, + expr.arguments[2].range, + `Object.defineProperty(${exportsArg.identifier})`, + [property] + ); + dep.loc = expr.loc; + parser.state.module.addDependency(dep); - default: - throw new Error(`Unknown mode ${mode.type}`); - } - } - - getReexportFragment( - module, - comment, - key, - name, - valueKey, - runtimeRequirements - ) { - const returnValue = this.getReturnValue(name, valueKey); - - runtimeRequirements.add(RuntimeGlobals.exports); - runtimeRequirements.add(RuntimeGlobals.definePropertyGetters); + parser.walkExpression(expr.arguments[2]); + return true; + }); - const map = new Map(); - map.set(key, `/* ${comment} */ ${returnValue}`); + // Self reference // + const handleAccessExport = (expr, base, members, call = undefined) => { + if (HarmonyExports.isEnabled(parser.state)) return; + if (members.length === 0) { + bailout(`${base} is used directly at ${formatLocation(expr.loc)}`); + } + if (call && members.length === 1) { + bailoutHint( + `${base}${propertyAccess( + members + )}(...) prevents optimization as ${base} is passed as call context at ${formatLocation( + expr.loc + )}` + ); + } + const dep = new CommonJsSelfReferenceDependency( + expr.range, + base, + members, + !!call + ); + dep.loc = expr.loc; + parser.state.module.addDependency(dep); + if (call) { + parser.walkExpressions(call.arguments); + } + return true; + }; + parser.hooks.callMemberChain + .for("exports") + .tap("CommonJsExportsParserPlugin", (expr, members) => { + return handleAccessExport(expr.callee, "exports", members, expr); + }); + parser.hooks.expressionMemberChain + .for("exports") + .tap("CommonJsExportsParserPlugin", (expr, members) => { + return handleAccessExport(expr, "exports", members); + }); + parser.hooks.expression + .for("exports") + .tap("CommonJsExportsParserPlugin", expr => { + return handleAccessExport(expr, "exports", []); + }); + parser.hooks.callMemberChain + .for("module") + .tap("CommonJsExportsParserPlugin", (expr, members) => { + if (members[0] !== "exports") return; + return handleAccessExport( + expr.callee, + "module.exports", + members.slice(1), + expr + ); + }); + parser.hooks.expressionMemberChain + .for("module") + .tap("CommonJsExportsParserPlugin", (expr, members) => { + if (members[0] !== "exports") return; + return handleAccessExport(expr, "module.exports", members.slice(1)); + }); + parser.hooks.expression + .for("module.exports") + .tap("CommonJsExportsParserPlugin", expr => { + return handleAccessExport(expr, "module.exports", []); + }); + parser.hooks.callMemberChain + .for("this") + .tap("CommonJsExportsParserPlugin", (expr, members) => { + if (!parser.scope.topLevelScope) return; + return handleAccessExport(expr.callee, "this", members, expr); + }); + parser.hooks.expressionMemberChain + .for("this") + .tap("CommonJsExportsParserPlugin", (expr, members) => { + if (!parser.scope.topLevelScope) return; + return handleAccessExport(expr, "this", members); + }); + parser.hooks.expression + .for("this") + .tap("CommonJsExportsParserPlugin", expr => { + if (!parser.scope.topLevelScope) return; + return handleAccessExport(expr, "this", []); + }); - return new HarmonyExportInitFragment(module.exportsArgument, map); + // Bailouts // + parser.hooks.expression.for("module").tap("CommonJsPlugin", expr => { + bailout(); + const isHarmony = HarmonyExports.isEnabled(parser.state); + const dep = new ModuleDecoratorDependency( + isHarmony + ? RuntimeGlobals.harmonyModuleDecorator + : RuntimeGlobals.nodeModuleDecorator, + !isHarmony + ); + dep.loc = expr.loc; + parser.state.module.addDependency(dep); + return true; + }); } +} +module.exports = CommonJsExportsParserPlugin; - getReexportFakeNamespaceObjectFragments( - module, - key, - name, - fakeType, - runtimeRequirements - ) { - runtimeRequirements.add(RuntimeGlobals.exports); - runtimeRequirements.add(RuntimeGlobals.definePropertyGetters); - runtimeRequirements.add(RuntimeGlobals.createFakeNamespaceObject); - const map = new Map(); - map.set( - key, - `/* reexport fake namespace object from non-harmony */ ${name}_namespace_cache || (${name}_namespace_cache = ${ - RuntimeGlobals.createFakeNamespaceObject - }(${name}${fakeType ? `, ${fakeType}` : ""}))` - ); +/***/ }), - return [ - new InitFragment( - `var ${name}_namespace_cache;\n`, - InitFragment.STAGE_CONSTANTS, - -1, - `${name}_namespace_cache` - ), - new HarmonyExportInitFragment(module.exportsArgument, map) - ]; - } +/***/ 29496: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - getConditionalReexportStatement( - module, - key, - name, - valueKey, - runtimeRequirements - ) { - if (valueKey === false) { - return "/* unused export */\n"; - } +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ - const exportsName = module.exportsArgument; - const returnValue = this.getReturnValue(name, valueKey); - runtimeRequirements.add(RuntimeGlobals.exports); - runtimeRequirements.add(RuntimeGlobals.definePropertyGetters); - runtimeRequirements.add(RuntimeGlobals.hasOwnProperty); - return `if(${RuntimeGlobals.hasOwnProperty}(${name}, ${JSON.stringify( - valueKey[0] - )})) ${ - RuntimeGlobals.definePropertyGetters - }(${exportsName}, { ${JSON.stringify( - key - )}: function() { return ${returnValue}; } });\n`; - } +const Template = __webpack_require__(92066); +const { equals } = __webpack_require__(21537); +const makeSerializable = __webpack_require__(26522); +const propertyAccess = __webpack_require__(86709); +const ModuleDependency = __webpack_require__(80944); - getReturnValue(name, valueKey) { - if (valueKey === null) { - return `${name}_default.a`; - } +/** @typedef {import("webpack-sources").ReplaceSource} ReplaceSource */ +/** @typedef {import("../Dependency")} Dependency */ +/** @typedef {import("../Dependency").ReferencedExport} ReferencedExport */ +/** @typedef {import("../DependencyTemplate").DependencyTemplateContext} DependencyTemplateContext */ +/** @typedef {import("../ModuleGraph")} ModuleGraph */ +/** @typedef {import("../util/runtime").RuntimeSpec} RuntimeSpec */ - if (valueKey === "") { - return name; - } +class CommonJsFullRequireDependency extends ModuleDependency { + /** + * @param {string} request the request string + * @param {[number, number]} range location in source code + * @param {string[]} names accessed properties on module + */ + constructor(request, range, names) { + super(request); + this.range = range; + this.names = names; + this.call = false; + this.asiSafe = undefined; + } - if (valueKey === false) { - return "/* unused export */ undefined"; + /** + * Returns list of exports referenced by this dependency + * @param {ModuleGraph} moduleGraph module graph + * @param {RuntimeSpec} runtime the runtime for which the module is analysed + * @returns {(string[] | ReferencedExport)[]} referenced exports + */ + getReferencedExports(moduleGraph, runtime) { + if (this.call) { + const importedModule = moduleGraph.getModule(this); + if ( + !importedModule || + importedModule.getExportsType(moduleGraph, false) !== "namespace" + ) { + return [this.names.slice(0, -1)]; + } } - - return `${name}${propertyAccess(valueKey)}`; + return [this.names]; } -}; -class HarmonyStarExportsList { - constructor() { - /** @type {HarmonyExportImportedSpecifierDependency[]} */ - this.dependencies = []; + serialize(context) { + const { write } = context; + write(this.names); + write(this.call); + write(this.asiSafe); + super.serialize(context); } - /** - * @param {HarmonyExportImportedSpecifierDependency} dep dependency - * @returns {void} - */ - push(dep) { - this.dependencies.push(dep); + deserialize(context) { + const { read } = context; + this.names = read(); + this.call = read(); + this.asiSafe = read(); + super.deserialize(context); } - slice() { - return this.dependencies.slice(); + get type() { + return "cjs full require"; } - serialize({ write, setCircularReference }) { - setCircularReference(this); - write(this.dependencies); + get category() { + return "commonjs"; } +} - deserialize({ read, setCircularReference }) { - setCircularReference(this); - this.dependencies = read(); +CommonJsFullRequireDependency.Template = class CommonJsFullRequireDependencyTemplate extends ( + ModuleDependency.Template +) { + /** + * @param {Dependency} dependency the dependency for which the template should be applied + * @param {ReplaceSource} source the current replace source which can be modified + * @param {DependencyTemplateContext} templateContext the context object + * @returns {void} + */ + apply( + dependency, + source, + { + module, + runtimeTemplate, + moduleGraph, + chunkGraph, + runtimeRequirements, + runtime, + initFragments + } + ) { + const dep = /** @type {CommonJsFullRequireDependency} */ (dependency); + if (!dep.range) return; + const importedModule = moduleGraph.getModule(dep); + let requireExpr = runtimeTemplate.moduleExports({ + module: importedModule, + chunkGraph, + request: dep.request, + weak: dep.weak, + runtimeRequirements + }); + if (importedModule) { + const ids = dep.names; + const usedImported = moduleGraph + .getExportsInfo(importedModule) + .getUsedName(ids, runtime); + if (usedImported) { + const comment = equals(usedImported, ids) + ? "" + : Template.toNormalComment(propertyAccess(ids)) + " "; + const access = `${comment}${propertyAccess(usedImported)}`; + requireExpr = + dep.asiSafe === true + ? `(${requireExpr}${access})` + : `${requireExpr}${access}`; + } + } + source.replace(dep.range[0], dep.range[1] - 1, requireExpr); } -} +}; makeSerializable( - HarmonyStarExportsList, - "webpack/lib/dependencies/HarmonyExportImportedSpecifierDependency", - "HarmonyStarExportsList" + CommonJsFullRequireDependency, + "webpack/lib/dependencies/CommonJsFullRequireDependency" ); -module.exports.HarmonyStarExportsList = HarmonyStarExportsList; +module.exports = CommonJsFullRequireDependency; /***/ }), -/***/ 68664: +/***/ 78321: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; @@ -80158,169 +77762,392 @@ module.exports.HarmonyStarExportsList = HarmonyStarExportsList; -const InitFragment = __webpack_require__(51739); +const CommentCompilationWarning = __webpack_require__(28151); const RuntimeGlobals = __webpack_require__(49404); -const { first } = __webpack_require__(34715); - -/** @typedef {import("webpack-sources").Source} Source */ -/** @typedef {import("../Generator").GenerateContext} GenerateContext */ - -const joinIterableWithComma = iterable => { - // This is more performant than Array.from().join(", ") - // as it doesn't create an array - let str = ""; - let first = true; - for (const item of iterable) { - if (first) { - first = false; - } else { - str += ", "; - } - str += item; - } - return str; -}; +const UnsupportedFeatureWarning = __webpack_require__(9532); +const { + evaluateToIdentifier, + evaluateToString, + expressionIsUnsupported, + toConstantDependency +} = __webpack_require__(28723); +const CommonJsFullRequireDependency = __webpack_require__(29496); +const CommonJsRequireContextDependency = __webpack_require__(84175); +const CommonJsRequireDependency = __webpack_require__(38604); +const ConstDependency = __webpack_require__(60864); +const ContextDependencyHelpers = __webpack_require__(7114); +const LocalModuleDependency = __webpack_require__(67494); +const { getLocalModule } = __webpack_require__(6311); +const RequireHeaderDependency = __webpack_require__(57010); +const RequireResolveContextDependency = __webpack_require__(48789); +const RequireResolveDependency = __webpack_require__(93172); +const RequireResolveHeaderDependency = __webpack_require__(24128); -const EMPTY_MAP = new Map(); -const EMPTY_SET = new Set(); +/** @typedef {import("../../declarations/WebpackOptions").JavascriptParserOptions} JavascriptParserOptions */ -/** - * @typedef {GenerateContext} Context - */ -class HarmonyExportInitFragment extends InitFragment { +class CommonJsImportsParserPlugin { /** - * @param {string} exportsArgument the exports identifier - * @param {Map} exportMap mapping from used name to exposed variable name - * @param {Set} unusedExports list of unused export names + * @param {JavascriptParserOptions} options parser options */ - constructor( - exportsArgument, - exportMap = EMPTY_MAP, - unusedExports = EMPTY_SET - ) { - super(undefined, InitFragment.STAGE_HARMONY_EXPORTS, 1, "harmony-exports"); - this.exportsArgument = exportsArgument; - this.exportMap = exportMap; - this.unusedExports = unusedExports; + constructor(options) { + this.options = options; } - /** - * @param {HarmonyExportInitFragment[]} fragments all fragments to merge - * @returns {HarmonyExportInitFragment} merged fragment - */ - mergeAll(fragments) { - let exportMap; - let exportMapOwned = false; - let unusedExports; - let unusedExportsOwned = false; + apply(parser) { + const options = this.options; - for (const fragment of fragments) { - if (fragment.exportMap.size !== 0) { - if (exportMap === undefined) { - exportMap = fragment.exportMap; - exportMapOwned = false; - } else { - if (!exportMapOwned) { - exportMap = new Map(exportMap); - exportMapOwned = true; + // metadata // + const tapRequireExpression = (expression, getMembers) => { + parser.hooks.typeof + .for(expression) + .tap( + "CommonJsPlugin", + toConstantDependency(parser, JSON.stringify("function")) + ); + parser.hooks.evaluateTypeof + .for(expression) + .tap("CommonJsPlugin", evaluateToString("function")); + parser.hooks.evaluateIdentifier + .for(expression) + .tap( + "CommonJsPlugin", + evaluateToIdentifier(expression, "require", getMembers, true) + ); + }; + tapRequireExpression("require", () => []); + tapRequireExpression("require.resolve", () => ["resolve"]); + tapRequireExpression("require.resolveWeak", () => ["resolveWeak"]); + + // Weird stuff // + parser.hooks.assign.for("require").tap("CommonJsPlugin", expr => { + // to not leak to global "require", we need to define a local require here. + const dep = new ConstDependency("var require;", 0); + dep.loc = expr.loc; + parser.state.module.addPresentationalDependency(dep); + return true; + }); + + // Unsupported // + parser.hooks.expression + .for("require.main.require") + .tap( + "CommonJsPlugin", + expressionIsUnsupported( + parser, + "require.main.require is not supported by webpack." + ) + ); + parser.hooks.call + .for("require.main.require") + .tap( + "CommonJsPlugin", + expressionIsUnsupported( + parser, + "require.main.require is not supported by webpack." + ) + ); + parser.hooks.expression + .for("module.parent.require") + .tap( + "CommonJsPlugin", + expressionIsUnsupported( + parser, + "module.parent.require is not supported by webpack." + ) + ); + parser.hooks.call + .for("module.parent.require") + .tap( + "CommonJsPlugin", + expressionIsUnsupported( + parser, + "module.parent.require is not supported by webpack." + ) + ); + + // renaming // + parser.hooks.canRename.for("require").tap("CommonJsPlugin", () => true); + parser.hooks.rename.for("require").tap("CommonJsPlugin", expr => { + // To avoid "not defined" error, replace the value with undefined + const dep = new ConstDependency("undefined", expr.range); + dep.loc = expr.loc; + parser.state.module.addPresentationalDependency(dep); + return false; + }); + + // inspection // + parser.hooks.expression + .for("require.cache") + .tap( + "CommonJsImportsParserPlugin", + toConstantDependency(parser, RuntimeGlobals.moduleCache, [ + RuntimeGlobals.moduleCache, + RuntimeGlobals.moduleId, + RuntimeGlobals.moduleLoaded + ]) + ); + + // require as expression // + parser.hooks.expression + .for("require") + .tap("CommonJsImportsParserPlugin", expr => { + const dep = new CommonJsRequireContextDependency( + { + request: options.unknownContextRequest, + recursive: options.unknownContextRecursive, + regExp: options.unknownContextRegExp, + mode: "sync" + }, + expr.range, + undefined, + parser.scope.inShorthand + ); + dep.critical = + options.unknownContextCritical && + "require function is used in a way in which dependencies cannot be statically extracted"; + dep.loc = expr.loc; + dep.optional = !!parser.scope.inTry; + parser.state.current.addDependency(dep); + return true; + }); + + // require // + const processRequireItem = (expr, param) => { + if (param.isString()) { + const dep = new CommonJsRequireDependency(param.string, param.range); + dep.loc = expr.loc; + dep.optional = !!parser.scope.inTry; + parser.state.current.addDependency(dep); + return true; + } + }; + const processRequireContext = (expr, param) => { + const dep = ContextDependencyHelpers.create( + CommonJsRequireContextDependency, + expr.range, + param, + expr, + options, + { + category: "commonjs" + }, + parser + ); + if (!dep) return; + dep.loc = expr.loc; + dep.optional = !!parser.scope.inTry; + parser.state.current.addDependency(dep); + return true; + }; + const createRequireHandler = callNew => expr => { + if (options.commonjsMagicComments) { + const { options: requireOptions, errors: commentErrors } = + parser.parseCommentOptions(expr.range); + + if (commentErrors) { + for (const e of commentErrors) { + const { comment } = e; + parser.state.module.addWarning( + new CommentCompilationWarning( + `Compilation error while processing magic comment(-s): /*${comment.value}*/: ${e.message}`, + comment.loc + ) + ); } - for (const [key, value] of fragment.exportMap) { - if (!exportMap.has(key)) exportMap.set(key, value); + } + if (requireOptions) { + if (requireOptions.webpackIgnore !== undefined) { + if (typeof requireOptions.webpackIgnore !== "boolean") { + parser.state.module.addWarning( + new UnsupportedFeatureWarning( + `\`webpackIgnore\` expected a boolean, but received: ${requireOptions.webpackIgnore}.`, + expr.loc + ) + ); + } else { + // Do not instrument `require()` if `webpackIgnore` is `true` + if (requireOptions.webpackIgnore) { + return true; + } + } } } } - if (fragment.unusedExports.size !== 0) { - if (unusedExports === undefined) { - unusedExports = fragment.unusedExports; - unusedExportsOwned = false; - } else { - if (!unusedExportsOwned) { - unusedExports = new Set(unusedExports); - unusedExportsOwned = true; - } - for (const value of fragment.unusedExports) { - unusedExports.add(value); + + if (expr.arguments.length !== 1) return; + let localModule; + const param = parser.evaluateExpression(expr.arguments[0]); + if (param.isConditional()) { + let isExpression = false; + for (const p of param.options) { + const result = processRequireItem(expr, p); + if (result === undefined) { + isExpression = true; } } + if (!isExpression) { + const dep = new RequireHeaderDependency(expr.callee.range); + dep.loc = expr.loc; + parser.state.module.addPresentationalDependency(dep); + return true; + } } - } - return new HarmonyExportInitFragment( - this.exportsArgument, - exportMap, - unusedExports - ); - } + if ( + param.isString() && + (localModule = getLocalModule(parser.state, param.string)) + ) { + localModule.flagUsed(); + const dep = new LocalModuleDependency(localModule, expr.range, callNew); + dep.loc = expr.loc; + parser.state.module.addPresentationalDependency(dep); + return true; + } else { + const result = processRequireItem(expr, param); + if (result === undefined) { + processRequireContext(expr, param); + } else { + const dep = new RequireHeaderDependency(expr.callee.range); + dep.loc = expr.loc; + parser.state.module.addPresentationalDependency(dep); + } + return true; + } + }; + parser.hooks.call + .for("require") + .tap("CommonJsImportsParserPlugin", createRequireHandler(false)); + parser.hooks.new + .for("require") + .tap("CommonJsImportsParserPlugin", createRequireHandler(true)); + parser.hooks.call + .for("module.require") + .tap("CommonJsImportsParserPlugin", createRequireHandler(false)); + parser.hooks.new + .for("module.require") + .tap("CommonJsImportsParserPlugin", createRequireHandler(true)); - merge(other) { - let exportMap; - if (this.exportMap.size === 0) { - exportMap = other.exportMap; - } else if (other.exportMap.size === 0) { - exportMap = this.exportMap; - } else { - exportMap = new Map(other.exportMap); - for (const [key, value] of this.exportMap) { - if (!exportMap.has(key)) exportMap.set(key, value); + // require with property access // + const chainHandler = (expr, calleeMembers, callExpr, members) => { + if (callExpr.arguments.length !== 1) return; + const param = parser.evaluateExpression(callExpr.arguments[0]); + if (param.isString() && !getLocalModule(parser.state, param.string)) { + const dep = new CommonJsFullRequireDependency( + param.string, + expr.range, + members + ); + dep.asiSafe = !parser.isAsiPosition(expr.range[0]); + dep.optional = !!parser.scope.inTry; + dep.loc = expr.loc; + parser.state.current.addDependency(dep); + return true; } - } - let unusedExports; - if (this.unusedExports.size === 0) { - unusedExports = other.unusedExports; - } else if (other.unusedExports.size === 0) { - unusedExports = this.unusedExports; - } else { - unusedExports = new Set(other.unusedExports); - for (const value of this.unusedExports) { - unusedExports.add(value); + }; + const callChainHandler = (expr, calleeMembers, callExpr, members) => { + if (callExpr.arguments.length !== 1) return; + const param = parser.evaluateExpression(callExpr.arguments[0]); + if (param.isString() && !getLocalModule(parser.state, param.string)) { + const dep = new CommonJsFullRequireDependency( + param.string, + expr.callee.range, + members + ); + dep.call = true; + dep.asiSafe = !parser.isAsiPosition(expr.range[0]); + dep.optional = !!parser.scope.inTry; + dep.loc = expr.callee.loc; + parser.state.current.addDependency(dep); + parser.walkExpressions(expr.arguments); + return true; } - } - return new HarmonyExportInitFragment( - this.exportsArgument, - exportMap, - unusedExports - ); - } - - /** - * @param {Context} context context - * @returns {string|Source} the source code that will be included as initialization code - */ - getContent({ runtimeTemplate, runtimeRequirements }) { - runtimeRequirements.add(RuntimeGlobals.exports); - runtimeRequirements.add(RuntimeGlobals.definePropertyGetters); + }; + parser.hooks.memberChainOfCallMemberChain + .for("require") + .tap("CommonJsImportsParserPlugin", chainHandler); + parser.hooks.memberChainOfCallMemberChain + .for("module.require") + .tap("CommonJsImportsParserPlugin", chainHandler); + parser.hooks.callMemberChainOfCallMemberChain + .for("require") + .tap("CommonJsImportsParserPlugin", callChainHandler); + parser.hooks.callMemberChainOfCallMemberChain + .for("module.require") + .tap("CommonJsImportsParserPlugin", callChainHandler); - const unusedPart = - this.unusedExports.size > 1 - ? `/* unused harmony exports ${joinIterableWithComma( - this.unusedExports - )} */\n` - : this.unusedExports.size > 0 - ? `/* unused harmony export ${first(this.unusedExports)} */\n` - : ""; - const definitions = []; - for (const [key, value] of this.exportMap) { - definitions.push( - `\n/* harmony export */ ${JSON.stringify( - key - )}: ${runtimeTemplate.returningFunction(value)}` + // require.resolve // + const processResolve = (expr, weak) => { + if (expr.arguments.length !== 1) return; + const param = parser.evaluateExpression(expr.arguments[0]); + if (param.isConditional()) { + for (const option of param.options) { + const result = processResolveItem(expr, option, weak); + if (result === undefined) { + processResolveContext(expr, option, weak); + } + } + const dep = new RequireResolveHeaderDependency(expr.callee.range); + dep.loc = expr.loc; + parser.state.module.addPresentationalDependency(dep); + return true; + } else { + const result = processResolveItem(expr, param, weak); + if (result === undefined) { + processResolveContext(expr, param, weak); + } + const dep = new RequireResolveHeaderDependency(expr.callee.range); + dep.loc = expr.loc; + parser.state.module.addPresentationalDependency(dep); + return true; + } + }; + const processResolveItem = (expr, param, weak) => { + if (param.isString()) { + const dep = new RequireResolveDependency(param.string, param.range); + dep.loc = expr.loc; + dep.optional = !!parser.scope.inTry; + dep.weak = weak; + parser.state.current.addDependency(dep); + return true; + } + }; + const processResolveContext = (expr, param, weak) => { + const dep = ContextDependencyHelpers.create( + RequireResolveContextDependency, + param.range, + param, + expr, + options, + { + category: "commonjs", + mode: weak ? "weak" : "sync" + }, + parser ); - } - const definePart = - this.exportMap.size > 0 - ? `/* harmony export */ ${RuntimeGlobals.definePropertyGetters}(${ - this.exportsArgument - }, {${definitions.join(",")}\n/* harmony export */ });\n` - : ""; - return `${definePart}${unusedPart}`; + if (!dep) return; + dep.loc = expr.loc; + dep.optional = !!parser.scope.inTry; + parser.state.current.addDependency(dep); + return true; + }; + + parser.hooks.call + .for("require.resolve") + .tap("RequireResolveDependencyParserPlugin", expr => { + return processResolve(expr, false); + }); + parser.hooks.call + .for("require.resolveWeak") + .tap("RequireResolveDependencyParserPlugin", expr => { + return processResolve(expr, true); + }); } } - -module.exports = HarmonyExportInitFragment; +module.exports = CommonJsImportsParserPlugin; /***/ }), -/***/ 59042: +/***/ 8615: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; @@ -80331,530 +78158,389 @@ module.exports = HarmonyExportInitFragment; -const makeSerializable = __webpack_require__(26522); -const HarmonyExportInitFragment = __webpack_require__(68664); -const NullDependency = __webpack_require__(65845); - -/** @typedef {import("webpack-sources").ReplaceSource} ReplaceSource */ -/** @typedef {import("../Dependency")} Dependency */ -/** @typedef {import("../Dependency").ExportsSpec} ExportsSpec */ -/** @typedef {import("../DependencyTemplate").DependencyTemplateContext} DependencyTemplateContext */ -/** @typedef {import("../ModuleGraph")} ModuleGraph */ -/** @typedef {import("../ModuleGraphConnection").ConnectionState} ConnectionState */ - -class HarmonyExportSpecifierDependency extends NullDependency { - constructor(id, name) { - super(); - this.id = id; - this.name = name; - } - - get type() { - return "harmony export specifier"; - } - - /** - * Returns the exported names - * @param {ModuleGraph} moduleGraph module graph - * @returns {ExportsSpec | undefined} export names - */ - getExports(moduleGraph) { - return { - exports: [this.name], - priority: 1, - terminalBinding: true, - dependencies: undefined - }; - } - - /** - * @param {ModuleGraph} moduleGraph the module graph - * @returns {ConnectionState} how this dependency connects the module to referencing modules - */ - getModuleEvaluationSideEffectsState(moduleGraph) { - return false; - } +const RuntimeGlobals = __webpack_require__(49404); +const RuntimeModule = __webpack_require__(61439); +const SelfModuleFactory = __webpack_require__(31374); +const Template = __webpack_require__(92066); +const CommonJsExportsDependency = __webpack_require__(9585); +const CommonJsFullRequireDependency = __webpack_require__(29496); +const CommonJsRequireContextDependency = __webpack_require__(84175); +const CommonJsRequireDependency = __webpack_require__(38604); +const CommonJsSelfReferenceDependency = __webpack_require__(69217); +const ModuleDecoratorDependency = __webpack_require__(58969); +const RequireHeaderDependency = __webpack_require__(57010); +const RequireResolveContextDependency = __webpack_require__(48789); +const RequireResolveDependency = __webpack_require__(93172); +const RequireResolveHeaderDependency = __webpack_require__(24128); +const RuntimeRequirementsDependency = __webpack_require__(75941); - serialize(context) { - const { write } = context; - write(this.id); - write(this.name); - super.serialize(context); - } +const CommonJsExportsParserPlugin = __webpack_require__(49577); +const CommonJsImportsParserPlugin = __webpack_require__(78321); - deserialize(context) { - const { read } = context; - this.id = read(); - this.name = read(); - super.deserialize(context); - } -} +const { + evaluateToIdentifier, + toConstantDependency +} = __webpack_require__(28723); +const CommonJsExportRequireDependency = __webpack_require__(76922); -makeSerializable( - HarmonyExportSpecifierDependency, - "webpack/lib/dependencies/HarmonyExportSpecifierDependency" -); +class CommonJsPlugin { + apply(compiler) { + compiler.hooks.compilation.tap( + "CommonJsPlugin", + (compilation, { contextModuleFactory, normalModuleFactory }) => { + compilation.dependencyFactories.set( + CommonJsRequireDependency, + normalModuleFactory + ); + compilation.dependencyTemplates.set( + CommonJsRequireDependency, + new CommonJsRequireDependency.Template() + ); -HarmonyExportSpecifierDependency.Template = class HarmonyExportSpecifierDependencyTemplate extends ( - NullDependency.Template -) { - /** - * @param {Dependency} dependency the dependency for which the template should be applied - * @param {ReplaceSource} source the current replace source which can be modified - * @param {DependencyTemplateContext} templateContext the context object - * @returns {void} - */ - apply( - dependency, - source, - { module, moduleGraph, initFragments, runtime, concatenationScope } - ) { - const dep = /** @type {HarmonyExportSpecifierDependency} */ (dependency); - if (concatenationScope) { - concatenationScope.registerExport(dep.name, dep.id); - return; - } - const used = moduleGraph - .getExportsInfo(module) - .getUsedName(dep.name, runtime); - if (!used) { - const set = new Set(); - set.add(dep.name || "namespace"); - initFragments.push( - new HarmonyExportInitFragment(module.exportsArgument, undefined, set) - ); - return; - } + compilation.dependencyFactories.set( + CommonJsFullRequireDependency, + normalModuleFactory + ); + compilation.dependencyTemplates.set( + CommonJsFullRequireDependency, + new CommonJsFullRequireDependency.Template() + ); - const map = new Map(); - map.set(used, `/* binding */ ${dep.id}`); - initFragments.push( - new HarmonyExportInitFragment(module.exportsArgument, map, undefined) - ); - } -}; + compilation.dependencyFactories.set( + CommonJsRequireContextDependency, + contextModuleFactory + ); + compilation.dependencyTemplates.set( + CommonJsRequireContextDependency, + new CommonJsRequireContextDependency.Template() + ); -module.exports = HarmonyExportSpecifierDependency; + compilation.dependencyFactories.set( + RequireResolveDependency, + normalModuleFactory + ); + compilation.dependencyTemplates.set( + RequireResolveDependency, + new RequireResolveDependency.Template() + ); + compilation.dependencyFactories.set( + RequireResolveContextDependency, + contextModuleFactory + ); + compilation.dependencyTemplates.set( + RequireResolveContextDependency, + new RequireResolveContextDependency.Template() + ); -/***/ }), + compilation.dependencyTemplates.set( + RequireResolveHeaderDependency, + new RequireResolveHeaderDependency.Template() + ); -/***/ 37637: -/***/ (function(__unused_webpack_module, exports) { + compilation.dependencyTemplates.set( + RequireHeaderDependency, + new RequireHeaderDependency.Template() + ); -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ + compilation.dependencyTemplates.set( + CommonJsExportsDependency, + new CommonJsExportsDependency.Template() + ); + compilation.dependencyFactories.set( + CommonJsExportRequireDependency, + normalModuleFactory + ); + compilation.dependencyTemplates.set( + CommonJsExportRequireDependency, + new CommonJsExportRequireDependency.Template() + ); + const selfFactory = new SelfModuleFactory(compilation.moduleGraph); -/** @typedef {import("../Parser").ParserState} ParserState */ + compilation.dependencyFactories.set( + CommonJsSelfReferenceDependency, + selfFactory + ); + compilation.dependencyTemplates.set( + CommonJsSelfReferenceDependency, + new CommonJsSelfReferenceDependency.Template() + ); -/** @type {WeakMap} */ -const parserStateExportsState = new WeakMap(); + compilation.dependencyFactories.set( + ModuleDecoratorDependency, + selfFactory + ); + compilation.dependencyTemplates.set( + ModuleDecoratorDependency, + new ModuleDecoratorDependency.Template() + ); -/** - * @param {ParserState} parserState parser state - * @param {boolean} isStrictHarmony strict harmony mode should be enabled - * @returns {void} - */ -exports.enable = (parserState, isStrictHarmony) => { - const value = parserStateExportsState.get(parserState); - if (value === false) return; - parserStateExportsState.set(parserState, true); - if (value !== true) { - parserState.module.buildMeta.exportsType = "namespace"; - parserState.module.buildInfo.strict = true; - parserState.module.buildInfo.exportsArgument = "__webpack_exports__"; - if (isStrictHarmony) { - parserState.module.buildMeta.strictHarmonyModule = true; - parserState.module.buildInfo.moduleArgument = "__webpack_module__"; - } - } -}; + compilation.hooks.runtimeRequirementInModule + .for(RuntimeGlobals.harmonyModuleDecorator) + .tap("CommonJsPlugin", (module, set) => { + set.add(RuntimeGlobals.module); + set.add(RuntimeGlobals.requireScope); + }); -/** - * @param {ParserState} parserState parser state - * @returns {boolean} true, when enabled - */ -exports.isEnabled = parserState => { - const value = parserStateExportsState.get(parserState); - return value === true; -}; + compilation.hooks.runtimeRequirementInModule + .for(RuntimeGlobals.nodeModuleDecorator) + .tap("CommonJsPlugin", (module, set) => { + set.add(RuntimeGlobals.module); + set.add(RuntimeGlobals.requireScope); + }); + compilation.hooks.runtimeRequirementInTree + .for(RuntimeGlobals.harmonyModuleDecorator) + .tap("CommonJsPlugin", (chunk, set) => { + compilation.addRuntimeModule( + chunk, + new HarmonyModuleDecoratorRuntimeModule() + ); + }); -/***/ }), + compilation.hooks.runtimeRequirementInTree + .for(RuntimeGlobals.nodeModuleDecorator) + .tap("CommonJsPlugin", (chunk, set) => { + compilation.addRuntimeModule( + chunk, + new NodeModuleDecoratorRuntimeModule() + ); + }); -/***/ 19577: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + const handler = (parser, parserOptions) => { + if (parserOptions.commonjs !== undefined && !parserOptions.commonjs) + return; + parser.hooks.typeof + .for("module") + .tap( + "CommonJsPlugin", + toConstantDependency(parser, JSON.stringify("object")) + ); -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ + parser.hooks.expression + .for("require.main") + .tap( + "CommonJsPlugin", + toConstantDependency( + parser, + `${RuntimeGlobals.moduleCache}[${RuntimeGlobals.entryModuleId}]`, + [RuntimeGlobals.moduleCache, RuntimeGlobals.entryModuleId] + ) + ); + parser.hooks.expression + .for("module.loaded") + .tap("CommonJsPlugin", expr => { + parser.state.module.buildInfo.moduleConcatenationBailout = + "module.loaded"; + const dep = new RuntimeRequirementsDependency([ + RuntimeGlobals.moduleLoaded + ]); + dep.loc = expr.loc; + parser.state.module.addPresentationalDependency(dep); + return true; + }); + parser.hooks.expression + .for("module.id") + .tap("CommonJsPlugin", expr => { + parser.state.module.buildInfo.moduleConcatenationBailout = + "module.id"; + const dep = new RuntimeRequirementsDependency([ + RuntimeGlobals.moduleId + ]); + dep.loc = expr.loc; + parser.state.module.addPresentationalDependency(dep); + return true; + }); + parser.hooks.evaluateIdentifier.for("module.hot").tap( + "CommonJsPlugin", + evaluateToIdentifier("module.hot", "module", () => ["hot"], null) + ); -const ConditionalInitFragment = __webpack_require__(90921); -const Dependency = __webpack_require__(50384); -const HarmonyLinkingError = __webpack_require__(42766); -const InitFragment = __webpack_require__(51739); -const Template = __webpack_require__(92066); -const AwaitDependenciesInitFragment = __webpack_require__(20911); -const { filterRuntime, mergeRuntime } = __webpack_require__(19655); -const ModuleDependency = __webpack_require__(80944); + new CommonJsImportsParserPlugin(parserOptions).apply(parser); + new CommonJsExportsParserPlugin(compilation.moduleGraph).apply( + parser + ); + }; -/** @typedef {import("webpack-sources").ReplaceSource} ReplaceSource */ -/** @typedef {import("webpack-sources").Source} Source */ -/** @typedef {import("../ChunkGraph")} ChunkGraph */ -/** @typedef {import("../Dependency").ReferencedExport} ReferencedExport */ -/** @typedef {import("../Dependency").UpdateHashContext} UpdateHashContext */ -/** @typedef {import("../DependencyTemplate").DependencyTemplateContext} DependencyTemplateContext */ -/** @typedef {import("../Module")} Module */ -/** @typedef {import("../ModuleGraph")} ModuleGraph */ -/** @typedef {import("../RuntimeTemplate")} RuntimeTemplate */ -/** @typedef {import("../WebpackError")} WebpackError */ -/** @typedef {import("../util/Hash")} Hash */ -/** @typedef {import("../util/runtime").RuntimeSpec} RuntimeSpec */ + normalModuleFactory.hooks.parser + .for("javascript/auto") + .tap("CommonJsPlugin", handler); + normalModuleFactory.hooks.parser + .for("javascript/dynamic") + .tap("CommonJsPlugin", handler); + } + ); + } +} -const ExportPresenceModes = { - NONE: /** @type {0} */ (0), - WARN: /** @type {1} */ (1), - AUTO: /** @type {2} */ (2), - ERROR: /** @type {3} */ (3), - fromUserOption(str) { - switch (str) { - case "error": - return ExportPresenceModes.ERROR; - case "warn": - return ExportPresenceModes.WARN; - case "auto": - return ExportPresenceModes.AUTO; - case false: - return ExportPresenceModes.NONE; - default: - throw new Error(`Invalid export presence value ${str}`); - } +class HarmonyModuleDecoratorRuntimeModule extends RuntimeModule { + constructor() { + super("harmony module decorator"); } -}; -class HarmonyImportDependency extends ModuleDependency { /** - * - * @param {string} request request string - * @param {number} sourceOrder source order - * @param {Record=} assertions import assertions + * @returns {string} runtime code */ - constructor(request, sourceOrder, assertions) { - super(request); - this.sourceOrder = sourceOrder; - this.assertions = assertions; + generate() { + const { runtimeTemplate } = this.compilation; + return Template.asString([ + `${ + RuntimeGlobals.harmonyModuleDecorator + } = ${runtimeTemplate.basicFunction("module", [ + "module = Object.create(module);", + "if (!module.children) module.children = [];", + "Object.defineProperty(module, 'exports', {", + Template.indent([ + "enumerable: true,", + `set: ${runtimeTemplate.basicFunction("", [ + "throw new Error('ES Modules may not assign module.exports or exports.*, Use ESM export syntax, instead: ' + module.id);" + ])}` + ]), + "});", + "return module;" + ])};` + ]); } +} - get category() { - return "esm"; +class NodeModuleDecoratorRuntimeModule extends RuntimeModule { + constructor() { + super("node module decorator"); } /** - * Returns list of exports referenced by this dependency - * @param {ModuleGraph} moduleGraph module graph - * @param {RuntimeSpec} runtime the runtime for which the module is analysed - * @returns {(string[] | ReferencedExport)[]} referenced exports + * @returns {string} runtime code */ - getReferencedExports(moduleGraph, runtime) { - return Dependency.NO_EXPORTS_REFERENCED; + generate() { + const { runtimeTemplate } = this.compilation; + return Template.asString([ + `${RuntimeGlobals.nodeModuleDecorator} = ${runtimeTemplate.basicFunction( + "module", + [ + "module.paths = [];", + "if (!module.children) module.children = [];", + "return module;" + ] + )};` + ]); } +} - /** - * @param {ModuleGraph} moduleGraph the module graph - * @returns {string} name of the variable for the import - */ - getImportVar(moduleGraph) { - const module = moduleGraph.getParentModule(this); - const meta = moduleGraph.getMeta(module); - let importVarMap = meta.importVarMap; - if (!importVarMap) meta.importVarMap = importVarMap = new Map(); - let importVar = importVarMap.get(moduleGraph.getModule(this)); - if (importVar) return importVar; - importVar = `${Template.toIdentifier( - `${this.userRequest}` - )}__WEBPACK_IMPORTED_MODULE_${importVarMap.size}__`; - importVarMap.set(moduleGraph.getModule(this), importVar); - return importVar; - } +module.exports = CommonJsPlugin; - /** - * @param {boolean} update create new variables or update existing one - * @param {DependencyTemplateContext} templateContext the template context - * @returns {[string, string]} the import statement and the compat statement - */ - getImportStatement( - update, - { runtimeTemplate, module, moduleGraph, chunkGraph, runtimeRequirements } - ) { - return runtimeTemplate.importStatement({ - update, - module: moduleGraph.getModule(this), - chunkGraph, - importVar: this.getImportVar(moduleGraph), - request: this.request, - originModule: module, - runtimeRequirements - }); - } - /** - * @param {ModuleGraph} moduleGraph module graph - * @param {string[]} ids imported ids - * @param {string} additionalMessage extra info included in the error message - * @returns {WebpackError[] | undefined} errors - */ - getLinkingErrors(moduleGraph, ids, additionalMessage) { - const importedModule = moduleGraph.getModule(this); - // ignore errors for missing or failed modules - if (!importedModule || importedModule.getNumberOfErrors() > 0) { - return; - } +/***/ }), - const parentModule = moduleGraph.getParentModule(this); - const exportsType = importedModule.getExportsType( - moduleGraph, - parentModule.buildMeta.strictHarmonyModule - ); - if (exportsType === "namespace" || exportsType === "default-with-named") { - if (ids.length === 0) { - return; - } +/***/ 84175: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ + + + +const makeSerializable = __webpack_require__(26522); +const ContextDependency = __webpack_require__(67840); +const ContextDependencyTemplateAsRequireCall = __webpack_require__(18259); - if ( - (exportsType !== "default-with-named" || ids[0] !== "default") && - moduleGraph.isExportProvided(importedModule, ids) === false - ) { - // We are sure that it's not provided +class CommonJsRequireContextDependency extends ContextDependency { + constructor(options, range, valueRange, inShorthand) { + super(options); - // Try to provide detailed info in the error message - let pos = 0; - let exportsInfo = moduleGraph.getExportsInfo(importedModule); - while (pos < ids.length && exportsInfo) { - const id = ids[pos++]; - const exportInfo = exportsInfo.getReadOnlyExportInfo(id); - if (exportInfo.provided === false) { - // We are sure that it's not provided - const providedExports = exportsInfo.getProvidedExports(); - const moreInfo = !Array.isArray(providedExports) - ? " (possible exports unknown)" - : providedExports.length === 0 - ? " (module has no exports)" - : ` (possible exports: ${providedExports.join(", ")})`; - return [ - new HarmonyLinkingError( - `export ${ids - .slice(0, pos) - .map(id => `'${id}'`) - .join(".")} ${additionalMessage} was not found in '${ - this.userRequest - }'${moreInfo}` - ) - ]; - } - exportsInfo = exportInfo.getNestedExportsInfo(); - } + this.range = range; + this.valueRange = valueRange; + // inShorthand must be serialized by subclasses that use it + this.inShorthand = inShorthand; + } - // General error message - return [ - new HarmonyLinkingError( - `export ${ids - .map(id => `'${id}'`) - .join(".")} ${additionalMessage} was not found in '${ - this.userRequest - }'` - ) - ]; - } - } - switch (exportsType) { - case "default-only": - // It's has only a default export - if (ids.length > 0 && ids[0] !== "default") { - // In strict harmony modules we only support the default export - return [ - new HarmonyLinkingError( - `Can't import the named export ${ids - .map(id => `'${id}'`) - .join( - "." - )} ${additionalMessage} from default-exporting module (only default export is available)` - ) - ]; - } - break; - case "default-with-named": - // It has a default export and named properties redirect - // In some cases we still want to warn here - if ( - ids.length > 0 && - ids[0] !== "default" && - importedModule.buildMeta.defaultObject === "redirect-warn" - ) { - // For these modules only the default export is supported - return [ - new HarmonyLinkingError( - `Should not import the named export ${ids - .map(id => `'${id}'`) - .join( - "." - )} ${additionalMessage} from default-exporting module (only default export is available soon)` - ) - ]; - } - break; - } + get type() { + return "cjs require context"; } serialize(context) { const { write } = context; - write(this.sourceOrder); - write(this.assertions); + + write(this.range); + write(this.valueRange); + write(this.inShorthand); + super.serialize(context); } deserialize(context) { const { read } = context; - this.sourceOrder = read(); - this.assertions = read(); + + this.range = read(); + this.valueRange = read(); + this.inShorthand = read(); + super.deserialize(context); } } -module.exports = HarmonyImportDependency; +makeSerializable( + CommonJsRequireContextDependency, + "webpack/lib/dependencies/CommonJsRequireContextDependency" +); -/** @type {WeakMap>} */ -const importEmittedMap = new WeakMap(); +CommonJsRequireContextDependency.Template = + ContextDependencyTemplateAsRequireCall; -HarmonyImportDependency.Template = class HarmonyImportDependencyTemplate extends ( - ModuleDependency.Template -) { - /** - * @param {Dependency} dependency the dependency for which the template should be applied - * @param {ReplaceSource} source the current replace source which can be modified - * @param {DependencyTemplateContext} templateContext the context object - * @returns {void} - */ - apply(dependency, source, templateContext) { - const dep = /** @type {HarmonyImportDependency} */ (dependency); - const { module, chunkGraph, moduleGraph, runtime } = templateContext; +module.exports = CommonJsRequireContextDependency; - const connection = moduleGraph.getConnection(dep); - if (connection && !connection.isTargetActive(runtime)) return; - const referencedModule = connection && connection.module; +/***/ }), - if ( - connection && - connection.weak && - referencedModule && - chunkGraph.getModuleId(referencedModule) === null - ) { - // in weak references, module might not be in any chunk - // but that's ok, we don't need that logic in this case - return; - } +/***/ 38604: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - const moduleKey = referencedModule - ? referencedModule.identifier() - : dep.request; - const key = `harmony import ${moduleKey}`; +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ - const runtimeCondition = dep.weak - ? false - : connection - ? filterRuntime(runtime, r => connection.isTargetActive(r)) - : true; - if (module && referencedModule) { - let emittedModules = importEmittedMap.get(module); - if (emittedModules === undefined) { - emittedModules = new WeakMap(); - importEmittedMap.set(module, emittedModules); - } - let mergedRuntimeCondition = runtimeCondition; - const oldRuntimeCondition = emittedModules.get(referencedModule) || false; - if (oldRuntimeCondition !== false && mergedRuntimeCondition !== true) { - if (mergedRuntimeCondition === false || oldRuntimeCondition === true) { - mergedRuntimeCondition = oldRuntimeCondition; - } else { - mergedRuntimeCondition = mergeRuntime( - oldRuntimeCondition, - mergedRuntimeCondition - ); - } - } - emittedModules.set(referencedModule, mergedRuntimeCondition); - } - const importStatement = dep.getImportStatement(false, templateContext); - if ( - referencedModule && - templateContext.moduleGraph.isAsync(referencedModule) - ) { - templateContext.initFragments.push( - new ConditionalInitFragment( - importStatement[0], - InitFragment.STAGE_HARMONY_IMPORTS, - dep.sourceOrder, - key, - runtimeCondition - ) - ); - templateContext.initFragments.push( - new AwaitDependenciesInitFragment( - new Set([dep.getImportVar(templateContext.moduleGraph)]) - ) - ); - templateContext.initFragments.push( - new ConditionalInitFragment( - importStatement[1], - InitFragment.STAGE_ASYNC_HARMONY_IMPORTS, - dep.sourceOrder, - key + " compat", - runtimeCondition - ) - ); - } else { - templateContext.initFragments.push( - new ConditionalInitFragment( - importStatement[0] + importStatement[1], - InitFragment.STAGE_HARMONY_IMPORTS, - dep.sourceOrder, - key, - runtimeCondition - ) - ); - } +const makeSerializable = __webpack_require__(26522); +const ModuleDependency = __webpack_require__(80944); +const ModuleDependencyTemplateAsId = __webpack_require__(35795); + +class CommonJsRequireDependency extends ModuleDependency { + constructor(request, range) { + super(request); + this.range = range; } - /** - * - * @param {Module} module the module - * @param {Module} referencedModule the referenced module - * @returns {RuntimeSpec | boolean} runtimeCondition in which this import has been emitted - */ - static getImportEmittedRuntime(module, referencedModule) { - const emittedModules = importEmittedMap.get(module); - if (emittedModules === undefined) return false; - return emittedModules.get(referencedModule) || false; + get type() { + return "cjs require"; } -}; -module.exports.ExportPresenceModes = ExportPresenceModes; + get category() { + return "commonjs"; + } +} + +CommonJsRequireDependency.Template = ModuleDependencyTemplateAsId; + +makeSerializable( + CommonJsRequireDependency, + "webpack/lib/dependencies/CommonJsRequireDependency" +); + +module.exports = CommonJsRequireDependency; /***/ }), -/***/ 76581: +/***/ 69217: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; @@ -80865,260 +78551,145 @@ module.exports.ExportPresenceModes = ExportPresenceModes; -const HotModuleReplacementPlugin = __webpack_require__(616); -const InnerGraph = __webpack_require__(92886); -const ConstDependency = __webpack_require__(60864); -const HarmonyAcceptDependency = __webpack_require__(38421); -const HarmonyAcceptImportDependency = __webpack_require__(35316); -const HarmonyExports = __webpack_require__(37637); -const { ExportPresenceModes } = __webpack_require__(19577); -const HarmonyImportSideEffectDependency = __webpack_require__(76853); -const HarmonyImportSpecifierDependency = __webpack_require__(61994); - -/** @typedef {import("estree").ExportAllDeclaration} ExportAllDeclaration */ -/** @typedef {import("estree").ExportNamedDeclaration} ExportNamedDeclaration */ -/** @typedef {import("estree").Identifier} Identifier */ -/** @typedef {import("estree").ImportDeclaration} ImportDeclaration */ -/** @typedef {import("estree").ImportExpression} ImportExpression */ -/** @typedef {import("../../declarations/WebpackOptions").JavascriptParserOptions} JavascriptParserOptions */ -/** @typedef {import("../javascript/JavascriptParser")} JavascriptParser */ -/** @typedef {import("../optimize/InnerGraph").InnerGraph} InnerGraph */ -/** @typedef {import("../optimize/InnerGraph").TopLevelSymbol} TopLevelSymbol */ -/** @typedef {import("./HarmonyImportDependency")} HarmonyImportDependency */ - -const harmonySpecifierTag = Symbol("harmony import"); - -/** - * @typedef {Object} HarmonySettings - * @property {string[]} ids - * @property {string} source - * @property {number} sourceOrder - * @property {string} name - * @property {boolean} await - * @property {Record | undefined} assertions - */ - -/** - * @param {ImportDeclaration | ExportNamedDeclaration | ExportAllDeclaration | ImportExpression} node node with assertions - * @returns {Record | undefined} assertions - */ -function getAssertions(node) { - // TODO remove cast when @types/estree has been updated to import assertions - const assertions = /** @type {{ assertions?: ImportAttributeNode[] }} */ ( - node - ).assertions; - if (assertions === undefined) { - return undefined; - } - const result = {}; - for (const assertion of assertions) { - const key = - assertion.key.type === "Identifier" - ? assertion.key.name - : assertion.key.value; - result[key] = assertion.value.value; - } - return result; -} +const RuntimeGlobals = __webpack_require__(49404); +const { equals } = __webpack_require__(21537); +const makeSerializable = __webpack_require__(26522); +const propertyAccess = __webpack_require__(86709); +const NullDependency = __webpack_require__(65845); -module.exports = class HarmonyImportDependencyParserPlugin { - /** - * @param {JavascriptParserOptions} options options - */ - constructor(options) { - this.exportPresenceMode = - options.importExportsPresence !== undefined - ? ExportPresenceModes.fromUserOption(options.importExportsPresence) - : options.exportsPresence !== undefined - ? ExportPresenceModes.fromUserOption(options.exportsPresence) - : options.strictExportPresence - ? ExportPresenceModes.ERROR - : ExportPresenceModes.AUTO; - this.strictThisContextOnImports = options.strictThisContextOnImports; - } +/** @typedef {import("webpack-sources").ReplaceSource} ReplaceSource */ +/** @typedef {import("../Dependency")} Dependency */ +/** @typedef {import("../Dependency").ExportsSpec} ExportsSpec */ +/** @typedef {import("../Dependency").ReferencedExport} ReferencedExport */ +/** @typedef {import("../DependencyTemplate").DependencyTemplateContext} DependencyTemplateContext */ +/** @typedef {import("../ModuleGraph")} ModuleGraph */ +/** @typedef {import("../util/runtime").RuntimeSpec} RuntimeSpec */ - /** - * @param {JavascriptParser} parser the parser - * @returns {void} - */ - apply(parser) { - const { exportPresenceMode } = this; - parser.hooks.isPure - .for("Identifier") - .tap("HarmonyImportDependencyParserPlugin", expression => { - const expr = /** @type {Identifier} */ (expression); - if ( - parser.isVariableDefined(expr.name) || - parser.getTagData(expr.name, harmonySpecifierTag) - ) { - return true; - } - }); - parser.hooks.import.tap( - "HarmonyImportDependencyParserPlugin", - (statement, source) => { - parser.state.lastHarmonyImportOrder = - (parser.state.lastHarmonyImportOrder || 0) + 1; - const clearDep = new ConstDependency( - parser.isAsiPosition(statement.range[0]) ? ";" : "", - statement.range - ); - clearDep.loc = statement.loc; - parser.state.module.addPresentationalDependency(clearDep); - parser.unsetAsiPosition(statement.range[1]); - const assertions = getAssertions(statement); - const sideEffectDep = new HarmonyImportSideEffectDependency( - source, - parser.state.lastHarmonyImportOrder, - assertions - ); - sideEffectDep.loc = statement.loc; - parser.state.module.addDependency(sideEffectDep); - return true; - } - ); - parser.hooks.importSpecifier.tap( - "HarmonyImportDependencyParserPlugin", - (statement, source, id, name) => { - const ids = id === null ? [] : [id]; - parser.tagVariable(name, harmonySpecifierTag, { - name, - source, - ids, - sourceOrder: parser.state.lastHarmonyImportOrder, - assertions: getAssertions(statement) - }); - return true; - } - ); - parser.hooks.expression - .for(harmonySpecifierTag) - .tap("HarmonyImportDependencyParserPlugin", expr => { - const settings = /** @type {HarmonySettings} */ (parser.currentTagData); - const dep = new HarmonyImportSpecifierDependency( - settings.source, - settings.sourceOrder, - settings.ids, - settings.name, - expr.range, - exportPresenceMode, - settings.assertions - ); - dep.shorthand = parser.scope.inShorthand; - dep.directImport = true; - dep.asiSafe = !parser.isAsiPosition(expr.range[0]); - dep.loc = expr.loc; - parser.state.module.addDependency(dep); - InnerGraph.onUsage(parser.state, e => (dep.usedByExports = e)); - return true; - }); - parser.hooks.expressionMemberChain - .for(harmonySpecifierTag) - .tap("HarmonyImportDependencyParserPlugin", (expr, members) => { - const settings = /** @type {HarmonySettings} */ (parser.currentTagData); - const ids = settings.ids.concat(members); - const dep = new HarmonyImportSpecifierDependency( - settings.source, - settings.sourceOrder, - ids, - settings.name, - expr.range, - exportPresenceMode, - settings.assertions - ); - dep.asiSafe = !parser.isAsiPosition(expr.range[0]); - dep.loc = expr.loc; - parser.state.module.addDependency(dep); - InnerGraph.onUsage(parser.state, e => (dep.usedByExports = e)); - return true; - }); - parser.hooks.callMemberChain - .for(harmonySpecifierTag) - .tap("HarmonyImportDependencyParserPlugin", (expr, members) => { - const { arguments: args, callee } = expr; - const settings = /** @type {HarmonySettings} */ (parser.currentTagData); - const ids = settings.ids.concat(members); - const dep = new HarmonyImportSpecifierDependency( - settings.source, - settings.sourceOrder, - ids, - settings.name, - callee.range, - exportPresenceMode, - settings.assertions - ); - dep.directImport = members.length === 0; - dep.call = true; - dep.asiSafe = !parser.isAsiPosition(callee.range[0]); - // only in case when we strictly follow the spec we need a special case here - dep.namespaceObjectAsContext = - members.length > 0 && this.strictThisContextOnImports; - dep.loc = callee.loc; - parser.state.module.addDependency(dep); - if (args) parser.walkExpressions(args); - InnerGraph.onUsage(parser.state, e => (dep.usedByExports = e)); - return true; - }); - const { hotAcceptCallback, hotAcceptWithoutCallback } = - HotModuleReplacementPlugin.getParserHooks(parser); - hotAcceptCallback.tap( - "HarmonyImportDependencyParserPlugin", - (expr, requests) => { - if (!HarmonyExports.isEnabled(parser.state)) { - // This is not a harmony module, skip it - return; - } - const dependencies = requests.map(request => { - const dep = new HarmonyAcceptImportDependency(request); - dep.loc = expr.loc; - parser.state.module.addDependency(dep); - return dep; - }); - if (dependencies.length > 0) { - const dep = new HarmonyAcceptDependency( - expr.range, - dependencies, - true - ); - dep.loc = expr.loc; - parser.state.module.addDependency(dep); - } - } - ); - hotAcceptWithoutCallback.tap( - "HarmonyImportDependencyParserPlugin", - (expr, requests) => { - if (!HarmonyExports.isEnabled(parser.state)) { - // This is not a harmony module, skip it - return; - } - const dependencies = requests.map(request => { - const dep = new HarmonyAcceptImportDependency(request); - dep.loc = expr.loc; - parser.state.module.addDependency(dep); - return dep; - }); - if (dependencies.length > 0) { - const dep = new HarmonyAcceptDependency( - expr.range, - dependencies, - false - ); - dep.loc = expr.loc; - parser.state.module.addDependency(dep); - } - } +class CommonJsSelfReferenceDependency extends NullDependency { + constructor(range, base, names, call) { + super(); + this.range = range; + this.base = base; + this.names = names; + this.call = call; + } + + get type() { + return "cjs self exports reference"; + } + + get category() { + return "self"; + } + + /** + * @returns {string | null} an identifier to merge equal requests + */ + getResourceIdentifier() { + return `self`; + } + + /** + * Returns list of exports referenced by this dependency + * @param {ModuleGraph} moduleGraph module graph + * @param {RuntimeSpec} runtime the runtime for which the module is analysed + * @returns {(string[] | ReferencedExport)[]} referenced exports + */ + getReferencedExports(moduleGraph, runtime) { + return [this.call ? this.names.slice(0, -1) : this.names]; + } + + serialize(context) { + const { write } = context; + write(this.range); + write(this.base); + write(this.names); + write(this.call); + super.serialize(context); + } + + deserialize(context) { + const { read } = context; + this.range = read(); + this.base = read(); + this.names = read(); + this.call = read(); + super.deserialize(context); + } +} + +makeSerializable( + CommonJsSelfReferenceDependency, + "webpack/lib/dependencies/CommonJsSelfReferenceDependency" +); + +CommonJsSelfReferenceDependency.Template = class CommonJsSelfReferenceDependencyTemplate extends ( + NullDependency.Template +) { + /** + * @param {Dependency} dependency the dependency for which the template should be applied + * @param {ReplaceSource} source the current replace source which can be modified + * @param {DependencyTemplateContext} templateContext the context object + * @returns {void} + */ + apply( + dependency, + source, + { module, moduleGraph, runtime, runtimeRequirements } + ) { + const dep = /** @type {CommonJsSelfReferenceDependency} */ (dependency); + let used; + if (dep.names.length === 0) { + used = dep.names; + } else { + used = moduleGraph.getExportsInfo(module).getUsedName(dep.names, runtime); + } + if (!used) { + throw new Error( + "Self-reference dependency has unused export name: This should not happen" + ); + } + + let base = undefined; + switch (dep.base) { + case "exports": + runtimeRequirements.add(RuntimeGlobals.exports); + base = module.exportsArgument; + break; + case "module.exports": + runtimeRequirements.add(RuntimeGlobals.module); + base = `${module.moduleArgument}.exports`; + break; + case "this": + runtimeRequirements.add(RuntimeGlobals.thisAsExports); + base = "this"; + break; + default: + throw new Error(`Unsupported base ${dep.base}`); + } + + if (base === dep.base && equals(used, dep.names)) { + // Nothing has to be changed + // We don't use a replacement for compat reasons + // for plugins that update `module._source` which they + // shouldn't do! + return; + } + + source.replace( + dep.range[0], + dep.range[1] - 1, + `${base}${propertyAccess(used)}` ); } }; -module.exports.harmonySpecifierTag = harmonySpecifierTag; -module.exports.getAssertions = getAssertions; +module.exports = CommonJsSelfReferenceDependency; /***/ }), -/***/ 76853: +/***/ 60864: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; @@ -81130,38 +78701,51 @@ module.exports.getAssertions = getAssertions; const makeSerializable = __webpack_require__(26522); -const HarmonyImportDependency = __webpack_require__(19577); +const NullDependency = __webpack_require__(65845); /** @typedef {import("webpack-sources").ReplaceSource} ReplaceSource */ +/** @typedef {import("../ChunkGraph")} ChunkGraph */ /** @typedef {import("../Dependency")} Dependency */ +/** @typedef {import("../Dependency").UpdateHashContext} UpdateHashContext */ /** @typedef {import("../DependencyTemplate").DependencyTemplateContext} DependencyTemplateContext */ -/** @typedef {import("../InitFragment")} InitFragment */ -/** @typedef {import("../Module")} Module */ /** @typedef {import("../ModuleGraph")} ModuleGraph */ -/** @typedef {import("../ModuleGraphConnection")} ModuleGraphConnection */ /** @typedef {import("../ModuleGraphConnection").ConnectionState} ConnectionState */ /** @typedef {import("../util/Hash")} Hash */ -/** @typedef {import("../util/runtime").RuntimeSpec} RuntimeSpec */ - -class HarmonyImportSideEffectDependency extends HarmonyImportDependency { - constructor(request, sourceOrder, assertions) { - super(request, sourceOrder, assertions); - } - get type() { - return "harmony side effect evaluation"; +class ConstDependency extends NullDependency { + /** + * @param {string} expression the expression + * @param {number|[number, number]} range the source range + * @param {string[]=} runtimeRequirements runtime requirements + */ + constructor(expression, range, runtimeRequirements) { + super(); + this.expression = expression; + this.range = range; + this.runtimeRequirements = runtimeRequirements + ? new Set(runtimeRequirements) + : null; + this._hashUpdate = undefined; } /** - * @param {ModuleGraph} moduleGraph module graph - * @returns {null | false | function(ModuleGraphConnection, RuntimeSpec): ConnectionState} function to determine if the connection is active + * Update the hash + * @param {Hash} hash hash to be updated + * @param {UpdateHashContext} context context + * @returns {void} */ - getCondition(moduleGraph) { - return connection => { - const refModule = connection.resolvedModule; - if (!refModule) return true; - return refModule.getSideEffectsConnectionState(moduleGraph); - }; + updateHash(hash, context) { + if (this._hashUpdate === undefined) { + let hashUpdate = "" + this.range + "|" + this.expression; + if (this.runtimeRequirements) { + for (const item of this.runtimeRequirements) { + hashUpdate += "|"; + hashUpdate += item; + } + } + this._hashUpdate = hashUpdate; + } + hash.update(this._hashUpdate); } /** @@ -81169,19 +78753,30 @@ class HarmonyImportSideEffectDependency extends HarmonyImportDependency { * @returns {ConnectionState} how this dependency connects the module to referencing modules */ getModuleEvaluationSideEffectsState(moduleGraph) { - const refModule = moduleGraph.getModule(this); - if (!refModule) return true; - return refModule.getSideEffectsConnectionState(moduleGraph); + return false; + } + + serialize(context) { + const { write } = context; + write(this.expression); + write(this.range); + write(this.runtimeRequirements); + super.serialize(context); + } + + deserialize(context) { + const { read } = context; + this.expression = read(); + this.range = read(); + this.runtimeRequirements = read(); + super.deserialize(context); } } -makeSerializable( - HarmonyImportSideEffectDependency, - "webpack/lib/dependencies/HarmonyImportSideEffectDependency" -); +makeSerializable(ConstDependency, "webpack/lib/dependencies/ConstDependency"); -HarmonyImportSideEffectDependency.Template = class HarmonyImportSideEffectDependencyTemplate extends ( - HarmonyImportDependency.Template +ConstDependency.Template = class ConstDependencyTemplate extends ( + NullDependency.Template ) { /** * @param {Dependency} dependency the dependency for which the template should be applied @@ -81190,23 +78785,27 @@ HarmonyImportSideEffectDependency.Template = class HarmonyImportSideEffectDepend * @returns {void} */ apply(dependency, source, templateContext) { - const { moduleGraph, concatenationScope } = templateContext; - if (concatenationScope) { - const module = moduleGraph.getModule(dependency); - if (concatenationScope.isModuleInScope(module)) { - return; + const dep = /** @type {ConstDependency} */ (dependency); + if (dep.runtimeRequirements) { + for (const req of dep.runtimeRequirements) { + templateContext.runtimeRequirements.add(req); } } - super.apply(dependency, source, templateContext); + if (typeof dep.range === "number") { + source.insert(dep.range, dep.expression); + return; + } + + source.replace(dep.range[0], dep.range[1] - 1, dep.expression); } }; -module.exports = HarmonyImportSideEffectDependency; +module.exports = ConstDependency; /***/ }), -/***/ 61994: +/***/ 67840: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; @@ -81218,334 +78817,390 @@ module.exports = HarmonyImportSideEffectDependency; const Dependency = __webpack_require__(50384); -const { - getDependencyUsedByExportsCondition -} = __webpack_require__(92886); +const DependencyTemplate = __webpack_require__(17600); const makeSerializable = __webpack_require__(26522); -const propertyAccess = __webpack_require__(86709); -const HarmonyImportDependency = __webpack_require__(19577); +const memoize = __webpack_require__(84297); -/** @typedef {import("webpack-sources").ReplaceSource} ReplaceSource */ -/** @typedef {import("../ChunkGraph")} ChunkGraph */ -/** @typedef {import("../Dependency").ExportsSpec} ExportsSpec */ -/** @typedef {import("../Dependency").ReferencedExport} ReferencedExport */ -/** @typedef {import("../Dependency").UpdateHashContext} UpdateHashContext */ -/** @typedef {import("../DependencyTemplate").DependencyTemplateContext} DependencyTemplateContext */ +/** @typedef {import("../ContextModule").ContextOptions} ContextOptions */ +/** @typedef {import("../Dependency").TRANSITIVE} TRANSITIVE */ /** @typedef {import("../ModuleGraph")} ModuleGraph */ -/** @typedef {import("../ModuleGraphConnection")} ModuleGraphConnection */ -/** @typedef {import("../ModuleGraphConnection").ConnectionState} ConnectionState */ /** @typedef {import("../WebpackError")} WebpackError */ -/** @typedef {import("../util/Hash")} Hash */ -/** @typedef {import("../util/runtime").RuntimeSpec} RuntimeSpec */ -const idsSymbol = Symbol("HarmonyImportSpecifierDependency.ids"); +const getCriticalDependencyWarning = memoize(() => + __webpack_require__(14190) +); -const { ExportPresenceModes } = HarmonyImportDependency; +/** @typedef {ContextOptions & { request: string }} ContextDependencyOptions */ -class HarmonyImportSpecifierDependency extends HarmonyImportDependency { - constructor( - request, - sourceOrder, - ids, - name, - range, - exportPresenceMode, - assertions - ) { - super(request, sourceOrder, assertions); - this.ids = ids; - this.name = name; - this.range = range; - this.exportPresenceMode = exportPresenceMode; - this.namespaceObjectAsContext = false; - this.call = undefined; - this.directImport = undefined; - this.shorthand = undefined; - this.asiSafe = undefined; - /** @type {Set | boolean} */ - this.usedByExports = undefined; - } +const regExpToString = r => (r ? r + "" : ""); - // TODO webpack 6 remove - get id() { - throw new Error("id was renamed to ids and type changed to string[]"); - } +class ContextDependency extends Dependency { + /** + * @param {ContextDependencyOptions} options options for the context module + */ + constructor(options) { + super(); - // TODO webpack 6 remove - getId() { - throw new Error("id was renamed to ids and type changed to string[]"); - } + this.options = options; + this.userRequest = this.options && this.options.request; + /** @type {false | string} */ + this.critical = false; + this.hadGlobalOrStickyRegExp = false; - // TODO webpack 6 remove - setId() { - throw new Error("id was renamed to ids and type changed to string[]"); - } + if ( + this.options && + (this.options.regExp.global || this.options.regExp.sticky) + ) { + this.options = { ...this.options, regExp: null }; + this.hadGlobalOrStickyRegExp = true; + } - get type() { - return "harmony import specifier"; + this.request = undefined; + this.range = undefined; + this.valueRange = undefined; + this.inShorthand = undefined; + // TODO refactor this + this.replaces = undefined; } - /** - * @param {ModuleGraph} moduleGraph the module graph - * @returns {string[]} the imported ids - */ - getIds(moduleGraph) { - const meta = moduleGraph.getMetaIfExisting(this); - if (meta === undefined) return this.ids; - const ids = meta[idsSymbol]; - return ids !== undefined ? ids : this.ids; + get category() { + return "commonjs"; } /** - * @param {ModuleGraph} moduleGraph the module graph - * @param {string[]} ids the imported ids - * @returns {void} + * @returns {boolean | TRANSITIVE} true, when changes to the referenced module could affect the referencing module; TRANSITIVE, when changes to the referenced module could affect referencing modules of the referencing module */ - setIds(moduleGraph, ids) { - moduleGraph.getMeta(this)[idsSymbol] = ids; + couldAffectReferencingModule() { + return true; } /** - * @param {ModuleGraph} moduleGraph module graph - * @returns {null | false | function(ModuleGraphConnection, RuntimeSpec): ConnectionState} function to determine if the connection is active + * @returns {string | null} an identifier to merge equal requests */ - getCondition(moduleGraph) { - return getDependencyUsedByExportsCondition( - this, - this.usedByExports, - moduleGraph + getResourceIdentifier() { + return ( + `context${this.options.request} ${this.options.recursive} ` + + `${regExpToString(this.options.regExp)} ${regExpToString( + this.options.include + )} ${regExpToString(this.options.exclude)} ` + + `${this.options.mode} ${this.options.chunkName} ` + + `${JSON.stringify(this.options.groupOptions)}` ); } /** - * @param {ModuleGraph} moduleGraph the module graph - * @returns {ConnectionState} how this dependency connects the module to referencing modules - */ - getModuleEvaluationSideEffectsState(moduleGraph) { - return false; - } - - /** - * Returns list of exports referenced by this dependency + * Returns warnings * @param {ModuleGraph} moduleGraph module graph - * @param {RuntimeSpec} runtime the runtime for which the module is analysed - * @returns {(string[] | ReferencedExport)[]} referenced exports + * @returns {WebpackError[]} warnings */ - getReferencedExports(moduleGraph, runtime) { - let ids = this.getIds(moduleGraph); - if (ids.length === 0) return Dependency.EXPORTS_OBJECT_REFERENCED; - let namespaceObjectAsContext = this.namespaceObjectAsContext; - if (ids[0] === "default") { - const selfModule = moduleGraph.getParentModule(this); - const importedModule = moduleGraph.getModule(this); - switch ( - importedModule.getExportsType( - moduleGraph, - selfModule.buildMeta.strictHarmonyModule - ) - ) { - case "default-only": - case "default-with-named": - if (ids.length === 1) return Dependency.EXPORTS_OBJECT_REFERENCED; - ids = ids.slice(1); - namespaceObjectAsContext = true; - break; - case "dynamic": - return Dependency.EXPORTS_OBJECT_REFERENCED; - } + getWarnings(moduleGraph) { + let warnings = super.getWarnings(moduleGraph); + + if (this.critical) { + if (!warnings) warnings = []; + const CriticalDependencyWarning = getCriticalDependencyWarning(); + warnings.push(new CriticalDependencyWarning(this.critical)); } - if ( - this.call && - !this.directImport && - (namespaceObjectAsContext || ids.length > 1) - ) { - if (ids.length === 1) return Dependency.EXPORTS_OBJECT_REFERENCED; - ids = ids.slice(0, -1); + if (this.hadGlobalOrStickyRegExp) { + if (!warnings) warnings = []; + const CriticalDependencyWarning = getCriticalDependencyWarning(); + warnings.push( + new CriticalDependencyWarning( + "Contexts can't use RegExps with the 'g' or 'y' flags." + ) + ); } - return [ids]; + return warnings; } - /** - * @param {ModuleGraph} moduleGraph module graph - * @returns {number} effective mode - */ - _getEffectiveExportPresenceLevel(moduleGraph) { - if (this.exportPresenceMode !== ExportPresenceModes.AUTO) - return this.exportPresenceMode; - return moduleGraph.getParentModule(this).buildMeta.strictHarmonyModule - ? ExportPresenceModes.ERROR - : ExportPresenceModes.WARN; - } + serialize(context) { + const { write } = context; - /** - * Returns warnings - * @param {ModuleGraph} moduleGraph module graph - * @returns {WebpackError[]} warnings - */ - getWarnings(moduleGraph) { - const exportsPresence = this._getEffectiveExportPresenceLevel(moduleGraph); - if (exportsPresence === ExportPresenceModes.WARN) { - return this._getErrors(moduleGraph); - } - return null; - } + write(this.options); + write(this.userRequest); + write(this.critical); + write(this.hadGlobalOrStickyRegExp); + write(this.request); + write(this.range); + write(this.valueRange); + write(this.prepend); + write(this.replaces); - /** - * Returns errors - * @param {ModuleGraph} moduleGraph module graph - * @returns {WebpackError[]} errors - */ - getErrors(moduleGraph) { - const exportsPresence = this._getEffectiveExportPresenceLevel(moduleGraph); - if (exportsPresence === ExportPresenceModes.ERROR) { - return this._getErrors(moduleGraph); - } - return null; + super.serialize(context); } - /** - * @param {ModuleGraph} moduleGraph module graph - * @returns {WebpackError[] | undefined} errors - */ - _getErrors(moduleGraph) { - const ids = this.getIds(moduleGraph); - return this.getLinkingErrors( - moduleGraph, - ids, - `(imported as '${this.name}')` - ); + deserialize(context) { + const { read } = context; + + this.options = read(); + this.userRequest = read(); + this.critical = read(); + this.hadGlobalOrStickyRegExp = read(); + this.request = read(); + this.range = read(); + this.valueRange = read(); + this.prepend = read(); + this.replaces = read(); + + super.deserialize(context); } +} + +makeSerializable( + ContextDependency, + "webpack/lib/dependencies/ContextDependency" +); + +ContextDependency.Template = DependencyTemplate; + +module.exports = ContextDependency; + + +/***/ }), + +/***/ 7114: +/***/ (function(__unused_webpack_module, exports, __webpack_require__) { + +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ + + + +const { parseResource } = __webpack_require__(96236); + +/** @typedef {import("estree").Node} EsTreeNode */ +/** @typedef {import("../../declarations/WebpackOptions").JavascriptParserOptions} JavascriptParserOptions */ +/** @typedef {import("../../declarations/WebpackOptions").ModuleOptionsNormalized} ModuleOptions */ +/** @typedef {import("../javascript/BasicEvaluatedExpression")} BasicEvaluatedExpression */ +/** @typedef {import("../javascript/JavascriptParser")} JavascriptParser */ +/** @typedef {import("./ContextDependency")} ContextDependency */ +/** @typedef {import("./ContextDependency").ContextDependencyOptions} ContextDependencyOptions */ + +/** + * Escapes regular expression metacharacters + * @param {string} str String to quote + * @returns {string} Escaped string + */ +const quoteMeta = str => { + return str.replace(/[-[\]\\/{}()*+?.^$|]/g, "\\$&"); +}; - /** - * implement this method to allow the occurrence order plugin to count correctly - * @returns {number} count how often the id is used in this dependency - */ - getNumberOfIdOccurrences() { - return 0; +const splitContextFromPrefix = prefix => { + const idx = prefix.lastIndexOf("/"); + let context = "."; + if (idx >= 0) { + context = prefix.substr(0, idx); + prefix = `.${prefix.substr(idx)}`; } + return { + context, + prefix + }; +}; - serialize(context) { - const { write } = context; - write(this.ids); - write(this.name); - write(this.range); - write(this.exportPresenceMode); - write(this.namespaceObjectAsContext); - write(this.call); - write(this.directImport); - write(this.shorthand); - write(this.asiSafe); - write(this.usedByExports); - super.serialize(context); - } +/** @typedef {Partial>} PartialContextDependencyOptions */ - deserialize(context) { - const { read } = context; - this.ids = read(); - this.name = read(); - this.range = read(); - this.exportPresenceMode = read(); - this.namespaceObjectAsContext = read(); - this.call = read(); - this.directImport = read(); - this.shorthand = read(); - this.asiSafe = read(); - this.usedByExports = read(); - super.deserialize(context); - } -} +/** @typedef {{ new(options: ContextDependencyOptions, range: [number, number], valueRange: [number, number]): ContextDependency }} ContextDependencyConstructor */ -makeSerializable( - HarmonyImportSpecifierDependency, - "webpack/lib/dependencies/HarmonyImportSpecifierDependency" -); +/** + * @param {ContextDependencyConstructor} Dep the Dependency class + * @param {[number, number]} range source range + * @param {BasicEvaluatedExpression} param context param + * @param {EsTreeNode} expr expr + * @param {Pick} options options for context creation + * @param {PartialContextDependencyOptions} contextOptions options for the ContextModule + * @param {JavascriptParser} parser the parser + * @returns {ContextDependency} the created Dependency + */ +exports.create = (Dep, range, param, expr, options, contextOptions, parser) => { + if (param.isTemplateString()) { + let prefixRaw = param.quasis[0].string; + let postfixRaw = + param.quasis.length > 1 + ? param.quasis[param.quasis.length - 1].string + : ""; -HarmonyImportSpecifierDependency.Template = class HarmonyImportSpecifierDependencyTemplate extends ( - HarmonyImportDependency.Template -) { - /** - * @param {Dependency} dependency the dependency for which the template should be applied - * @param {ReplaceSource} source the current replace source which can be modified - * @param {DependencyTemplateContext} templateContext the context object - * @returns {void} - */ - apply(dependency, source, templateContext) { - const dep = /** @type {HarmonyImportSpecifierDependency} */ (dependency); - const { moduleGraph, module, runtime, concatenationScope } = - templateContext; - const connection = moduleGraph.getConnection(dep); - // Skip rendering depending when dependency is conditional - if (connection && !connection.isTargetActive(runtime)) return; + const valueRange = param.range; + const { context, prefix } = splitContextFromPrefix(prefixRaw); + const { + path: postfix, + query, + fragment + } = parseResource(postfixRaw, parser); - const ids = dep.getIds(moduleGraph); + // When there are more than two quasis, the generated RegExp can be more precise + // We join the quasis with the expression regexp + const innerQuasis = param.quasis.slice(1, param.quasis.length - 1); + const innerRegExp = + options.wrappedContextRegExp.source + + innerQuasis + .map(q => quoteMeta(q.string) + options.wrappedContextRegExp.source) + .join(""); - let exportExpr; - if ( - connection && - concatenationScope && - concatenationScope.isModuleInScope(connection.module) - ) { - if (ids.length === 0) { - exportExpr = concatenationScope.createModuleReference( - connection.module, - { - asiSafe: dep.asiSafe - } - ); - } else if (dep.namespaceObjectAsContext && ids.length === 1) { - exportExpr = - concatenationScope.createModuleReference(connection.module, { - asiSafe: dep.asiSafe - }) + propertyAccess(ids); + // Example: `./context/pre${e}inner${e}inner2${e}post?query#frag` + // context: "./context" + // prefix: "./pre" + // innerQuasis: [BEE("inner"), BEE("inner2")] + // (BEE = BasicEvaluatedExpression) + // postfix: "post" + // query: "?query" + // fragment: "#frag" + // regExp: /^\.\/pre.*inner.*inner2.*post$/ + const regExp = new RegExp( + `^${quoteMeta(prefix)}${innerRegExp}${quoteMeta(postfix)}$` + ); + const dep = new Dep( + { + request: context + query + fragment, + recursive: options.wrappedContextRecursive, + regExp, + mode: "sync", + ...contextOptions + }, + range, + valueRange + ); + dep.loc = expr.loc; + const replaces = []; + + param.parts.forEach((part, i) => { + if (i % 2 === 0) { + // Quasis or merged quasi + let range = part.range; + let value = part.string; + if (param.templateStringKind === "cooked") { + value = JSON.stringify(value); + value = value.slice(1, value.length - 1); + } + if (i === 0) { + // prefix + value = prefix; + range = [param.range[0], part.range[1]]; + value = + (param.templateStringKind === "cooked" ? "`" : "String.raw`") + + value; + } else if (i === param.parts.length - 1) { + // postfix + value = postfix; + range = [part.range[0], param.range[1]]; + value = value + "`"; + } else if ( + part.expression && + part.expression.type === "TemplateElement" && + part.expression.value.raw === value + ) { + // Shortcut when it's a single quasi and doesn't need to be replaced + return; + } + replaces.push({ + range, + value + }); } else { - exportExpr = concatenationScope.createModuleReference( - connection.module, - { - ids, - call: dep.call, - directImport: dep.directImport, - asiSafe: dep.asiSafe - } - ); + // Expression + parser.walkExpression(part.expression); } - } else { - super.apply(dependency, source, templateContext); - - const { runtimeTemplate, initFragments, runtimeRequirements } = - templateContext; + }); - exportExpr = runtimeTemplate.exportFromImport({ - moduleGraph, - module: moduleGraph.getModule(dep), - request: dep.request, - exportName: ids, - originModule: module, - asiSafe: dep.shorthand ? true : dep.asiSafe, - isCall: dep.call, - callContext: !dep.directImport, - defaultInterop: true, - importVar: dep.getImportVar(moduleGraph), - initFragments, - runtime, - runtimeRequirements + dep.replaces = replaces; + dep.critical = + options.wrappedContextCritical && + "a part of the request of a dependency is an expression"; + return dep; + } else if ( + param.isWrapped() && + ((param.prefix && param.prefix.isString()) || + (param.postfix && param.postfix.isString())) + ) { + let prefixRaw = + param.prefix && param.prefix.isString() ? param.prefix.string : ""; + let postfixRaw = + param.postfix && param.postfix.isString() ? param.postfix.string : ""; + const prefixRange = + param.prefix && param.prefix.isString() ? param.prefix.range : null; + const postfixRange = + param.postfix && param.postfix.isString() ? param.postfix.range : null; + const valueRange = param.range; + const { context, prefix } = splitContextFromPrefix(prefixRaw); + const { + path: postfix, + query, + fragment + } = parseResource(postfixRaw, parser); + const regExp = new RegExp( + `^${quoteMeta(prefix)}${options.wrappedContextRegExp.source}${quoteMeta( + postfix + )}$` + ); + const dep = new Dep( + { + request: context + query + fragment, + recursive: options.wrappedContextRecursive, + regExp, + mode: "sync", + ...contextOptions + }, + range, + valueRange + ); + dep.loc = expr.loc; + const replaces = []; + if (prefixRange) { + replaces.push({ + range: prefixRange, + value: JSON.stringify(prefix) }); } - if (dep.shorthand) { - source.insert(dep.range[1], `: ${exportExpr}`); - } else { - source.replace(dep.range[0], dep.range[1] - 1, exportExpr); + if (postfixRange) { + replaces.push({ + range: postfixRange, + value: JSON.stringify(postfix) + }); + } + dep.replaces = replaces; + dep.critical = + options.wrappedContextCritical && + "a part of the request of a dependency is an expression"; + + if (parser && param.wrappedInnerExpressions) { + for (const part of param.wrappedInnerExpressions) { + if (part.expression) parser.walkExpression(part.expression); + } } + + return dep; + } else { + const dep = new Dep( + { + request: options.exprContextRequest, + recursive: options.exprContextRecursive, + regExp: /** @type {RegExp} */ (options.exprContextRegExp), + mode: "sync", + ...contextOptions + }, + range, + param.range + ); + dep.loc = expr.loc; + dep.critical = + options.exprContextCritical && + "the request of a dependency is an expression"; + + parser.walkExpression(param.expression); + + return dep; } }; -module.exports = HarmonyImportSpecifierDependency; - /***/ }), -/***/ 73365: +/***/ 95080: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; @@ -81556,160 +79211,132 @@ module.exports = HarmonyImportSpecifierDependency; -const HarmonyAcceptDependency = __webpack_require__(38421); -const HarmonyAcceptImportDependency = __webpack_require__(35316); -const HarmonyCompatibilityDependency = __webpack_require__(56164); -const HarmonyExportExpressionDependency = __webpack_require__(22705); -const HarmonyExportHeaderDependency = __webpack_require__(67159); -const HarmonyExportImportedSpecifierDependency = __webpack_require__(77952); -const HarmonyExportSpecifierDependency = __webpack_require__(59042); -const HarmonyImportSideEffectDependency = __webpack_require__(76853); -const HarmonyImportSpecifierDependency = __webpack_require__(61994); - -const HarmonyDetectionParserPlugin = __webpack_require__(63683); -const HarmonyExportDependencyParserPlugin = __webpack_require__(70925); -const HarmonyImportDependencyParserPlugin = __webpack_require__(76581); -const HarmonyTopLevelThisParserPlugin = __webpack_require__(79065); - -/** @typedef {import("../Compiler")} Compiler */ +const ContextDependency = __webpack_require__(67840); -class HarmonyModulesPlugin { - constructor(options) { - this.options = options; - } +/** @typedef {import("webpack-sources").ReplaceSource} ReplaceSource */ +/** @typedef {import("../Dependency")} Dependency */ +/** @typedef {import("../DependencyTemplate").DependencyTemplateContext} DependencyTemplateContext */ +class ContextDependencyTemplateAsId extends ContextDependency.Template { /** - * Apply the plugin - * @param {Compiler} compiler the compiler instance + * @param {Dependency} dependency the dependency for which the template should be applied + * @param {ReplaceSource} source the current replace source which can be modified + * @param {DependencyTemplateContext} templateContext the context object * @returns {void} */ - apply(compiler) { - compiler.hooks.compilation.tap( - "HarmonyModulesPlugin", - (compilation, { normalModuleFactory }) => { - compilation.dependencyTemplates.set( - HarmonyCompatibilityDependency, - new HarmonyCompatibilityDependency.Template() - ); - - compilation.dependencyFactories.set( - HarmonyImportSideEffectDependency, - normalModuleFactory - ); - compilation.dependencyTemplates.set( - HarmonyImportSideEffectDependency, - new HarmonyImportSideEffectDependency.Template() - ); - - compilation.dependencyFactories.set( - HarmonyImportSpecifierDependency, - normalModuleFactory - ); - compilation.dependencyTemplates.set( - HarmonyImportSpecifierDependency, - new HarmonyImportSpecifierDependency.Template() - ); - - compilation.dependencyTemplates.set( - HarmonyExportHeaderDependency, - new HarmonyExportHeaderDependency.Template() - ); - - compilation.dependencyTemplates.set( - HarmonyExportExpressionDependency, - new HarmonyExportExpressionDependency.Template() - ); - - compilation.dependencyTemplates.set( - HarmonyExportSpecifierDependency, - new HarmonyExportSpecifierDependency.Template() - ); - - compilation.dependencyFactories.set( - HarmonyExportImportedSpecifierDependency, - normalModuleFactory - ); - compilation.dependencyTemplates.set( - HarmonyExportImportedSpecifierDependency, - new HarmonyExportImportedSpecifierDependency.Template() - ); - - compilation.dependencyTemplates.set( - HarmonyAcceptDependency, - new HarmonyAcceptDependency.Template() - ); + apply( + dependency, + source, + { runtimeTemplate, moduleGraph, chunkGraph, runtimeRequirements } + ) { + const dep = /** @type {ContextDependency} */ (dependency); + const moduleExports = runtimeTemplate.moduleExports({ + module: moduleGraph.getModule(dep), + chunkGraph, + request: dep.request, + weak: dep.weak, + runtimeRequirements + }); - compilation.dependencyFactories.set( - HarmonyAcceptImportDependency, - normalModuleFactory + if (moduleGraph.getModule(dep)) { + if (dep.valueRange) { + if (Array.isArray(dep.replaces)) { + for (let i = 0; i < dep.replaces.length; i++) { + const rep = dep.replaces[i]; + source.replace(rep.range[0], rep.range[1] - 1, rep.value); + } + } + source.replace(dep.valueRange[1], dep.range[1] - 1, ")"); + source.replace( + dep.range[0], + dep.valueRange[0] - 1, + `${moduleExports}.resolve(` ); - compilation.dependencyTemplates.set( - HarmonyAcceptImportDependency, - new HarmonyAcceptImportDependency.Template() + } else { + source.replace( + dep.range[0], + dep.range[1] - 1, + `${moduleExports}.resolve` ); - - const handler = (parser, parserOptions) => { - // TODO webpack 6: rename harmony to esm or module - if (parserOptions.harmony !== undefined && !parserOptions.harmony) - return; - - new HarmonyDetectionParserPlugin(this.options).apply(parser); - new HarmonyImportDependencyParserPlugin(parserOptions).apply(parser); - new HarmonyExportDependencyParserPlugin(parserOptions).apply(parser); - new HarmonyTopLevelThisParserPlugin().apply(parser); - }; - - normalModuleFactory.hooks.parser - .for("javascript/auto") - .tap("HarmonyModulesPlugin", handler); - normalModuleFactory.hooks.parser - .for("javascript/esm") - .tap("HarmonyModulesPlugin", handler); } - ); + } else { + source.replace(dep.range[0], dep.range[1] - 1, moduleExports); + } } } -module.exports = HarmonyModulesPlugin; +module.exports = ContextDependencyTemplateAsId; /***/ }), -/***/ 79065: +/***/ 18259: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; /* MIT License http://www.opensource.org/licenses/mit-license.php - Author Florent Cailhol @ooflorent + Author Tobias Koppers @sokra */ -const ConstDependency = __webpack_require__(60864); -const HarmonyExports = __webpack_require__(37637); +const ContextDependency = __webpack_require__(67840); -class HarmonyTopLevelThisParserPlugin { - apply(parser) { - parser.hooks.expression - .for("this") - .tap("HarmonyTopLevelThisParserPlugin", node => { - if (!parser.scope.topLevelScope) return; - if (HarmonyExports.isEnabled(parser.state)) { - const dep = new ConstDependency("undefined", node.range, null); - dep.loc = node.loc; - parser.state.module.addPresentationalDependency(dep); - return this; +/** @typedef {import("webpack-sources").ReplaceSource} ReplaceSource */ +/** @typedef {import("../Dependency")} Dependency */ +/** @typedef {import("../DependencyTemplate").DependencyTemplateContext} DependencyTemplateContext */ + +class ContextDependencyTemplateAsRequireCall extends ContextDependency.Template { + /** + * @param {Dependency} dependency the dependency for which the template should be applied + * @param {ReplaceSource} source the current replace source which can be modified + * @param {DependencyTemplateContext} templateContext the context object + * @returns {void} + */ + apply( + dependency, + source, + { runtimeTemplate, moduleGraph, chunkGraph, runtimeRequirements } + ) { + const dep = /** @type {ContextDependency} */ (dependency); + let moduleExports = runtimeTemplate.moduleExports({ + module: moduleGraph.getModule(dep), + chunkGraph, + request: dep.request, + runtimeRequirements + }); + + if (dep.inShorthand) { + moduleExports = `${dep.inShorthand}: ${moduleExports}`; + } + if (moduleGraph.getModule(dep)) { + if (dep.valueRange) { + if (Array.isArray(dep.replaces)) { + for (let i = 0; i < dep.replaces.length; i++) { + const rep = dep.replaces[i]; + source.replace(rep.range[0], rep.range[1] - 1, rep.value); + } } - }); + source.replace(dep.valueRange[1], dep.range[1] - 1, ")"); + source.replace( + dep.range[0], + dep.valueRange[0] - 1, + `${moduleExports}(` + ); + } else { + source.replace(dep.range[0], dep.range[1] - 1, moduleExports); + } + } else { + source.replace(dep.range[0], dep.range[1] - 1, moduleExports); + } } } - -module.exports = HarmonyTopLevelThisParserPlugin; +module.exports = ContextDependencyTemplateAsRequireCall; /***/ }), -/***/ 75785: +/***/ 83853: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; @@ -81720,58 +79347,75 @@ module.exports = HarmonyTopLevelThisParserPlugin; +const Dependency = __webpack_require__(50384); const makeSerializable = __webpack_require__(26522); -const ContextDependency = __webpack_require__(67840); -const ContextDependencyTemplateAsRequireCall = __webpack_require__(18259); +const ModuleDependency = __webpack_require__(80944); -class ImportContextDependency extends ContextDependency { - constructor(options, range, valueRange) { - super(options); +/** @typedef {import("../Dependency").ReferencedExport} ReferencedExport */ +/** @typedef {import("../ModuleGraph")} ModuleGraph */ +/** @typedef {import("../util/runtime").RuntimeSpec} RuntimeSpec */ - this.range = range; - this.valueRange = valueRange; +class ContextElementDependency extends ModuleDependency { + constructor(request, userRequest, typePrefix, category, referencedExports) { + super(request); + this.referencedExports = referencedExports; + this._typePrefix = typePrefix; + this._category = category; + + if (userRequest) { + this.userRequest = userRequest; + } } get type() { - return `import() context ${this.options.mode}`; + if (this._typePrefix) { + return `${this._typePrefix} context element`; + } + + return "context element"; } get category() { - return "esm"; + return this._category; } - serialize(context) { - const { write } = context; - - write(this.range); - write(this.valueRange); + /** + * Returns list of exports referenced by this dependency + * @param {ModuleGraph} moduleGraph module graph + * @param {RuntimeSpec} runtime the runtime for which the module is analysed + * @returns {(string[] | ReferencedExport)[]} referenced exports + */ + getReferencedExports(moduleGraph, runtime) { + return this.referencedExports + ? this.referencedExports.map(e => ({ + name: e, + canMangle: false + })) + : Dependency.EXPORTS_OBJECT_REFERENCED; + } + serialize(context) { + context.write(this.referencedExports); super.serialize(context); } deserialize(context) { - const { read } = context; - - this.range = read(); - this.valueRange = read(); - + this.referencedExports = context.read(); super.deserialize(context); } } makeSerializable( - ImportContextDependency, - "webpack/lib/dependencies/ImportContextDependency" + ContextElementDependency, + "webpack/lib/dependencies/ContextElementDependency" ); -ImportContextDependency.Template = ContextDependencyTemplateAsRequireCall; - -module.exports = ImportContextDependency; +module.exports = ContextElementDependency; /***/ }), -/***/ 16727: +/***/ 29829: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; @@ -81782,69 +79426,30 @@ module.exports = ImportContextDependency; -const Dependency = __webpack_require__(50384); +const RuntimeGlobals = __webpack_require__(49404); const makeSerializable = __webpack_require__(26522); -const ModuleDependency = __webpack_require__(80944); +const NullDependency = __webpack_require__(65845); /** @typedef {import("webpack-sources").ReplaceSource} ReplaceSource */ -/** @typedef {import("../AsyncDependenciesBlock")} AsyncDependenciesBlock */ -/** @typedef {import("../Dependency").ReferencedExport} ReferencedExport */ +/** @typedef {import("../Dependency")} Dependency */ /** @typedef {import("../DependencyTemplate").DependencyTemplateContext} DependencyTemplateContext */ -/** @typedef {import("../ModuleGraph")} ModuleGraph */ -/** @typedef {import("../util/runtime").RuntimeSpec} RuntimeSpec */ -class ImportDependency extends ModuleDependency { +class CreateScriptUrlDependency extends NullDependency { /** - * @param {string} request the request - * @param {[number, number]} range expression range - * @param {string[][]=} referencedExports list of referenced exports + * @param {[number, number]} range range */ - constructor(request, range, referencedExports) { - super(request); + constructor(range) { + super(); this.range = range; - this.referencedExports = referencedExports; } get type() { - return "import()"; - } - - get category() { - return "esm"; - } - - /** - * Returns list of exports referenced by this dependency - * @param {ModuleGraph} moduleGraph module graph - * @param {RuntimeSpec} runtime the runtime for which the module is analysed - * @returns {(string[] | ReferencedExport)[]} referenced exports - */ - getReferencedExports(moduleGraph, runtime) { - return this.referencedExports - ? this.referencedExports.map(e => ({ - name: e, - canMangle: false - })) - : Dependency.EXPORTS_OBJECT_REFERENCED; - } - - serialize(context) { - context.write(this.range); - context.write(this.referencedExports); - super.serialize(context); - } - - deserialize(context) { - this.range = context.read(); - this.referencedExports = context.read(); - super.deserialize(context); + return "create script url"; } } -makeSerializable(ImportDependency, "webpack/lib/dependencies/ImportDependency"); - -ImportDependency.Template = class ImportDependencyTemplate extends ( - ModuleDependency.Template +CreateScriptUrlDependency.Template = class CreateScriptUrlDependencyTemplate extends ( + NullDependency.Template ) { /** * @param {Dependency} dependency the dependency for which the template should be applied @@ -81852,35 +79457,27 @@ ImportDependency.Template = class ImportDependencyTemplate extends ( * @param {DependencyTemplateContext} templateContext the context object * @returns {void} */ - apply( - dependency, - source, - { runtimeTemplate, module, moduleGraph, chunkGraph, runtimeRequirements } - ) { - const dep = /** @type {ImportDependency} */ (dependency); - const block = /** @type {AsyncDependenciesBlock} */ ( - moduleGraph.getParentBlock(dep) - ); - const content = runtimeTemplate.moduleNamespacePromise({ - chunkGraph, - block: block, - module: moduleGraph.getModule(dep), - request: dep.request, - strict: module.buildMeta.strictHarmonyModule, - message: "import()", - runtimeRequirements - }); + apply(dependency, source, { runtimeRequirements }) { + const dep = /** @type {CreateScriptUrlDependency} */ (dependency); - source.replace(dep.range[0], dep.range[1] - 1, content); + runtimeRequirements.add(RuntimeGlobals.createScriptUrl); + + source.insert(dep.range[0], `${RuntimeGlobals.createScriptUrl}(`); + source.insert(dep.range[1], ")"); } }; -module.exports = ImportDependency; +makeSerializable( + CreateScriptUrlDependency, + "webpack/lib/dependencies/CreateScriptUrlDependency" +); + +module.exports = CreateScriptUrlDependency; /***/ }), -/***/ 91941: +/***/ 14190: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; @@ -81891,27 +79488,49 @@ module.exports = ImportDependency; +const WebpackError = __webpack_require__(68422); const makeSerializable = __webpack_require__(26522); -const ImportDependency = __webpack_require__(16727); -/** @typedef {import("webpack-sources").ReplaceSource} ReplaceSource */ -/** @typedef {import("../Dependency")} Dependency */ -/** @typedef {import("../Dependency").ReferencedExport} ReferencedExport */ -/** @typedef {import("../DependencyTemplate").DependencyTemplateContext} DependencyTemplateContext */ -/** @typedef {import("../ModuleGraph")} ModuleGraph */ +class CriticalDependencyWarning extends WebpackError { + constructor(message) { + super(); -class ImportEagerDependency extends ImportDependency { - /** - * @param {string} request the request - * @param {[number, number]} range expression range - * @param {string[][]=} referencedExports list of referenced exports - */ - constructor(request, range, referencedExports) { - super(request, range, referencedExports); + this.name = "CriticalDependencyWarning"; + this.message = "Critical dependency: " + message; + } +} + +makeSerializable( + CriticalDependencyWarning, + "webpack/lib/dependencies/CriticalDependencyWarning" +); + +module.exports = CriticalDependencyWarning; + + +/***/ }), + +/***/ 82766: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ + + + +const makeSerializable = __webpack_require__(26522); +const ModuleDependency = __webpack_require__(80944); + +class DelegatedSourceDependency extends ModuleDependency { + constructor(request) { + super(request); } get type() { - return "import() eager"; + return "delegated source"; } get category() { @@ -81920,111 +79539,171 @@ class ImportEagerDependency extends ImportDependency { } makeSerializable( - ImportEagerDependency, - "webpack/lib/dependencies/ImportEagerDependency" + DelegatedSourceDependency, + "webpack/lib/dependencies/DelegatedSourceDependency" ); -ImportEagerDependency.Template = class ImportEagerDependencyTemplate extends ( - ImportDependency.Template -) { - /** - * @param {Dependency} dependency the dependency for which the template should be applied - * @param {ReplaceSource} source the current replace source which can be modified - * @param {DependencyTemplateContext} templateContext the context object - * @returns {void} - */ - apply( - dependency, - source, - { runtimeTemplate, module, moduleGraph, chunkGraph, runtimeRequirements } - ) { - const dep = /** @type {ImportEagerDependency} */ (dependency); - const content = runtimeTemplate.moduleNamespacePromise({ - chunkGraph, - module: moduleGraph.getModule(dep), - request: dep.request, - strict: module.buildMeta.strictHarmonyModule, - message: "import() eager", - runtimeRequirements - }); - - source.replace(dep.range[0], dep.range[1] - 1, content); - } -}; - -module.exports = ImportEagerDependency; +module.exports = DelegatedSourceDependency; /***/ }), -/***/ 58287: +/***/ 57839: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; /* MIT License http://www.opensource.org/licenses/mit-license.php - Author Ivan Kopeykin @vankop + Author Tobias Koppers @sokra */ +const Dependency = __webpack_require__(50384); const makeSerializable = __webpack_require__(26522); -const ModuleDependency = __webpack_require__(80944); -const ModuleDependencyTemplateAsId = __webpack_require__(35795); -class ImportMetaHotAcceptDependency extends ModuleDependency { - constructor(request, range) { - super(request); - this.range = range; - this.weak = true; +class DllEntryDependency extends Dependency { + constructor(dependencies, name) { + super(); + + this.dependencies = dependencies; + this.name = name; } get type() { - return "import.meta.webpackHot.accept"; + return "dll entry"; } - get category() { - return "esm"; + serialize(context) { + const { write } = context; + + write(this.dependencies); + write(this.name); + + super.serialize(context); + } + + deserialize(context) { + const { read } = context; + + this.dependencies = read(); + this.name = read(); + + super.deserialize(context); } } makeSerializable( - ImportMetaHotAcceptDependency, - "webpack/lib/dependencies/ImportMetaHotAcceptDependency" + DllEntryDependency, + "webpack/lib/dependencies/DllEntryDependency" ); -ImportMetaHotAcceptDependency.Template = ModuleDependencyTemplateAsId; +module.exports = DllEntryDependency; -module.exports = ImportMetaHotAcceptDependency; + +/***/ }), + +/***/ 87370: +/***/ (function(__unused_webpack_module, exports) { + +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ + + + +/** @typedef {import("../Parser").ParserState} ParserState */ + +/** @type {WeakMap} */ +const parserStateExportsState = new WeakMap(); + +/** + * @param {ParserState} parserState parser state + * @returns {void} + */ +exports.bailout = parserState => { + const value = parserStateExportsState.get(parserState); + parserStateExportsState.set(parserState, false); + if (value === true) { + parserState.module.buildMeta.exportsType = undefined; + parserState.module.buildMeta.defaultObject = false; + } +}; + +/** + * @param {ParserState} parserState parser state + * @returns {void} + */ +exports.enable = parserState => { + const value = parserStateExportsState.get(parserState); + if (value === false) return; + parserStateExportsState.set(parserState, true); + if (value !== true) { + parserState.module.buildMeta.exportsType = "default"; + parserState.module.buildMeta.defaultObject = "redirect"; + } +}; + +/** + * @param {ParserState} parserState parser state + * @returns {void} + */ +exports.setFlagged = parserState => { + const value = parserStateExportsState.get(parserState); + if (value !== true) return; + const buildMeta = parserState.module.buildMeta; + if (buildMeta.exportsType === "dynamic") return; + buildMeta.exportsType = "flagged"; +}; + +/** + * @param {ParserState} parserState parser state + * @returns {void} + */ +exports.setDynamic = parserState => { + const value = parserStateExportsState.get(parserState); + if (value !== true) return; + parserState.module.buildMeta.exportsType = "dynamic"; +}; + +/** + * @param {ParserState} parserState parser state + * @returns {boolean} true, when enabled + */ +exports.isEnabled = parserState => { + const value = parserStateExportsState.get(parserState); + return value === true; +}; /***/ }), -/***/ 89911: +/***/ 41075: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; /* MIT License http://www.opensource.org/licenses/mit-license.php - Author Ivan Kopeykin @vankop + Author Tobias Koppers @sokra */ const makeSerializable = __webpack_require__(26522); const ModuleDependency = __webpack_require__(80944); -const ModuleDependencyTemplateAsId = __webpack_require__(35795); -class ImportMetaHotDeclineDependency extends ModuleDependency { - constructor(request, range) { +class EntryDependency extends ModuleDependency { + /** + * @param {string} request request path for entry + */ + constructor(request) { super(request); - - this.range = range; - this.weak = true; } get type() { - return "import.meta.webpackHot.decline"; + return "entry"; } get category() { @@ -82032,211 +79711,159 @@ class ImportMetaHotDeclineDependency extends ModuleDependency { } } -makeSerializable( - ImportMetaHotDeclineDependency, - "webpack/lib/dependencies/ImportMetaHotDeclineDependency" -); - -ImportMetaHotDeclineDependency.Template = ModuleDependencyTemplateAsId; +makeSerializable(EntryDependency, "webpack/lib/dependencies/EntryDependency"); -module.exports = ImportMetaHotDeclineDependency; +module.exports = EntryDependency; /***/ }), -/***/ 81841: +/***/ 30474: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; /* MIT License http://www.opensource.org/licenses/mit-license.php - Author Ivan Kopeykin @vankop + Author Tobias Koppers @sokra */ -const { pathToFileURL } = __webpack_require__(78835); -const ModuleDependencyWarning = __webpack_require__(61528); -const Template = __webpack_require__(92066); -const BasicEvaluatedExpression = __webpack_require__(2412); -const { - evaluateToIdentifier, - toConstantDependency, - evaluateToString, - evaluateToNumber -} = __webpack_require__(28723); -const memoize = __webpack_require__(84297); -const propertyAccess = __webpack_require__(86709); -const ConstDependency = __webpack_require__(60864); +const { UsageState } = __webpack_require__(4295); +const makeSerializable = __webpack_require__(26522); +const NullDependency = __webpack_require__(65845); -/** @typedef {import("estree").MemberExpression} MemberExpression */ -/** @typedef {import("../Compiler")} Compiler */ -/** @typedef {import("../NormalModule")} NormalModule */ -/** @typedef {import("../javascript/JavascriptParser")} Parser */ +/** @typedef {import("webpack-sources").ReplaceSource} ReplaceSource */ +/** @typedef {import("../ChunkGraph")} ChunkGraph */ +/** @typedef {import("../Dependency")} Dependency */ +/** @typedef {import("../Dependency").UpdateHashContext} UpdateHashContext */ +/** @typedef {import("../DependencyTemplate").DependencyTemplateContext} DependencyTemplateContext */ +/** @typedef {import("../Module")} Module */ +/** @typedef {import("../ModuleGraph")} ModuleGraph */ +/** @typedef {import("../util/Hash")} Hash */ +/** @typedef {import("../util/runtime").RuntimeSpec} RuntimeSpec */ + +/** + * @param {ModuleGraph} moduleGraph the module graph + * @param {Module} module the module + * @param {string | null} exportName name of the export if any + * @param {string | null} property name of the requested property + * @param {RuntimeSpec} runtime for which runtime + * @returns {any} value of the property + */ +const getProperty = (moduleGraph, module, exportName, property, runtime) => { + if (!exportName) { + switch (property) { + case "usedExports": { + const usedExports = moduleGraph + .getExportsInfo(module) + .getUsedExports(runtime); + if ( + typeof usedExports === "boolean" || + usedExports === undefined || + usedExports === null + ) { + return usedExports; + } + return Array.from(usedExports).sort(); + } + } + } + switch (property) { + case "used": + return ( + moduleGraph.getExportsInfo(module).getUsed(exportName, runtime) !== + UsageState.Unused + ); + case "useInfo": { + const state = moduleGraph + .getExportsInfo(module) + .getUsed(exportName, runtime); + switch (state) { + case UsageState.Used: + case UsageState.OnlyPropertiesUsed: + return true; + case UsageState.Unused: + return false; + case UsageState.NoInfo: + return undefined; + case UsageState.Unknown: + return null; + default: + throw new Error(`Unexpected UsageState ${state}`); + } + } + case "provideInfo": + return moduleGraph.getExportsInfo(module).isExportProvided(exportName); + } + return undefined; +}; + +class ExportsInfoDependency extends NullDependency { + constructor(range, exportName, property) { + super(); + this.range = range; + this.exportName = exportName; + this.property = property; + } + + serialize(context) { + const { write } = context; + write(this.range); + write(this.exportName); + write(this.property); + super.serialize(context); + } + + static deserialize(context) { + const obj = new ExportsInfoDependency( + context.read(), + context.read(), + context.read() + ); + obj.deserialize(context); + return obj; + } +} -const getCriticalDependencyWarning = memoize(() => - __webpack_require__(14190) +makeSerializable( + ExportsInfoDependency, + "webpack/lib/dependencies/ExportsInfoDependency" ); -class ImportMetaPlugin { +ExportsInfoDependency.Template = class ExportsInfoDependencyTemplate extends ( + NullDependency.Template +) { /** - * @param {Compiler} compiler compiler + * @param {Dependency} dependency the dependency for which the template should be applied + * @param {ReplaceSource} source the current replace source which can be modified + * @param {DependencyTemplateContext} templateContext the context object + * @returns {void} */ - apply(compiler) { - compiler.hooks.compilation.tap( - "ImportMetaPlugin", - (compilation, { normalModuleFactory }) => { - /** - * @param {NormalModule} module module - * @returns {string} file url - */ - const getUrl = module => { - return pathToFileURL(module.resource).toString(); - }; - /** - * @param {Parser} parser parser - * @param {Object} parserOptions parserOptions - * @returns {void} - */ - const parserHandler = (parser, parserOptions) => { - /// import.meta direct /// - parser.hooks.typeof - .for("import.meta") - .tap( - "ImportMetaPlugin", - toConstantDependency(parser, JSON.stringify("object")) - ); - parser.hooks.expression - .for("import.meta") - .tap("ImportMetaPlugin", metaProperty => { - const CriticalDependencyWarning = getCriticalDependencyWarning(); - parser.state.module.addWarning( - new ModuleDependencyWarning( - parser.state.module, - new CriticalDependencyWarning( - "Accessing import.meta directly is unsupported (only property access is supported)" - ), - metaProperty.loc - ) - ); - const dep = new ConstDependency( - `${parser.isAsiPosition(metaProperty.range[0]) ? ";" : ""}({})`, - metaProperty.range - ); - dep.loc = metaProperty.loc; - parser.state.module.addPresentationalDependency(dep); - return true; - }); - parser.hooks.evaluateTypeof - .for("import.meta") - .tap("ImportMetaPlugin", evaluateToString("object")); - parser.hooks.evaluateIdentifier.for("import.meta").tap( - "ImportMetaPlugin", - evaluateToIdentifier("import.meta", "import.meta", () => [], true) - ); - - /// import.meta.url /// - parser.hooks.typeof - .for("import.meta.url") - .tap( - "ImportMetaPlugin", - toConstantDependency(parser, JSON.stringify("string")) - ); - parser.hooks.expression - .for("import.meta.url") - .tap("ImportMetaPlugin", expr => { - const dep = new ConstDependency( - JSON.stringify(getUrl(parser.state.module)), - expr.range - ); - dep.loc = expr.loc; - parser.state.module.addPresentationalDependency(dep); - return true; - }); - parser.hooks.evaluateTypeof - .for("import.meta.url") - .tap("ImportMetaPlugin", evaluateToString("string")); - parser.hooks.evaluateIdentifier - .for("import.meta.url") - .tap("ImportMetaPlugin", expr => { - return new BasicEvaluatedExpression() - .setString(getUrl(parser.state.module)) - .setRange(expr.range); - }); - - /// import.meta.webpack /// - const webpackVersion = parseInt( - __webpack_require__(87168)/* .version */ .i8, - 10 - ); - parser.hooks.typeof - .for("import.meta.webpack") - .tap( - "ImportMetaPlugin", - toConstantDependency(parser, JSON.stringify("number")) - ); - parser.hooks.expression - .for("import.meta.webpack") - .tap( - "ImportMetaPlugin", - toConstantDependency(parser, JSON.stringify(webpackVersion)) - ); - parser.hooks.evaluateTypeof - .for("import.meta.webpack") - .tap("ImportMetaPlugin", evaluateToString("number")); - parser.hooks.evaluateIdentifier - .for("import.meta.webpack") - .tap("ImportMetaPlugin", evaluateToNumber(webpackVersion)); - - /// Unknown properties /// - parser.hooks.unhandledExpressionMemberChain - .for("import.meta") - .tap("ImportMetaPlugin", (expr, members) => { - const dep = new ConstDependency( - `${Template.toNormalComment( - "unsupported import.meta." + members.join(".") - )} undefined${propertyAccess(members, 1)}`, - expr.range - ); - dep.loc = expr.loc; - parser.state.module.addPresentationalDependency(dep); - return true; - }); - parser.hooks.evaluate - .for("MemberExpression") - .tap("ImportMetaPlugin", expression => { - const expr = /** @type {MemberExpression} */ (expression); - if ( - expr.object.type === "MetaProperty" && - expr.object.meta.name === "import" && - expr.object.property.name === "meta" && - expr.property.type === - (expr.computed ? "Literal" : "Identifier") - ) { - return new BasicEvaluatedExpression() - .setUndefined() - .setRange(expr.range); - } - }); - }; + apply(dependency, source, { module, moduleGraph, runtime }) { + const dep = /** @type {ExportsInfoDependency} */ (dependency); - normalModuleFactory.hooks.parser - .for("javascript/auto") - .tap("ImportMetaPlugin", parserHandler); - normalModuleFactory.hooks.parser - .for("javascript/esm") - .tap("ImportMetaPlugin", parserHandler); - } + const value = getProperty( + moduleGraph, + module, + dep.exportName, + dep.property, + runtime + ); + source.replace( + dep.range[0], + dep.range[1] - 1, + value === undefined ? "undefined" : JSON.stringify(value) ); } -} +}; -module.exports = ImportMetaPlugin; +module.exports = ExportsInfoDependency; /***/ }), -/***/ 44136: +/***/ 38421: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; @@ -82247,271 +79874,138 @@ module.exports = ImportMetaPlugin; -const AsyncDependenciesBlock = __webpack_require__(11315); -const CommentCompilationWarning = __webpack_require__(28151); -const UnsupportedFeatureWarning = __webpack_require__(9532); -const ContextDependencyHelpers = __webpack_require__(7114); -const ImportContextDependency = __webpack_require__(75785); -const ImportDependency = __webpack_require__(16727); -const ImportEagerDependency = __webpack_require__(91941); -const ImportWeakDependency = __webpack_require__(58426); +const Template = __webpack_require__(92066); +const makeSerializable = __webpack_require__(26522); +const HarmonyImportDependency = __webpack_require__(19577); +const NullDependency = __webpack_require__(65845); -/** @typedef {import("../ChunkGroup").RawChunkGroupOptions} RawChunkGroupOptions */ -/** @typedef {import("../ContextModule").ContextMode} ContextMode */ +/** @typedef {import("webpack-sources").ReplaceSource} ReplaceSource */ +/** @typedef {import("../Dependency")} Dependency */ +/** @typedef {import("../DependencyTemplate").DependencyTemplateContext} DependencyTemplateContext */ +/** @typedef {import("./HarmonyAcceptImportDependency")} HarmonyAcceptImportDependency */ -class ImportParserPlugin { - constructor(options) { - this.options = options; +class HarmonyAcceptDependency extends NullDependency { + /** + * @param {[number, number]} range expression range + * @param {HarmonyAcceptImportDependency[]} dependencies import dependencies + * @param {boolean} hasCallback true, if the range wraps an existing callback + */ + constructor(range, dependencies, hasCallback) { + super(); + this.range = range; + this.dependencies = dependencies; + this.hasCallback = hasCallback; } - apply(parser) { - parser.hooks.importCall.tap("ImportParserPlugin", expr => { - const param = parser.evaluateExpression(expr.source); - - let chunkName = null; - /** @type {ContextMode} */ - let mode = "lazy"; - let include = null; - let exclude = null; - /** @type {string[][] | null} */ - let exports = null; - /** @type {RawChunkGroupOptions} */ - const groupOptions = {}; + get type() { + return "accepted harmony modules"; + } - const { options: importOptions, errors: commentErrors } = - parser.parseCommentOptions(expr.range); + serialize(context) { + const { write } = context; + write(this.range); + write(this.dependencies); + write(this.hasCallback); + super.serialize(context); + } - if (commentErrors) { - for (const e of commentErrors) { - const { comment } = e; - parser.state.module.addWarning( - new CommentCompilationWarning( - `Compilation error while processing magic comment(-s): /*${comment.value}*/: ${e.message}`, - comment.loc - ) - ); - } - } + deserialize(context) { + const { read } = context; + this.range = read(); + this.dependencies = read(); + this.hasCallback = read(); + super.deserialize(context); + } +} - if (importOptions) { - if (importOptions.webpackIgnore !== undefined) { - if (typeof importOptions.webpackIgnore !== "boolean") { - parser.state.module.addWarning( - new UnsupportedFeatureWarning( - `\`webpackIgnore\` expected a boolean, but received: ${importOptions.webpackIgnore}.`, - expr.loc - ) - ); - } else { - // Do not instrument `import()` if `webpackIgnore` is `true` - if (importOptions.webpackIgnore) { - return false; - } - } - } - if (importOptions.webpackChunkName !== undefined) { - if (typeof importOptions.webpackChunkName !== "string") { - parser.state.module.addWarning( - new UnsupportedFeatureWarning( - `\`webpackChunkName\` expected a string, but received: ${importOptions.webpackChunkName}.`, - expr.loc - ) - ); - } else { - chunkName = importOptions.webpackChunkName; - } - } - if (importOptions.webpackMode !== undefined) { - if (typeof importOptions.webpackMode !== "string") { - parser.state.module.addWarning( - new UnsupportedFeatureWarning( - `\`webpackMode\` expected a string, but received: ${importOptions.webpackMode}.`, - expr.loc - ) - ); - } else { - mode = importOptions.webpackMode; - } - } - if (importOptions.webpackPrefetch !== undefined) { - if (importOptions.webpackPrefetch === true) { - groupOptions.prefetchOrder = 0; - } else if (typeof importOptions.webpackPrefetch === "number") { - groupOptions.prefetchOrder = importOptions.webpackPrefetch; - } else { - parser.state.module.addWarning( - new UnsupportedFeatureWarning( - `\`webpackPrefetch\` expected true or a number, but received: ${importOptions.webpackPrefetch}.`, - expr.loc - ) - ); - } - } - if (importOptions.webpackPreload !== undefined) { - if (importOptions.webpackPreload === true) { - groupOptions.preloadOrder = 0; - } else if (typeof importOptions.webpackPreload === "number") { - groupOptions.preloadOrder = importOptions.webpackPreload; - } else { - parser.state.module.addWarning( - new UnsupportedFeatureWarning( - `\`webpackPreload\` expected true or a number, but received: ${importOptions.webpackPreload}.`, - expr.loc - ) - ); - } - } - if (importOptions.webpackInclude !== undefined) { - if ( - !importOptions.webpackInclude || - importOptions.webpackInclude.constructor.name !== "RegExp" - ) { - parser.state.module.addWarning( - new UnsupportedFeatureWarning( - `\`webpackInclude\` expected a regular expression, but received: ${importOptions.webpackInclude}.`, - expr.loc - ) - ); - } else { - include = new RegExp(importOptions.webpackInclude); - } - } - if (importOptions.webpackExclude !== undefined) { - if ( - !importOptions.webpackExclude || - importOptions.webpackExclude.constructor.name !== "RegExp" - ) { - parser.state.module.addWarning( - new UnsupportedFeatureWarning( - `\`webpackExclude\` expected a regular expression, but received: ${importOptions.webpackExclude}.`, - expr.loc - ) - ); - } else { - exclude = new RegExp(importOptions.webpackExclude); - } - } - if (importOptions.webpackExports !== undefined) { - if ( - !( - typeof importOptions.webpackExports === "string" || - (Array.isArray(importOptions.webpackExports) && - importOptions.webpackExports.every( - item => typeof item === "string" - )) - ) - ) { - parser.state.module.addWarning( - new UnsupportedFeatureWarning( - `\`webpackExports\` expected a string or an array of strings, but received: ${importOptions.webpackExports}.`, - expr.loc - ) - ); - } else { - if (typeof importOptions.webpackExports === "string") { - exports = [[importOptions.webpackExports]]; - } else { - exports = Array.from(importOptions.webpackExports, e => [e]); - } - } - } - } +makeSerializable( + HarmonyAcceptDependency, + "webpack/lib/dependencies/HarmonyAcceptDependency" +); - if (param.isString()) { - if (mode !== "lazy" && mode !== "eager" && mode !== "weak") { - parser.state.module.addWarning( - new UnsupportedFeatureWarning( - `\`webpackMode\` expected 'lazy', 'eager' or 'weak', but received: ${mode}.`, - expr.loc - ) - ); +HarmonyAcceptDependency.Template = class HarmonyAcceptDependencyTemplate extends ( + NullDependency.Template +) { + /** + * @param {Dependency} dependency the dependency for which the template should be applied + * @param {ReplaceSource} source the current replace source which can be modified + * @param {DependencyTemplateContext} templateContext the context object + * @returns {void} + */ + apply(dependency, source, templateContext) { + const dep = /** @type {HarmonyAcceptDependency} */ (dependency); + const { + module, + runtime, + runtimeRequirements, + runtimeTemplate, + moduleGraph, + chunkGraph + } = templateContext; + const content = dep.dependencies + .map(dependency => { + const referencedModule = moduleGraph.getModule(dependency); + return { + dependency, + runtimeCondition: referencedModule + ? HarmonyImportDependency.Template.getImportEmittedRuntime( + module, + referencedModule + ) + : false + }; + }) + .filter(({ runtimeCondition }) => runtimeCondition !== false) + .map(({ dependency, runtimeCondition }) => { + const condition = runtimeTemplate.runtimeConditionExpression({ + chunkGraph, + runtime, + runtimeCondition, + runtimeRequirements + }); + const s = dependency.getImportStatement(true, templateContext); + const code = s[0] + s[1]; + if (condition !== "true") { + return `if (${condition}) {\n${Template.indent(code)}\n}\n`; } + return code; + }) + .join(""); - if (mode === "eager") { - const dep = new ImportEagerDependency( - param.string, - expr.range, - exports - ); - parser.state.current.addDependency(dep); - } else if (mode === "weak") { - const dep = new ImportWeakDependency( - param.string, - expr.range, - exports - ); - parser.state.current.addDependency(dep); - } else { - const depBlock = new AsyncDependenciesBlock( - { - ...groupOptions, - name: chunkName - }, - expr.loc, - param.string - ); - const dep = new ImportDependency(param.string, expr.range, exports); - dep.loc = expr.loc; - depBlock.addDependency(dep); - parser.state.current.addBlock(depBlock); - } - return true; + if (dep.hasCallback) { + if (runtimeTemplate.supportsArrowFunction()) { + source.insert( + dep.range[0], + `__WEBPACK_OUTDATED_DEPENDENCIES__ => { ${content}(` + ); + source.insert(dep.range[1], ")(__WEBPACK_OUTDATED_DEPENDENCIES__); }"); } else { - if ( - mode !== "lazy" && - mode !== "lazy-once" && - mode !== "eager" && - mode !== "weak" - ) { - parser.state.module.addWarning( - new UnsupportedFeatureWarning( - `\`webpackMode\` expected 'lazy', 'lazy-once', 'eager' or 'weak', but received: ${mode}.`, - expr.loc - ) - ); - mode = "lazy"; - } - - if (mode === "weak") { - mode = "async-weak"; - } - const dep = ContextDependencyHelpers.create( - ImportContextDependency, - expr.range, - param, - expr, - this.options, - { - chunkName, - groupOptions, - include, - exclude, - mode, - namespaceObject: parser.state.module.buildMeta.strictHarmonyModule - ? "strict" - : true, - typePrefix: "import()", - category: "esm", - referencedExports: exports - }, - parser + source.insert( + dep.range[0], + `function(__WEBPACK_OUTDATED_DEPENDENCIES__) { ${content}(` + ); + source.insert( + dep.range[1], + ")(__WEBPACK_OUTDATED_DEPENDENCIES__); }.bind(this)" ); - if (!dep) return; - dep.loc = expr.loc; - dep.optional = !!parser.scope.inTry; - parser.state.current.addDependency(dep); - return true; } - }); + return; + } + + const arrow = runtimeTemplate.supportsArrowFunction(); + source.insert( + dep.range[1] - 0.5, + `, ${arrow ? "() =>" : "function()"} { ${content} }` + ); } -} +}; -module.exports = ImportParserPlugin; +module.exports = HarmonyAcceptDependency; /***/ }), -/***/ 77199: +/***/ 35316: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; @@ -82522,86 +80016,39 @@ module.exports = ImportParserPlugin; -const ImportContextDependency = __webpack_require__(75785); -const ImportDependency = __webpack_require__(16727); -const ImportEagerDependency = __webpack_require__(91941); -const ImportParserPlugin = __webpack_require__(44136); -const ImportWeakDependency = __webpack_require__(58426); - -/** @typedef {import("../Compiler")} Compiler */ - -class ImportPlugin { - /** - * Apply the plugin - * @param {Compiler} compiler the compiler instance - * @returns {void} - */ - apply(compiler) { - compiler.hooks.compilation.tap( - "ImportPlugin", - (compilation, { contextModuleFactory, normalModuleFactory }) => { - compilation.dependencyFactories.set( - ImportDependency, - normalModuleFactory - ); - compilation.dependencyTemplates.set( - ImportDependency, - new ImportDependency.Template() - ); +const makeSerializable = __webpack_require__(26522); +const HarmonyImportDependency = __webpack_require__(19577); - compilation.dependencyFactories.set( - ImportEagerDependency, - normalModuleFactory - ); - compilation.dependencyTemplates.set( - ImportEagerDependency, - new ImportEagerDependency.Template() - ); +/** @typedef {import("webpack-sources").ReplaceSource} ReplaceSource */ +/** @typedef {import("../Dependency")} Dependency */ +/** @typedef {import("../DependencyTemplate").DependencyTemplateContext} DependencyTemplateContext */ - compilation.dependencyFactories.set( - ImportWeakDependency, - normalModuleFactory - ); - compilation.dependencyTemplates.set( - ImportWeakDependency, - new ImportWeakDependency.Template() - ); +class HarmonyAcceptImportDependency extends HarmonyImportDependency { + constructor(request) { + super(request, NaN); + this.weak = true; + } - compilation.dependencyFactories.set( - ImportContextDependency, - contextModuleFactory - ); - compilation.dependencyTemplates.set( - ImportContextDependency, - new ImportContextDependency.Template() - ); + get type() { + return "harmony accept"; + } +} - const handler = (parser, parserOptions) => { - if (parserOptions.import !== undefined && !parserOptions.import) - return; +makeSerializable( + HarmonyAcceptImportDependency, + "webpack/lib/dependencies/HarmonyAcceptImportDependency" +); - new ImportParserPlugin(parserOptions).apply(parser); - }; +HarmonyAcceptImportDependency.Template = class HarmonyAcceptImportDependencyTemplate extends ( + HarmonyImportDependency.Template +) {}; - normalModuleFactory.hooks.parser - .for("javascript/auto") - .tap("ImportPlugin", handler); - normalModuleFactory.hooks.parser - .for("javascript/dynamic") - .tap("ImportPlugin", handler); - normalModuleFactory.hooks.parser - .for("javascript/esm") - .tap("ImportPlugin", handler); - } - ); - } -} -module.exports = ImportPlugin; +module.exports = HarmonyAcceptImportDependency; /***/ }), -/***/ 58426: +/***/ 56164: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; @@ -82612,38 +80059,30 @@ module.exports = ImportPlugin; +const { UsageState } = __webpack_require__(4295); +const InitFragment = __webpack_require__(51739); +const RuntimeGlobals = __webpack_require__(49404); const makeSerializable = __webpack_require__(26522); -const ImportDependency = __webpack_require__(16727); +const NullDependency = __webpack_require__(65845); /** @typedef {import("webpack-sources").ReplaceSource} ReplaceSource */ /** @typedef {import("../Dependency")} Dependency */ -/** @typedef {import("../Dependency").ReferencedExport} ReferencedExport */ /** @typedef {import("../DependencyTemplate").DependencyTemplateContext} DependencyTemplateContext */ -/** @typedef {import("../ModuleGraph")} ModuleGraph */ - -class ImportWeakDependency extends ImportDependency { - /** - * @param {string} request the request - * @param {[number, number]} range expression range - * @param {string[][]=} referencedExports list of referenced exports - */ - constructor(request, range, referencedExports) { - super(request, range, referencedExports); - this.weak = true; - } +/** @typedef {import("../Module")} Module */ +class HarmonyCompatibilityDependency extends NullDependency { get type() { - return "import() weak"; + return "harmony export header"; } } makeSerializable( - ImportWeakDependency, - "webpack/lib/dependencies/ImportWeakDependency" + HarmonyCompatibilityDependency, + "webpack/lib/dependencies/HarmonyCompatibilityDependency" ); -ImportWeakDependency.Template = class ImportDependencyTemplate extends ( - ImportDependency.Template +HarmonyCompatibilityDependency.Template = class HarmonyExportDependencyTemplate extends ( + NullDependency.Template ) { /** * @param {Dependency} dependency the dependency for which the template should be applied @@ -82654,29 +80093,61 @@ ImportWeakDependency.Template = class ImportDependencyTemplate extends ( apply( dependency, source, - { runtimeTemplate, module, moduleGraph, chunkGraph, runtimeRequirements } + { + module, + runtimeTemplate, + moduleGraph, + initFragments, + runtimeRequirements, + runtime, + concatenationScope + } ) { - const dep = /** @type {ImportWeakDependency} */ (dependency); - const content = runtimeTemplate.moduleNamespacePromise({ - chunkGraph, - module: moduleGraph.getModule(dep), - request: dep.request, - strict: module.buildMeta.strictHarmonyModule, - message: "import() weak", - weak: true, - runtimeRequirements - }); - - source.replace(dep.range[0], dep.range[1] - 1, content); + if (concatenationScope) return; + const exportsInfo = moduleGraph.getExportsInfo(module); + if ( + exportsInfo.getReadOnlyExportInfo("__esModule").getUsed(runtime) !== + UsageState.Unused + ) { + const content = runtimeTemplate.defineEsModuleFlagStatement({ + exportsArgument: module.exportsArgument, + runtimeRequirements + }); + initFragments.push( + new InitFragment( + content, + InitFragment.STAGE_HARMONY_EXPORTS, + 0, + "harmony compatibility" + ) + ); + } + if (moduleGraph.isAsync(module)) { + runtimeRequirements.add(RuntimeGlobals.module); + runtimeRequirements.add(RuntimeGlobals.asyncModule); + initFragments.push( + new InitFragment( + runtimeTemplate.supportsArrowFunction() + ? `${RuntimeGlobals.asyncModule}(${module.moduleArgument}, async (__webpack_handle_async_dependencies__) => {\n` + : `${RuntimeGlobals.asyncModule}(${module.moduleArgument}, async function (__webpack_handle_async_dependencies__) {\n`, + InitFragment.STAGE_ASYNC_BOUNDARY, + 0, + undefined, + module.buildMeta.async + ? `\n__webpack_handle_async_dependencies__();\n}, 1);` + : "\n});" + ) + ); + } } }; -module.exports = ImportWeakDependency; +module.exports = HarmonyCompatibilityDependency; /***/ }), -/***/ 36986: +/***/ 63683: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; @@ -82687,53 +80158,328 @@ module.exports = ImportWeakDependency; -const makeSerializable = __webpack_require__(26522); -const NullDependency = __webpack_require__(65845); +const DynamicExports = __webpack_require__(87370); +const HarmonyCompatibilityDependency = __webpack_require__(56164); +const HarmonyExports = __webpack_require__(37637); -/** @typedef {import("../ChunkGraph")} ChunkGraph */ -/** @typedef {import("../Dependency").ExportSpec} ExportSpec */ -/** @typedef {import("../Dependency").ExportsSpec} ExportsSpec */ -/** @typedef {import("../Dependency").UpdateHashContext} UpdateHashContext */ -/** @typedef {import("../ModuleGraph")} ModuleGraph */ -/** @typedef {import("../util/Hash")} Hash */ +module.exports = class HarmonyDetectionParserPlugin { + constructor(options) { + const { topLevelAwait = false } = options || {}; + this.topLevelAwait = topLevelAwait; + } -const getExportsFromData = data => { - if (data && typeof data === "object") { - if (Array.isArray(data)) { - return data.map((item, idx) => { - return { - name: `${idx}`, - canMangle: true, - exports: getExportsFromData(item) + apply(parser) { + parser.hooks.program.tap("HarmonyDetectionParserPlugin", ast => { + const isStrictHarmony = parser.state.module.type === "javascript/esm"; + const isHarmony = + isStrictHarmony || + ast.body.some( + statement => + statement.type === "ImportDeclaration" || + statement.type === "ExportDefaultDeclaration" || + statement.type === "ExportNamedDeclaration" || + statement.type === "ExportAllDeclaration" + ); + if (isHarmony) { + const module = parser.state.module; + const compatDep = new HarmonyCompatibilityDependency(); + compatDep.loc = { + start: { + line: -1, + column: 0 + }, + end: { + line: -1, + column: 0 + }, + index: -3 }; - }); - } else { - const exports = []; - for (const key of Object.keys(data)) { - exports.push({ - name: key, - canMangle: true, - exports: getExportsFromData(data[key]) - }); + module.addPresentationalDependency(compatDep); + DynamicExports.bailout(parser.state); + HarmonyExports.enable(parser.state, isStrictHarmony); + parser.scope.isStrict = true; } - return exports; + }); + + parser.hooks.topLevelAwait.tap("HarmonyDetectionParserPlugin", () => { + const module = parser.state.module; + if (!this.topLevelAwait) { + throw new Error( + "The top-level-await experiment is not enabled (set experiments.topLevelAwait: true to enabled it)" + ); + } + if (!HarmonyExports.isEnabled(parser.state)) { + throw new Error( + "Top-level-await is only supported in EcmaScript Modules" + ); + } + module.buildMeta.async = true; + }); + + const skipInHarmony = () => { + if (HarmonyExports.isEnabled(parser.state)) { + return true; + } + }; + + const nullInHarmony = () => { + if (HarmonyExports.isEnabled(parser.state)) { + return null; + } + }; + + const nonHarmonyIdentifiers = ["define", "exports"]; + for (const identifier of nonHarmonyIdentifiers) { + parser.hooks.evaluateTypeof + .for(identifier) + .tap("HarmonyDetectionParserPlugin", nullInHarmony); + parser.hooks.typeof + .for(identifier) + .tap("HarmonyDetectionParserPlugin", skipInHarmony); + parser.hooks.evaluate + .for(identifier) + .tap("HarmonyDetectionParserPlugin", nullInHarmony); + parser.hooks.expression + .for(identifier) + .tap("HarmonyDetectionParserPlugin", skipInHarmony); + parser.hooks.call + .for(identifier) + .tap("HarmonyDetectionParserPlugin", skipInHarmony); } } - return undefined; }; -class JsonExportsDependency extends NullDependency { - /** - * @param {(string | ExportSpec)[]} exports json exports - */ - constructor(exports) { + +/***/ }), + +/***/ 70925: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ + + + +const InnerGraph = __webpack_require__(92886); +const ConstDependency = __webpack_require__(60864); +const HarmonyExportExpressionDependency = __webpack_require__(22705); +const HarmonyExportHeaderDependency = __webpack_require__(67159); +const HarmonyExportImportedSpecifierDependency = __webpack_require__(77952); +const HarmonyExportSpecifierDependency = __webpack_require__(59042); +const { ExportPresenceModes } = __webpack_require__(19577); +const { + harmonySpecifierTag, + getAssertions +} = __webpack_require__(76581); +const HarmonyImportSideEffectDependency = __webpack_require__(76853); + +const { HarmonyStarExportsList } = HarmonyExportImportedSpecifierDependency; + +module.exports = class HarmonyExportDependencyParserPlugin { + constructor(options) { + this.exportPresenceMode = + options.reexportExportsPresence !== undefined + ? ExportPresenceModes.fromUserOption(options.reexportExportsPresence) + : options.exportsPresence !== undefined + ? ExportPresenceModes.fromUserOption(options.exportsPresence) + : options.strictExportPresence + ? ExportPresenceModes.ERROR + : ExportPresenceModes.AUTO; + } + + apply(parser) { + const { exportPresenceMode } = this; + parser.hooks.export.tap( + "HarmonyExportDependencyParserPlugin", + statement => { + const dep = new HarmonyExportHeaderDependency( + statement.declaration && statement.declaration.range, + statement.range + ); + dep.loc = Object.create(statement.loc); + dep.loc.index = -1; + parser.state.module.addPresentationalDependency(dep); + return true; + } + ); + parser.hooks.exportImport.tap( + "HarmonyExportDependencyParserPlugin", + (statement, source) => { + parser.state.lastHarmonyImportOrder = + (parser.state.lastHarmonyImportOrder || 0) + 1; + const clearDep = new ConstDependency("", statement.range); + clearDep.loc = Object.create(statement.loc); + clearDep.loc.index = -1; + parser.state.module.addPresentationalDependency(clearDep); + const sideEffectDep = new HarmonyImportSideEffectDependency( + source, + parser.state.lastHarmonyImportOrder, + getAssertions(statement) + ); + sideEffectDep.loc = Object.create(statement.loc); + sideEffectDep.loc.index = -1; + parser.state.current.addDependency(sideEffectDep); + return true; + } + ); + parser.hooks.exportExpression.tap( + "HarmonyExportDependencyParserPlugin", + (statement, expr) => { + const isFunctionDeclaration = expr.type === "FunctionDeclaration"; + const comments = parser.getComments([ + statement.range[0], + expr.range[0] + ]); + const dep = new HarmonyExportExpressionDependency( + expr.range, + statement.range, + comments + .map(c => { + switch (c.type) { + case "Block": + return `/*${c.value}*/`; + case "Line": + return `//${c.value}\n`; + } + return ""; + }) + .join(""), + expr.type.endsWith("Declaration") && expr.id + ? expr.id.name + : isFunctionDeclaration + ? { + id: expr.id ? expr.id.name : undefined, + range: [ + expr.range[0], + expr.params.length > 0 + ? expr.params[0].range[0] + : expr.body.range[0] + ], + prefix: `${expr.async ? "async " : ""}function${ + expr.generator ? "*" : "" + } `, + suffix: `(${expr.params.length > 0 ? "" : ") "}` + } + : undefined + ); + dep.loc = Object.create(statement.loc); + dep.loc.index = -1; + parser.state.current.addDependency(dep); + InnerGraph.addVariableUsage( + parser, + expr.type.endsWith("Declaration") && expr.id + ? expr.id.name + : "*default*", + "default" + ); + return true; + } + ); + parser.hooks.exportSpecifier.tap( + "HarmonyExportDependencyParserPlugin", + (statement, id, name, idx) => { + const settings = parser.getTagData(id, harmonySpecifierTag); + let dep; + const harmonyNamedExports = (parser.state.harmonyNamedExports = + parser.state.harmonyNamedExports || new Set()); + harmonyNamedExports.add(name); + InnerGraph.addVariableUsage(parser, id, name); + if (settings) { + dep = new HarmonyExportImportedSpecifierDependency( + settings.source, + settings.sourceOrder, + settings.ids, + name, + harmonyNamedExports, + null, + exportPresenceMode, + null, + settings.assertions + ); + } else { + dep = new HarmonyExportSpecifierDependency(id, name); + } + dep.loc = Object.create(statement.loc); + dep.loc.index = idx; + parser.state.current.addDependency(dep); + return true; + } + ); + parser.hooks.exportImportSpecifier.tap( + "HarmonyExportDependencyParserPlugin", + (statement, source, id, name, idx) => { + const harmonyNamedExports = (parser.state.harmonyNamedExports = + parser.state.harmonyNamedExports || new Set()); + let harmonyStarExports = null; + if (name) { + harmonyNamedExports.add(name); + } else { + harmonyStarExports = parser.state.harmonyStarExports = + parser.state.harmonyStarExports || new HarmonyStarExportsList(); + } + const dep = new HarmonyExportImportedSpecifierDependency( + source, + parser.state.lastHarmonyImportOrder, + id ? [id] : [], + name, + harmonyNamedExports, + harmonyStarExports && harmonyStarExports.slice(), + exportPresenceMode, + harmonyStarExports + ); + if (harmonyStarExports) { + harmonyStarExports.push(dep); + } + dep.loc = Object.create(statement.loc); + dep.loc.index = idx; + parser.state.current.addDependency(dep); + return true; + } + ); + } +}; + + +/***/ }), + +/***/ 22705: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ + + + +const ConcatenationScope = __webpack_require__(14067); +const RuntimeGlobals = __webpack_require__(49404); +const makeSerializable = __webpack_require__(26522); +const HarmonyExportInitFragment = __webpack_require__(68664); +const NullDependency = __webpack_require__(65845); + +/** @typedef {import("webpack-sources").ReplaceSource} ReplaceSource */ +/** @typedef {import("../Dependency")} Dependency */ +/** @typedef {import("../Dependency").ExportsSpec} ExportsSpec */ +/** @typedef {import("../DependencyTemplate").DependencyTemplateContext} DependencyTemplateContext */ +/** @typedef {import("../ModuleGraph")} ModuleGraph */ +/** @typedef {import("../ModuleGraphConnection").ConnectionState} ConnectionState */ + +class HarmonyExportExpressionDependency extends NullDependency { + constructor(range, rangeStatement, prefix, declarationId) { super(); - this.exports = exports; - this._hashUpdate = undefined; + this.range = range; + this.rangeStatement = rangeStatement; + this.prefix = prefix; + this.declarationId = declarationId; } get type() { - return "json exports"; + return "harmony export expression"; } /** @@ -82743,441 +80489,161 @@ class JsonExportsDependency extends NullDependency { */ getExports(moduleGraph) { return { - exports: this.exports, + exports: ["default"], + priority: 1, + terminalBinding: true, dependencies: undefined }; } /** - * Update the hash - * @param {Hash} hash hash to be updated - * @param {UpdateHashContext} context context - * @returns {void} + * @param {ModuleGraph} moduleGraph the module graph + * @returns {ConnectionState} how this dependency connects the module to referencing modules */ - updateHash(hash, context) { - if (this._hashUpdate === undefined) { - this._hashUpdate = this.exports - ? JSON.stringify(this.exports) - : "undefined"; - } - hash.update(this._hashUpdate); + getModuleEvaluationSideEffectsState(moduleGraph) { + // The expression/declaration is already covered by SideEffectsFlagPlugin + return false; } serialize(context) { const { write } = context; - write(this.exports); + write(this.range); + write(this.rangeStatement); + write(this.prefix); + write(this.declarationId); super.serialize(context); } deserialize(context) { const { read } = context; - this.exports = read(); + this.range = read(); + this.rangeStatement = read(); + this.prefix = read(); + this.declarationId = read(); super.deserialize(context); } } makeSerializable( - JsonExportsDependency, - "webpack/lib/dependencies/JsonExportsDependency" + HarmonyExportExpressionDependency, + "webpack/lib/dependencies/HarmonyExportExpressionDependency" ); -module.exports = JsonExportsDependency; -module.exports.getExportsFromData = getExportsFromData; - - -/***/ }), - -/***/ 52067: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ - - - -const ModuleDependency = __webpack_require__(80944); - -class LoaderDependency extends ModuleDependency { - /** - * @param {string} request request string - */ - constructor(request) { - super(request); - } - - get type() { - return "loader"; - } - - get category() { - return "loader"; - } -} - -module.exports = LoaderDependency; - - -/***/ }), - -/***/ 33824: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ - - - -const ModuleDependency = __webpack_require__(80944); - -class LoaderImportDependency extends ModuleDependency { - /** - * @param {string} request request string - */ - constructor(request) { - super(request); - this.weak = true; - } - - get type() { - return "loader import"; - } - - get category() { - return "loaderImport"; - } -} - -module.exports = LoaderImportDependency; - - -/***/ }), - -/***/ 34204: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ - - - -const NormalModule = __webpack_require__(11026); -const LazySet = __webpack_require__(59534); -const LoaderDependency = __webpack_require__(52067); -const LoaderImportDependency = __webpack_require__(33824); - -/** @typedef {import("../Compilation").DepConstructor} DepConstructor */ -/** @typedef {import("../Compiler")} Compiler */ -/** @typedef {import("../Module")} Module */ - -/** - * @callback LoadModuleCallback - * @param {Error=} err error object - * @param {string | Buffer=} source source code - * @param {object=} map source map - * @param {Module=} module loaded module if successful - */ - -/** - * @callback ImportModuleCallback - * @param {Error=} err error object - * @param {any=} exports exports of the evaluated module - */ - -/** - * @typedef {Object} ImportModuleOptions - * @property {string=} layer the target layer - * @property {string=} publicPath the target public path - */ - -class LoaderPlugin { - /** - * @param {Object} options options - */ - constructor(options = {}) {} - +HarmonyExportExpressionDependency.Template = class HarmonyExportDependencyTemplate extends ( + NullDependency.Template +) { /** - * Apply the plugin - * @param {Compiler} compiler the compiler instance + * @param {Dependency} dependency the dependency for which the template should be applied + * @param {ReplaceSource} source the current replace source which can be modified + * @param {DependencyTemplateContext} templateContext the context object * @returns {void} */ - apply(compiler) { - compiler.hooks.compilation.tap( - "LoaderPlugin", - (compilation, { normalModuleFactory }) => { - compilation.dependencyFactories.set( - LoaderDependency, - normalModuleFactory - ); - compilation.dependencyFactories.set( - LoaderImportDependency, - normalModuleFactory + apply( + dependency, + source, + { + module, + moduleGraph, + runtimeTemplate, + runtimeRequirements, + initFragments, + runtime, + concatenationScope + } + ) { + const dep = /** @type {HarmonyExportExpressionDependency} */ (dependency); + const { declarationId } = dep; + const exportsName = module.exportsArgument; + if (declarationId) { + let name; + if (typeof declarationId === "string") { + name = declarationId; + } else { + name = ConcatenationScope.DEFAULT_EXPORT; + source.replace( + declarationId.range[0], + declarationId.range[1] - 1, + `${declarationId.prefix}${name}${declarationId.suffix}` ); } - ); - - compiler.hooks.compilation.tap("LoaderPlugin", compilation => { - const moduleGraph = compilation.moduleGraph; - NormalModule.getCompilationHooks(compilation).loader.tap( - "LoaderPlugin", - loaderContext => { - /** - * @param {string} request the request string to load the module from - * @param {LoadModuleCallback} callback callback returning the loaded module or error - * @returns {void} - */ - loaderContext.loadModule = (request, callback) => { - const dep = new LoaderDependency(request); - dep.loc = { - name: request - }; - const factory = compilation.dependencyFactories.get( - /** @type {DepConstructor} */ (dep.constructor) - ); - if (factory === undefined) { - return callback( - new Error( - `No module factory available for dependency type: ${dep.constructor.name}` - ) - ); - } - compilation.buildQueue.increaseParallelism(); - compilation.handleModuleCreation( - { - factory, - dependencies: [dep], - originModule: loaderContext._module, - context: loaderContext.context, - recursive: false - }, - err => { - compilation.buildQueue.decreaseParallelism(); - if (err) { - return callback(err); - } - const referencedModule = moduleGraph.getModule(dep); - if (!referencedModule) { - return callback(new Error("Cannot load the module")); - } - if (referencedModule.getNumberOfErrors() > 0) { - return callback( - new Error("The loaded module contains errors") - ); - } - const moduleSource = referencedModule.originalSource(); - if (!moduleSource) { - return callback( - new Error( - "The module created for a LoaderDependency must have an original source" - ) - ); - } - let source, map; - if (moduleSource.sourceAndMap) { - const sourceAndMap = moduleSource.sourceAndMap(); - map = sourceAndMap.map; - source = sourceAndMap.source; - } else { - map = moduleSource.map(); - source = moduleSource.source(); - } - const fileDependencies = new LazySet(); - const contextDependencies = new LazySet(); - const missingDependencies = new LazySet(); - const buildDependencies = new LazySet(); - referencedModule.addCacheDependencies( - fileDependencies, - contextDependencies, - missingDependencies, - buildDependencies - ); - - for (const d of fileDependencies) { - loaderContext.addDependency(d); - } - for (const d of contextDependencies) { - loaderContext.addContextDependency(d); - } - for (const d of missingDependencies) { - loaderContext.addMissingDependency(d); - } - for (const d of buildDependencies) { - loaderContext.addBuildDependency(d); - } - return callback(null, source, map, referencedModule); - } - ); - }; - - /** - * @param {string} request the request string to load the module from - * @param {ImportModuleOptions=} options options - * @param {ImportModuleCallback=} callback callback returning the exports - * @returns {void} - */ - const importModule = (request, options, callback) => { - const dep = new LoaderImportDependency(request); - dep.loc = { - name: request - }; - const factory = compilation.dependencyFactories.get( - /** @type {DepConstructor} */ (dep.constructor) - ); - if (factory === undefined) { - return callback( - new Error( - `No module factory available for dependency type: ${dep.constructor.name}` - ) - ); - } - compilation.buildQueue.increaseParallelism(); - compilation.handleModuleCreation( - { - factory, - dependencies: [dep], - originModule: loaderContext._module, - contextInfo: { - issuerLayer: options.layer - }, - context: loaderContext.context, - connectOrigin: false - }, - err => { - compilation.buildQueue.decreaseParallelism(); - if (err) { - return callback(err); - } - const referencedModule = moduleGraph.getModule(dep); - if (!referencedModule) { - return callback(new Error("Cannot load the module")); - } - compilation.executeModule( - referencedModule, - { - entryOptions: { - publicPath: options.publicPath - } - }, - (err, result) => { - if (err) return callback(err); - for (const d of result.fileDependencies) { - loaderContext.addDependency(d); - } - for (const d of result.contextDependencies) { - loaderContext.addContextDependency(d); - } - for (const d of result.missingDependencies) { - loaderContext.addMissingDependency(d); - } - for (const d of result.buildDependencies) { - loaderContext.addBuildDependency(d); - } - if (result.cacheable === false) - loaderContext.cacheable(false); - for (const [name, { source, info }] of result.assets) { - const { buildInfo } = loaderContext._module; - if (!buildInfo.assets) { - buildInfo.assets = Object.create(null); - buildInfo.assetsInfo = new Map(); - } - buildInfo.assets[name] = source; - buildInfo.assetsInfo.set(name, info); - } - callback(null, result.exports); - } - ); - } - ); - }; - /** - * @param {string} request the request string to load the module from - * @param {ImportModuleOptions} options options - * @param {ImportModuleCallback=} callback callback returning the exports - * @returns {Promise | void} exports - */ - loaderContext.importModule = (request, options, callback) => { - if (!callback) { - return new Promise((resolve, reject) => { - importModule(request, options || {}, (err, result) => { - if (err) reject(err); - else resolve(result); - }); - }); - } - return importModule(request, options || {}, callback); - }; + if (concatenationScope) { + concatenationScope.registerExport("default", name); + } else { + const used = moduleGraph + .getExportsInfo(module) + .getUsedName("default", runtime); + if (used) { + const map = new Map(); + map.set(used, `/* export default binding */ ${name}`); + initFragments.push(new HarmonyExportInitFragment(exportsName, map)); } - ); - }); - } -} -module.exports = LoaderPlugin; - - -/***/ }), - -/***/ 930: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ - - - -const makeSerializable = __webpack_require__(26522); - -class LocalModule { - constructor(name, idx) { - this.name = name; - this.idx = idx; - this.used = false; - } - - flagUsed() { - this.used = true; - } - - variableName() { - return "__WEBPACK_LOCAL_MODULE_" + this.idx + "__"; - } - - serialize(context) { - const { write } = context; + } - write(this.name); - write(this.idx); - write(this.used); - } + source.replace( + dep.rangeStatement[0], + dep.range[0] - 1, + `/* harmony default export */ ${dep.prefix}` + ); + } else { + let content; + const name = ConcatenationScope.DEFAULT_EXPORT; + if (runtimeTemplate.supportsConst()) { + content = `/* harmony default export */ const ${name} = `; + if (concatenationScope) { + concatenationScope.registerExport("default", name); + } else { + const used = moduleGraph + .getExportsInfo(module) + .getUsedName("default", runtime); + if (used) { + runtimeRequirements.add(RuntimeGlobals.exports); + const map = new Map(); + map.set(used, name); + initFragments.push(new HarmonyExportInitFragment(exportsName, map)); + } else { + content = `/* unused harmony default export */ var ${name} = `; + } + } + } else if (concatenationScope) { + content = `/* harmony default export */ var ${name} = `; + concatenationScope.registerExport("default", name); + } else { + const used = moduleGraph + .getExportsInfo(module) + .getUsedName("default", runtime); + if (used) { + runtimeRequirements.add(RuntimeGlobals.exports); + // This is a little bit incorrect as TDZ is not correct, but we can't use const. + content = `/* harmony default export */ ${exportsName}[${JSON.stringify( + used + )}] = `; + } else { + content = `/* unused harmony default export */ var ${name} = `; + } + } - deserialize(context) { - const { read } = context; + if (dep.range) { + source.replace( + dep.rangeStatement[0], + dep.range[0] - 1, + content + "(" + dep.prefix + ); + source.replace(dep.range[1], dep.rangeStatement[1] - 0.5, ");"); + return; + } - this.name = read(); - this.idx = read(); - this.used = read(); + source.replace(dep.rangeStatement[0], dep.rangeStatement[1] - 1, content); + } } -} - -makeSerializable(LocalModule, "webpack/lib/dependencies/LocalModule"); +}; -module.exports = LocalModule; +module.exports = HarmonyExportExpressionDependency; /***/ }), -/***/ 67494: +/***/ 67159: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; @@ -83195,42 +80661,38 @@ const NullDependency = __webpack_require__(65845); /** @typedef {import("../Dependency")} Dependency */ /** @typedef {import("../DependencyTemplate").DependencyTemplateContext} DependencyTemplateContext */ -class LocalModuleDependency extends NullDependency { - constructor(localModule, range, callNew) { +class HarmonyExportHeaderDependency extends NullDependency { + constructor(range, rangeStatement) { super(); - - this.localModule = localModule; this.range = range; - this.callNew = callNew; + this.rangeStatement = rangeStatement; + } + + get type() { + return "harmony export header"; } serialize(context) { const { write } = context; - - write(this.localModule); write(this.range); - write(this.callNew); - + write(this.rangeStatement); super.serialize(context); } deserialize(context) { const { read } = context; - - this.localModule = read(); this.range = read(); - this.callNew = read(); - + this.rangeStatement = read(); super.deserialize(context); } } makeSerializable( - LocalModuleDependency, - "webpack/lib/dependencies/LocalModuleDependency" + HarmonyExportHeaderDependency, + "webpack/lib/dependencies/HarmonyExportHeaderDependency" ); -LocalModuleDependency.Template = class LocalModuleDependencyTemplate extends ( +HarmonyExportHeaderDependency.Template = class HarmonyExportDependencyTemplate extends ( NullDependency.Template ) { /** @@ -83240,79 +80702,21 @@ LocalModuleDependency.Template = class LocalModuleDependencyTemplate extends ( * @returns {void} */ apply(dependency, source, templateContext) { - const dep = /** @type {LocalModuleDependency} */ (dependency); - if (!dep.range) return; - const moduleInstance = dep.callNew - ? `new (function () { return ${dep.localModule.variableName()}; })()` - : dep.localModule.variableName(); - source.replace(dep.range[0], dep.range[1] - 1, moduleInstance); - } -}; - -module.exports = LocalModuleDependency; - - -/***/ }), - -/***/ 6311: -/***/ (function(__unused_webpack_module, exports, __webpack_require__) { - -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ - - - -const LocalModule = __webpack_require__(930); - -const lookup = (parent, mod) => { - if (mod.charAt(0) !== ".") return mod; - - var path = parent.split("/"); - var segments = mod.split("/"); - path.pop(); - - for (let i = 0; i < segments.length; i++) { - const seg = segments[i]; - if (seg === "..") { - path.pop(); - } else if (seg !== ".") { - path.push(seg); - } - } - - return path.join("/"); -}; - -exports.addLocalModule = (state, name) => { - if (!state.localModules) { - state.localModules = []; + const dep = /** @type {HarmonyExportHeaderDependency} */ (dependency); + const content = ""; + const replaceUntil = dep.range + ? dep.range[0] - 1 + : dep.rangeStatement[1] - 1; + source.replace(dep.rangeStatement[0], replaceUntil, content); } - const m = new LocalModule(name, state.localModules.length); - state.localModules.push(m); - return m; }; -exports.getLocalModule = (state, name, namedModule) => { - if (!state.localModules) return null; - if (namedModule) { - // resolve dependency name relative to the defining named module - name = lookup(namedModule, name); - } - for (let i = 0; i < state.localModules.length; i++) { - if (state.localModules[i].name === name) { - return state.localModules[i]; - } - } - return null; -}; +module.exports = HarmonyExportHeaderDependency; /***/ }), -/***/ 58969: +/***/ 77952: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; @@ -83324,797 +80728,1274 @@ exports.getLocalModule = (state, name, namedModule) => { const Dependency = __webpack_require__(50384); +const { UsageState } = __webpack_require__(4295); +const HarmonyLinkingError = __webpack_require__(42766); const InitFragment = __webpack_require__(51739); const RuntimeGlobals = __webpack_require__(49404); +const Template = __webpack_require__(92066); +const { countIterable } = __webpack_require__(31065); +const { first, combine } = __webpack_require__(34715); const makeSerializable = __webpack_require__(26522); -const NullDependency = __webpack_require__(65845); +const propertyAccess = __webpack_require__(86709); +const { getRuntimeKey, keyToRuntime } = __webpack_require__(19655); +const HarmonyExportInitFragment = __webpack_require__(68664); +const HarmonyImportDependency = __webpack_require__(19577); +const processExportInfo = __webpack_require__(35873); /** @typedef {import("webpack-sources").ReplaceSource} ReplaceSource */ /** @typedef {import("../ChunkGraph")} ChunkGraph */ +/** @typedef {import("../Dependency").ExportsSpec} ExportsSpec */ /** @typedef {import("../Dependency").ReferencedExport} ReferencedExport */ +/** @typedef {import("../Dependency").TRANSITIVE} TRANSITIVE */ /** @typedef {import("../Dependency").UpdateHashContext} UpdateHashContext */ /** @typedef {import("../DependencyTemplate").DependencyTemplateContext} DependencyTemplateContext */ -/** @typedef {import("../DependencyTemplates")} DependencyTemplates */ +/** @typedef {import("../ExportsInfo")} ExportsInfo */ +/** @typedef {import("../ExportsInfo").ExportInfo} ExportInfo */ +/** @typedef {import("../Module")} Module */ /** @typedef {import("../ModuleGraph")} ModuleGraph */ +/** @typedef {import("../ModuleGraphConnection")} ModuleGraphConnection */ +/** @typedef {import("../ModuleGraphConnection").ConnectionState} ConnectionState */ +/** @typedef {import("../RuntimeTemplate")} RuntimeTemplate */ +/** @typedef {import("../WebpackError")} WebpackError */ /** @typedef {import("../util/Hash")} Hash */ /** @typedef {import("../util/runtime").RuntimeSpec} RuntimeSpec */ -class ModuleDecoratorDependency extends NullDependency { +/** @typedef {"missing"|"unused"|"empty-star"|"reexport-dynamic-default"|"reexport-named-default"|"reexport-namespace-object"|"reexport-fake-namespace-object"|"reexport-undefined"|"normal-reexport"|"dynamic-reexport"} ExportModeType */ + +const { ExportPresenceModes } = HarmonyImportDependency; + +const idsSymbol = Symbol("HarmonyExportImportedSpecifierDependency.ids"); + +class NormalReexportItem { /** - * @param {string} decorator the decorator requirement - * @param {boolean} allowExportsAccess allow to access exports from module + * @param {string} name export name + * @param {string[]} ids reexported ids from other module + * @param {ExportInfo} exportInfo export info from other module + * @param {boolean} checked true, if it should be checked at runtime if this export exists + * @param {boolean} hidden true, if it is hidden behind another active export in the same module */ - constructor(decorator, allowExportsAccess) { - super(); - this.decorator = decorator; - this.allowExportsAccess = allowExportsAccess; - this._hashUpdate = undefined; + constructor(name, ids, exportInfo, checked, hidden) { + this.name = name; + this.ids = ids; + this.exportInfo = exportInfo; + this.checked = checked; + this.hidden = hidden; } +} +class ExportMode { /** - * @returns {string} a display name for the type of dependency + * @param {ExportModeType} type type of the mode */ - get type() { - return "module decorator"; - } + constructor(type) { + /** @type {ExportModeType} */ + this.type = type; - get category() { - return "self"; - } + // for "normal-reexport": + /** @type {NormalReexportItem[] | null} */ + this.items = null; - /** - * @returns {string | null} an identifier to merge equal requests - */ - getResourceIdentifier() { - return `self`; + // for "reexport-named-default" | "reexport-fake-namespace-object" | "reexport-namespace-object" + /** @type {string|null} */ + this.name = null; + /** @type {ExportInfo | null} */ + this.partialNamespaceExportInfo = null; + + // for "dynamic-reexport": + /** @type {Set | null} */ + this.ignored = null; + + // for "dynamic-reexport" | "empty-star": + /** @type {Set | null} */ + this.hidden = null; + + // for "missing": + /** @type {string | null} */ + this.userRequest = null; + + // for "reexport-fake-namespace-object": + /** @type {number} */ + this.fakeType = 0; } +} - /** - * Returns list of exports referenced by this dependency - * @param {ModuleGraph} moduleGraph module graph - * @param {RuntimeSpec} runtime the runtime for which the module is analysed - * @returns {(string[] | ReferencedExport)[]} referenced exports - */ - getReferencedExports(moduleGraph, runtime) { - return this.allowExportsAccess - ? Dependency.EXPORTS_OBJECT_REFERENCED - : Dependency.NO_EXPORTS_REFERENCED; +const determineExportAssignments = ( + moduleGraph, + dependencies, + additionalDependency +) => { + const names = new Set(); + const dependencyIndices = []; + + if (additionalDependency) { + dependencies = dependencies.concat(additionalDependency); } - /** - * Update the hash - * @param {Hash} hash hash to be updated - * @param {UpdateHashContext} context context - * @returns {void} - */ - updateHash(hash, context) { - if (this._hashUpdate === undefined) { - this._hashUpdate = `${this.decorator}${this.allowExportsAccess}`; + for (const dep of dependencies) { + const i = dependencyIndices.length; + dependencyIndices[i] = names.size; + const otherImportedModule = moduleGraph.getModule(dep); + if (otherImportedModule) { + const exportsInfo = moduleGraph.getExportsInfo(otherImportedModule); + for (const exportInfo of exportsInfo.exports) { + if ( + exportInfo.provided === true && + exportInfo.name !== "default" && + !names.has(exportInfo.name) + ) { + names.add(exportInfo.name); + dependencyIndices[i] = names.size; + } + } } - hash.update(this._hashUpdate); } + dependencyIndices.push(names.size); - serialize(context) { - const { write } = context; - write(this.decorator); - write(this.allowExportsAccess); - super.serialize(context); + return { names: Array.from(names), dependencyIndices }; +}; + +const findDependencyForName = ( + { names, dependencyIndices }, + name, + dependencies +) => { + const dependenciesIt = dependencies[Symbol.iterator](); + const dependencyIndicesIt = dependencyIndices[Symbol.iterator](); + let dependenciesItResult = dependenciesIt.next(); + let dependencyIndicesItResult = dependencyIndicesIt.next(); + if (dependencyIndicesItResult.done) return; + for (let i = 0; i < names.length; i++) { + while (i >= dependencyIndicesItResult.value) { + dependenciesItResult = dependenciesIt.next(); + dependencyIndicesItResult = dependencyIndicesIt.next(); + if (dependencyIndicesItResult.done) return; + } + if (names[i] === name) return dependenciesItResult.value; } + return undefined; +}; - deserialize(context) { - const { read } = context; - this.decorator = read(); - this.allowExportsAccess = read(); - super.deserialize(context); +/** + * @param {ModuleGraph} moduleGraph the module graph + * @param {HarmonyExportImportedSpecifierDependency} dep the dependency + * @param {string} runtimeKey the runtime key + * @returns {ExportMode} the export mode + */ +const getMode = (moduleGraph, dep, runtimeKey) => { + const importedModule = moduleGraph.getModule(dep); + + if (!importedModule) { + const mode = new ExportMode("missing"); + + mode.userRequest = dep.userRequest; + + return mode; } -} -makeSerializable( - ModuleDecoratorDependency, - "webpack/lib/dependencies/ModuleDecoratorDependency" -); + const name = dep.name; + const runtime = keyToRuntime(runtimeKey); + const parentModule = moduleGraph.getParentModule(dep); + const exportsInfo = moduleGraph.getExportsInfo(parentModule); -ModuleDecoratorDependency.Template = class ModuleDecoratorDependencyTemplate extends ( - NullDependency.Template -) { - /** - * @param {Dependency} dependency the dependency for which the template should be applied - * @param {ReplaceSource} source the current replace source which can be modified - * @param {DependencyTemplateContext} templateContext the context object - * @returns {void} - */ - apply( - dependency, - source, - { module, chunkGraph, initFragments, runtimeRequirements } + if ( + name + ? exportsInfo.getUsed(name, runtime) === UsageState.Unused + : exportsInfo.isUsed(runtime) === false ) { - const dep = /** @type {ModuleDecoratorDependency} */ (dependency); - runtimeRequirements.add(RuntimeGlobals.moduleLoaded); - runtimeRequirements.add(RuntimeGlobals.moduleId); - runtimeRequirements.add(RuntimeGlobals.module); - runtimeRequirements.add(dep.decorator); - initFragments.push( - new InitFragment( - `/* module decorator */ ${module.moduleArgument} = ${dep.decorator}(${module.moduleArgument});\n`, - InitFragment.STAGE_PROVIDES, - 0, - `module decorator ${chunkGraph.getModuleId(module)}` - ) - ); + const mode = new ExportMode("unused"); + + mode.name = name || "*"; + + return mode; } -}; -module.exports = ModuleDecoratorDependency; + const importedExportsType = importedModule.getExportsType( + moduleGraph, + parentModule.buildMeta.strictHarmonyModule + ); + const ids = dep.getIds(moduleGraph); -/***/ }), + // Special handling for reexporting the default export + // from non-namespace modules + if (name && ids.length > 0 && ids[0] === "default") { + switch (importedExportsType) { + case "dynamic": { + const mode = new ExportMode("reexport-dynamic-default"); -/***/ 80944: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + mode.name = name; -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ + return mode; + } + case "default-only": + case "default-with-named": { + const exportInfo = exportsInfo.getReadOnlyExportInfo(name); + const mode = new ExportMode("reexport-named-default"); + mode.name = name; + mode.partialNamespaceExportInfo = exportInfo; + return mode; + } + } + } -const Dependency = __webpack_require__(50384); -const DependencyTemplate = __webpack_require__(17600); -const memoize = __webpack_require__(84297); + // reexporting with a fixed name + if (name) { + let mode; + const exportInfo = exportsInfo.getReadOnlyExportInfo(name); -/** @typedef {import("../Dependency").TRANSITIVE} TRANSITIVE */ -/** @typedef {import("../Module")} Module */ + if (ids.length > 0) { + // export { name as name } + switch (importedExportsType) { + case "default-only": + mode = new ExportMode("reexport-undefined"); + mode.name = name; + break; + default: + mode = new ExportMode("normal-reexport"); + mode.items = [ + new NormalReexportItem(name, ids, exportInfo, false, false) + ]; + break; + } + } else { + // export * as name + switch (importedExportsType) { + case "default-only": + mode = new ExportMode("reexport-fake-namespace-object"); + mode.name = name; + mode.partialNamespaceExportInfo = exportInfo; + mode.fakeType = 0; + break; + case "default-with-named": + mode = new ExportMode("reexport-fake-namespace-object"); + mode.name = name; + mode.partialNamespaceExportInfo = exportInfo; + mode.fakeType = 2; + break; + case "dynamic": + default: + mode = new ExportMode("reexport-namespace-object"); + mode.name = name; + mode.partialNamespaceExportInfo = exportInfo; + } + } -const getRawModule = memoize(() => __webpack_require__(82329)); + return mode; + } -class ModuleDependency extends Dependency { - /** - * @param {string} request request path which needs resolving - */ - constructor(request) { - super(); - this.request = request; - this.userRequest = request; - this.range = undefined; - // assertions must be serialized by subclasses that use it - /** @type {Record | undefined} */ - this.assertions = undefined; + // Star reexporting + + const { ignoredExports, exports, checked, hidden } = dep.getStarReexports( + moduleGraph, + runtime, + exportsInfo, + importedModule + ); + if (!exports) { + // We have too few info about the modules + // Delegate the logic to the runtime code + + const mode = new ExportMode("dynamic-reexport"); + mode.ignored = ignoredExports; + mode.hidden = hidden; + + return mode; + } + + if (exports.size === 0) { + const mode = new ExportMode("empty-star"); + mode.hidden = hidden; + + return mode; + } + + const mode = new ExportMode("normal-reexport"); + + mode.items = Array.from( + exports, + exportName => + new NormalReexportItem( + exportName, + [exportName], + exportsInfo.getReadOnlyExportInfo(exportName), + checked.has(exportName), + false + ) + ); + if (hidden !== undefined) { + for (const exportName of hidden) { + mode.items.push( + new NormalReexportItem( + exportName, + [exportName], + exportsInfo.getReadOnlyExportInfo(exportName), + false, + true + ) + ); + } } + return mode; +}; + +class HarmonyExportImportedSpecifierDependency extends HarmonyImportDependency { /** - * @returns {string | null} an identifier to merge equal requests + * @param {string} request the request string + * @param {number} sourceOrder the order in the original source file + * @param {string[]} ids the requested export name of the imported module + * @param {string | null} name the export name of for this module + * @param {Set} activeExports other named exports in the module + * @param {ReadonlyArray | Iterable} otherStarExports other star exports in the module before this import + * @param {number} exportPresenceMode mode of checking export names + * @param {HarmonyStarExportsList} allStarExports all star exports in the module + * @param {Record=} assertions import assertions */ - getResourceIdentifier() { - let str = `module${this.request}`; - if (this.assertions !== undefined) { - str += JSON.stringify(this.assertions); - } - return str; + constructor( + request, + sourceOrder, + ids, + name, + activeExports, + otherStarExports, + exportPresenceMode, + allStarExports, + assertions + ) { + super(request, sourceOrder, assertions); + + this.ids = ids; + this.name = name; + this.activeExports = activeExports; + this.otherStarExports = otherStarExports; + this.exportPresenceMode = exportPresenceMode; + this.allStarExports = allStarExports; } /** * @returns {boolean | TRANSITIVE} true, when changes to the referenced module could affect the referencing module; TRANSITIVE, when changes to the referenced module could affect referencing modules of the referencing module */ couldAffectReferencingModule() { - return true; + return Dependency.TRANSITIVE; } - /** - * @param {string} context context directory - * @returns {Module} a module - */ - createIgnoredModule(context) { - const RawModule = getRawModule(); - return new RawModule( - "/* (ignored) */", - `ignored|${context}|${this.request}`, - `${this.request} (ignored)` - ); + // TODO webpack 6 remove + get id() { + throw new Error("id was renamed to ids and type changed to string[]"); } - serialize(context) { - const { write } = context; - write(this.request); - write(this.userRequest); - write(this.range); - super.serialize(context); + // TODO webpack 6 remove + getId() { + throw new Error("id was renamed to ids and type changed to string[]"); } - deserialize(context) { - const { read } = context; - this.request = read(); - this.userRequest = read(); - this.range = read(); - super.deserialize(context); + // TODO webpack 6 remove + setId() { + throw new Error("id was renamed to ids and type changed to string[]"); } -} - -ModuleDependency.Template = DependencyTemplate; - -module.exports = ModuleDependency; - - -/***/ }), - -/***/ 35795: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ - + get type() { + return "harmony export imported specifier"; + } -const ModuleDependency = __webpack_require__(80944); - -/** @typedef {import("webpack-sources").ReplaceSource} ReplaceSource */ -/** @typedef {import("../Dependency")} Dependency */ -/** @typedef {import("../DependencyTemplate").DependencyTemplateContext} DependencyTemplateContext */ + /** + * @param {ModuleGraph} moduleGraph the module graph + * @returns {string[]} the imported id + */ + getIds(moduleGraph) { + return moduleGraph.getMeta(this)[idsSymbol] || this.ids; + } -class ModuleDependencyTemplateAsId extends ModuleDependency.Template { /** - * @param {Dependency} dependency the dependency for which the template should be applied - * @param {ReplaceSource} source the current replace source which can be modified - * @param {DependencyTemplateContext} templateContext the context object + * @param {ModuleGraph} moduleGraph the module graph + * @param {string[]} ids the imported ids * @returns {void} */ - apply(dependency, source, { runtimeTemplate, moduleGraph, chunkGraph }) { - const dep = /** @type {ModuleDependency} */ (dependency); - if (!dep.range) return; - const content = runtimeTemplate.moduleId({ - module: moduleGraph.getModule(dep), - chunkGraph, - request: dep.request, - weak: dep.weak - }); - source.replace(dep.range[0], dep.range[1] - 1, content); + setIds(moduleGraph, ids) { + moduleGraph.getMeta(this)[idsSymbol] = ids; } -} - -module.exports = ModuleDependencyTemplateAsId; - - -/***/ }), - -/***/ 77802: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ - - - -const ModuleDependency = __webpack_require__(80944); -/** @typedef {import("webpack-sources").ReplaceSource} ReplaceSource */ -/** @typedef {import("../Dependency")} Dependency */ -/** @typedef {import("../DependencyTemplate").DependencyTemplateContext} DependencyTemplateContext */ - -class ModuleDependencyTemplateAsRequireId extends ModuleDependency.Template { /** - * @param {Dependency} dependency the dependency for which the template should be applied - * @param {ReplaceSource} source the current replace source which can be modified - * @param {DependencyTemplateContext} templateContext the context object - * @returns {void} + * @param {ModuleGraph} moduleGraph the module graph + * @param {RuntimeSpec} runtime the runtime + * @returns {ExportMode} the export mode */ - apply( - dependency, - source, - { runtimeTemplate, moduleGraph, chunkGraph, runtimeRequirements } - ) { - const dep = /** @type {ModuleDependency} */ (dependency); - if (!dep.range) return; - const content = runtimeTemplate.moduleExports({ - module: moduleGraph.getModule(dep), - chunkGraph, - request: dep.request, - weak: dep.weak, - runtimeRequirements - }); - source.replace(dep.range[0], dep.range[1] - 1, content); + getMode(moduleGraph, runtime) { + return moduleGraph.dependencyCacheProvide( + this, + getRuntimeKey(runtime), + getMode + ); } -} -module.exports = ModuleDependencyTemplateAsRequireId; + /** + * @param {ModuleGraph} moduleGraph the module graph + * @param {RuntimeSpec} runtime the runtime + * @param {ExportsInfo} exportsInfo exports info about the current module (optional) + * @param {Module} importedModule the imported module (optional) + * @returns {{exports?: Set, checked?: Set, ignoredExports: Set, hidden?: Set}} information + */ + getStarReexports( + moduleGraph, + runtime, + exportsInfo = moduleGraph.getExportsInfo(moduleGraph.getParentModule(this)), + importedModule = moduleGraph.getModule(this) + ) { + const importedExportsInfo = moduleGraph.getExportsInfo(importedModule); -/***/ }), + const noExtraExports = + importedExportsInfo.otherExportsInfo.provided === false; + const noExtraImports = + exportsInfo.otherExportsInfo.getUsed(runtime) === UsageState.Unused; -/***/ 90200: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + const ignoredExports = new Set(["default", ...this.activeExports]); -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ + let hiddenExports = undefined; + const otherStarExports = + this._discoverActiveExportsFromOtherStarExports(moduleGraph); + if (otherStarExports !== undefined) { + hiddenExports = new Set(); + for (let i = 0; i < otherStarExports.namesSlice; i++) { + hiddenExports.add(otherStarExports.names[i]); + } + for (const e of ignoredExports) hiddenExports.delete(e); + } + if (!noExtraExports && !noExtraImports) { + return { + ignoredExports, + hidden: hiddenExports + }; + } + /** @type {Set} */ + const exports = new Set(); + /** @type {Set} */ + const checked = new Set(); + /** @type {Set} */ + const hidden = hiddenExports !== undefined ? new Set() : undefined; -const makeSerializable = __webpack_require__(26522); -const ModuleDependency = __webpack_require__(80944); -const ModuleDependencyTemplateAsId = __webpack_require__(35795); + if (noExtraImports) { + for (const exportInfo of exportsInfo.orderedExports) { + const name = exportInfo.name; + if (ignoredExports.has(name)) continue; + if (exportInfo.getUsed(runtime) === UsageState.Unused) continue; + const importedExportInfo = + importedExportsInfo.getReadOnlyExportInfo(name); + if (importedExportInfo.provided === false) continue; + if (hiddenExports !== undefined && hiddenExports.has(name)) { + hidden.add(name); + continue; + } + exports.add(name); + if (importedExportInfo.provided === true) continue; + checked.add(name); + } + } else if (noExtraExports) { + for (const importedExportInfo of importedExportsInfo.orderedExports) { + const name = importedExportInfo.name; + if (ignoredExports.has(name)) continue; + if (importedExportInfo.provided === false) continue; + const exportInfo = exportsInfo.getReadOnlyExportInfo(name); + if (exportInfo.getUsed(runtime) === UsageState.Unused) continue; + if (hiddenExports !== undefined && hiddenExports.has(name)) { + hidden.add(name); + continue; + } + exports.add(name); + if (importedExportInfo.provided === true) continue; + checked.add(name); + } + } -class ModuleHotAcceptDependency extends ModuleDependency { - constructor(request, range) { - super(request); - this.range = range; - this.weak = true; + return { ignoredExports, exports, checked, hidden }; } - get type() { - return "module.hot.accept"; + /** + * @param {ModuleGraph} moduleGraph module graph + * @returns {null | false | function(ModuleGraphConnection, RuntimeSpec): ConnectionState} function to determine if the connection is active + */ + getCondition(moduleGraph) { + return (connection, runtime) => { + const mode = this.getMode(moduleGraph, runtime); + return mode.type !== "unused" && mode.type !== "empty-star"; + }; } - get category() { - return "commonjs"; + /** + * @param {ModuleGraph} moduleGraph the module graph + * @returns {ConnectionState} how this dependency connects the module to referencing modules + */ + getModuleEvaluationSideEffectsState(moduleGraph) { + return false; } -} - -makeSerializable( - ModuleHotAcceptDependency, - "webpack/lib/dependencies/ModuleHotAcceptDependency" -); - -ModuleHotAcceptDependency.Template = ModuleDependencyTemplateAsId; -module.exports = ModuleHotAcceptDependency; - - -/***/ }), - -/***/ 72986: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ + /** + * Returns list of exports referenced by this dependency + * @param {ModuleGraph} moduleGraph module graph + * @param {RuntimeSpec} runtime the runtime for which the module is analysed + * @returns {(string[] | ReferencedExport)[]} referenced exports + */ + getReferencedExports(moduleGraph, runtime) { + const mode = this.getMode(moduleGraph, runtime); + switch (mode.type) { + case "missing": + case "unused": + case "empty-star": + case "reexport-undefined": + return Dependency.NO_EXPORTS_REFERENCED; + case "reexport-dynamic-default": + return Dependency.EXPORTS_OBJECT_REFERENCED; -const makeSerializable = __webpack_require__(26522); -const ModuleDependency = __webpack_require__(80944); -const ModuleDependencyTemplateAsId = __webpack_require__(35795); + case "reexport-named-default": { + if (!mode.partialNamespaceExportInfo) + return Dependency.EXPORTS_OBJECT_REFERENCED; + /** @type {string[][]} */ + const referencedExports = []; + processExportInfo( + runtime, + referencedExports, + [], + /** @type {ExportInfo} */ (mode.partialNamespaceExportInfo) + ); + return referencedExports; + } -class ModuleHotDeclineDependency extends ModuleDependency { - constructor(request, range) { - super(request); + case "reexport-namespace-object": + case "reexport-fake-namespace-object": { + if (!mode.partialNamespaceExportInfo) + return Dependency.EXPORTS_OBJECT_REFERENCED; + /** @type {string[][]} */ + const referencedExports = []; + processExportInfo( + runtime, + referencedExports, + [], + /** @type {ExportInfo} */ (mode.partialNamespaceExportInfo), + mode.type === "reexport-fake-namespace-object" + ); + return referencedExports; + } - this.range = range; - this.weak = true; - } + case "dynamic-reexport": + return Dependency.EXPORTS_OBJECT_REFERENCED; - get type() { - return "module.hot.decline"; - } + case "normal-reexport": { + const referencedExports = []; + for (const { ids, exportInfo, hidden } of mode.items) { + if (hidden) continue; + processExportInfo(runtime, referencedExports, ids, exportInfo, false); + } + return referencedExports; + } - get category() { - return "commonjs"; + default: + throw new Error(`Unknown mode ${mode.type}`); + } } -} - -makeSerializable( - ModuleHotDeclineDependency, - "webpack/lib/dependencies/ModuleHotDeclineDependency" -); - -ModuleHotDeclineDependency.Template = ModuleDependencyTemplateAsId; -module.exports = ModuleHotDeclineDependency; - - -/***/ }), + /** + * @param {ModuleGraph} moduleGraph the module graph + * @returns {{ names: string[], namesSlice: number, dependencyIndices: number[], dependencyIndex: number } | undefined} exported names and their origin dependency + */ + _discoverActiveExportsFromOtherStarExports(moduleGraph) { + if (!this.otherStarExports) return undefined; -/***/ 65845: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + const i = + "length" in this.otherStarExports + ? this.otherStarExports.length + : countIterable(this.otherStarExports); + if (i === 0) return undefined; -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ + if (this.allStarExports) { + const { names, dependencyIndices } = moduleGraph.cached( + determineExportAssignments, + this.allStarExports.dependencies + ); + return { + names, + namesSlice: dependencyIndices[i - 1], + dependencyIndices, + dependencyIndex: i + }; + } + const { names, dependencyIndices } = moduleGraph.cached( + determineExportAssignments, + this.otherStarExports, + this + ); -const Dependency = __webpack_require__(50384); -const DependencyTemplate = __webpack_require__(17600); + return { + names, + namesSlice: dependencyIndices[i - 1], + dependencyIndices, + dependencyIndex: i + }; + } -/** @typedef {import("webpack-sources").ReplaceSource} ReplaceSource */ -/** @typedef {import("../Dependency").TRANSITIVE} TRANSITIVE */ -/** @typedef {import("../DependencyTemplate").DependencyTemplateContext} DependencyTemplateContext */ + /** + * Returns the exported names + * @param {ModuleGraph} moduleGraph module graph + * @returns {ExportsSpec | undefined} export names + */ + getExports(moduleGraph) { + const mode = this.getMode(moduleGraph, undefined); -class NullDependency extends Dependency { - get type() { - return "null"; + switch (mode.type) { + case "missing": + return undefined; + case "dynamic-reexport": { + const from = moduleGraph.getConnection(this); + return { + exports: true, + from, + canMangle: false, + excludeExports: mode.hidden + ? combine(mode.ignored, mode.hidden) + : mode.ignored, + hideExports: mode.hidden, + dependencies: [from.module] + }; + } + case "empty-star": + return { + exports: [], + hideExports: mode.hidden, + dependencies: [moduleGraph.getModule(this)] + }; + // falls through + case "normal-reexport": { + const from = moduleGraph.getConnection(this); + return { + exports: Array.from(mode.items, item => ({ + name: item.name, + from, + export: item.ids, + hidden: item.hidden + })), + priority: 1, + dependencies: [from.module] + }; + } + case "reexport-dynamic-default": { + { + const from = moduleGraph.getConnection(this); + return { + exports: [ + { + name: mode.name, + from, + export: ["default"] + } + ], + priority: 1, + dependencies: [from.module] + }; + } + } + case "reexport-undefined": + return { + exports: [mode.name], + dependencies: [moduleGraph.getModule(this)] + }; + case "reexport-fake-namespace-object": { + const from = moduleGraph.getConnection(this); + return { + exports: [ + { + name: mode.name, + from, + export: null, + exports: [ + { + name: "default", + canMangle: false, + from, + export: null + } + ] + } + ], + priority: 1, + dependencies: [from.module] + }; + } + case "reexport-namespace-object": { + const from = moduleGraph.getConnection(this); + return { + exports: [ + { + name: mode.name, + from, + export: null + } + ], + priority: 1, + dependencies: [from.module] + }; + } + case "reexport-named-default": { + const from = moduleGraph.getConnection(this); + return { + exports: [ + { + name: mode.name, + from, + export: ["default"] + } + ], + priority: 1, + dependencies: [from.module] + }; + } + default: + throw new Error(`Unknown mode ${mode.type}`); + } } /** - * @returns {boolean | TRANSITIVE} true, when changes to the referenced module could affect the referencing module; TRANSITIVE, when changes to the referenced module could affect referencing modules of the referencing module + * @param {ModuleGraph} moduleGraph module graph + * @returns {number} effective mode */ - couldAffectReferencingModule() { - return false; + _getEffectiveExportPresenceLevel(moduleGraph) { + if (this.exportPresenceMode !== ExportPresenceModes.AUTO) + return this.exportPresenceMode; + return moduleGraph.getParentModule(this).buildMeta.strictHarmonyModule + ? ExportPresenceModes.ERROR + : ExportPresenceModes.WARN; } -} -NullDependency.Template = class NullDependencyTemplate extends ( - DependencyTemplate -) { /** - * @param {Dependency} dependency the dependency for which the template should be applied - * @param {ReplaceSource} source the current replace source which can be modified - * @param {DependencyTemplateContext} templateContext the context object - * @returns {void} + * Returns warnings + * @param {ModuleGraph} moduleGraph module graph + * @returns {WebpackError[]} warnings */ - apply(dependency, source, templateContext) {} -}; - -module.exports = NullDependency; - - -/***/ }), - -/***/ 39986: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ - - - -const ModuleDependency = __webpack_require__(80944); - -class PrefetchDependency extends ModuleDependency { - constructor(request) { - super(request); - } - - get type() { - return "prefetch"; - } - - get category() { - return "esm"; - } -} - -module.exports = PrefetchDependency; - - -/***/ }), - -/***/ 88915: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Florent Cailhol @ooflorent -*/ - - - -const InitFragment = __webpack_require__(51739); -const makeSerializable = __webpack_require__(26522); -const ModuleDependency = __webpack_require__(80944); - -/** @typedef {import("webpack-sources").ReplaceSource} ReplaceSource */ -/** @typedef {import("../ChunkGraph")} ChunkGraph */ -/** @typedef {import("../Dependency")} Dependency */ -/** @typedef {import("../Dependency").UpdateHashContext} UpdateHashContext */ -/** @typedef {import("../DependencyTemplate").DependencyTemplateContext} DependencyTemplateContext */ -/** @typedef {import("../DependencyTemplates")} DependencyTemplates */ -/** @typedef {import("../ModuleGraph")} ModuleGraph */ -/** @typedef {import("../RuntimeTemplate")} RuntimeTemplate */ -/** @typedef {import("../util/Hash")} Hash */ - -/** - * @param {string[]|null} path the property path array - * @returns {string} the converted path - */ -const pathToString = path => - path !== null && path.length > 0 - ? path.map(part => `[${JSON.stringify(part)}]`).join("") - : ""; - -class ProvidedDependency extends ModuleDependency { - constructor(request, identifier, path, range) { - super(request); - this.identifier = identifier; - this.path = path; - this.range = range; - this._hashUpdate = undefined; - } - - get type() { - return "provided"; + getWarnings(moduleGraph) { + const exportsPresence = this._getEffectiveExportPresenceLevel(moduleGraph); + if (exportsPresence === ExportPresenceModes.WARN) { + return this._getErrors(moduleGraph); + } + return null; } - get category() { - return "esm"; + /** + * Returns errors + * @param {ModuleGraph} moduleGraph module graph + * @returns {WebpackError[]} errors + */ + getErrors(moduleGraph) { + const exportsPresence = this._getEffectiveExportPresenceLevel(moduleGraph); + if (exportsPresence === ExportPresenceModes.ERROR) { + return this._getErrors(moduleGraph); + } + return null; } /** - * Update the hash - * @param {Hash} hash hash to be updated - * @param {UpdateHashContext} context context - * @returns {void} + * @param {ModuleGraph} moduleGraph module graph + * @returns {WebpackError[] | undefined} errors */ - updateHash(hash, context) { - if (this._hashUpdate === undefined) { - this._hashUpdate = - this.identifier + (this.path ? this.path.join(",") : "null"); + _getErrors(moduleGraph) { + const ids = this.getIds(moduleGraph); + let errors = this.getLinkingErrors( + moduleGraph, + ids, + `(reexported as '${this.name}')` + ); + if (ids.length === 0 && this.name === null) { + const potentialConflicts = + this._discoverActiveExportsFromOtherStarExports(moduleGraph); + if (potentialConflicts && potentialConflicts.namesSlice > 0) { + const ownNames = new Set( + potentialConflicts.names.slice( + potentialConflicts.namesSlice, + potentialConflicts.dependencyIndices[ + potentialConflicts.dependencyIndex + ] + ) + ); + const importedModule = moduleGraph.getModule(this); + if (importedModule) { + const exportsInfo = moduleGraph.getExportsInfo(importedModule); + const conflicts = new Map(); + for (const exportInfo of exportsInfo.orderedExports) { + if (exportInfo.provided !== true) continue; + if (exportInfo.name === "default") continue; + if (this.activeExports.has(exportInfo.name)) continue; + if (ownNames.has(exportInfo.name)) continue; + const conflictingDependency = findDependencyForName( + potentialConflicts, + exportInfo.name, + this.allStarExports + ? this.allStarExports.dependencies + : [...this.otherStarExports, this] + ); + if (!conflictingDependency) continue; + const target = exportInfo.getTerminalBinding(moduleGraph); + if (!target) continue; + const conflictingModule = moduleGraph.getModule( + conflictingDependency + ); + if (conflictingModule === importedModule) continue; + const conflictingExportInfo = moduleGraph.getExportInfo( + conflictingModule, + exportInfo.name + ); + const conflictingTarget = + conflictingExportInfo.getTerminalBinding(moduleGraph); + if (!conflictingTarget) continue; + if (target === conflictingTarget) continue; + const list = conflicts.get(conflictingDependency.request); + if (list === undefined) { + conflicts.set(conflictingDependency.request, [exportInfo.name]); + } else { + list.push(exportInfo.name); + } + } + for (const [request, exports] of conflicts) { + if (!errors) errors = []; + errors.push( + new HarmonyLinkingError( + `The requested module '${ + this.request + }' contains conflicting star exports for the ${ + exports.length > 1 ? "names" : "name" + } ${exports + .map(e => `'${e}'`) + .join(", ")} with the previous requested module '${request}'` + ) + ); + } + } + } } - hash.update(this._hashUpdate); + return errors; } serialize(context) { - const { write } = context; - write(this.identifier); - write(this.path); + const { write, setCircularReference } = context; + + setCircularReference(this); + write(this.ids); + write(this.name); + write(this.activeExports); + write(this.otherStarExports); + write(this.exportPresenceMode); + write(this.allStarExports); + super.serialize(context); } deserialize(context) { - const { read } = context; - this.identifier = read(); - this.path = read(); + const { read, setCircularReference } = context; + + setCircularReference(this); + this.ids = read(); + this.name = read(); + this.activeExports = read(); + this.otherStarExports = read(); + this.exportPresenceMode = read(); + this.allStarExports = read(); + super.deserialize(context); } } makeSerializable( - ProvidedDependency, - "webpack/lib/dependencies/ProvidedDependency" + HarmonyExportImportedSpecifierDependency, + "webpack/lib/dependencies/HarmonyExportImportedSpecifierDependency" ); -class ProvidedDependencyTemplate extends ModuleDependency.Template { +module.exports = HarmonyExportImportedSpecifierDependency; + +HarmonyExportImportedSpecifierDependency.Template = class HarmonyExportImportedSpecifierDependencyTemplate extends ( + HarmonyImportDependency.Template +) { /** * @param {Dependency} dependency the dependency for which the template should be applied * @param {ReplaceSource} source the current replace source which can be modified * @param {DependencyTemplateContext} templateContext the context object * @returns {void} */ - apply( - dependency, - source, - { - runtimeTemplate, - moduleGraph, - chunkGraph, - initFragments, - runtimeRequirements - } - ) { - const dep = /** @type {ProvidedDependency} */ (dependency); - initFragments.push( - new InitFragment( - `/* provided dependency */ var ${ - dep.identifier - } = ${runtimeTemplate.moduleExports({ - module: moduleGraph.getModule(dep), - chunkGraph, - request: dep.request, - runtimeRequirements - })}${pathToString(dep.path)};\n`, - InitFragment.STAGE_PROVIDES, - 1, - `provided ${dep.identifier}` - ) + apply(dependency, source, templateContext) { + const { moduleGraph, runtime, concatenationScope } = templateContext; + + const dep = /** @type {HarmonyExportImportedSpecifierDependency} */ ( + dependency ); - source.replace(dep.range[0], dep.range[1] - 1, dep.identifier); + + const mode = dep.getMode(moduleGraph, runtime); + + if (concatenationScope) { + switch (mode.type) { + case "reexport-undefined": + concatenationScope.registerRawExport( + mode.name, + "/* reexport non-default export from non-harmony */ undefined" + ); + } + return; + } + + if (mode.type !== "unused" && mode.type !== "empty-star") { + super.apply(dependency, source, templateContext); + + this._addExportFragments( + templateContext.initFragments, + dep, + mode, + templateContext.module, + moduleGraph, + runtime, + templateContext.runtimeTemplate, + templateContext.runtimeRequirements + ); + } } -} -ProvidedDependency.Template = ProvidedDependencyTemplate; + /** + * @param {InitFragment[]} initFragments target array for init fragments + * @param {HarmonyExportImportedSpecifierDependency} dep dependency + * @param {ExportMode} mode the export mode + * @param {Module} module the current module + * @param {ModuleGraph} moduleGraph the module graph + * @param {RuntimeSpec} runtime the runtime + * @param {RuntimeTemplate} runtimeTemplate the runtime template + * @param {Set} runtimeRequirements runtime requirements + * @returns {void} + */ + _addExportFragments( + initFragments, + dep, + mode, + module, + moduleGraph, + runtime, + runtimeTemplate, + runtimeRequirements + ) { + const importedModule = moduleGraph.getModule(dep); + const importVar = dep.getImportVar(moduleGraph); -module.exports = ProvidedDependency; + switch (mode.type) { + case "missing": + case "empty-star": + initFragments.push( + new InitFragment( + "/* empty/unused harmony star reexport */\n", + InitFragment.STAGE_HARMONY_EXPORTS, + 1 + ) + ); + break; + case "unused": + initFragments.push( + new InitFragment( + `${Template.toNormalComment( + `unused harmony reexport ${mode.name}` + )}\n`, + InitFragment.STAGE_HARMONY_EXPORTS, + 1 + ) + ); + break; -/***/ }), + case "reexport-dynamic-default": + initFragments.push( + this.getReexportFragment( + module, + "reexport default from dynamic", + moduleGraph.getExportsInfo(module).getUsedName(mode.name, runtime), + importVar, + null, + runtimeRequirements + ) + ); + break; -/***/ 24746: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + case "reexport-fake-namespace-object": + initFragments.push( + ...this.getReexportFakeNamespaceObjectFragments( + module, + moduleGraph.getExportsInfo(module).getUsedName(mode.name, runtime), + importVar, + mode.fakeType, + runtimeRequirements + ) + ); + break; -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ + case "reexport-undefined": + initFragments.push( + this.getReexportFragment( + module, + "reexport non-default export from non-harmony", + moduleGraph.getExportsInfo(module).getUsedName(mode.name, runtime), + "undefined", + "", + runtimeRequirements + ) + ); + break; + + case "reexport-named-default": + initFragments.push( + this.getReexportFragment( + module, + "reexport default export from named module", + moduleGraph.getExportsInfo(module).getUsedName(mode.name, runtime), + importVar, + "", + runtimeRequirements + ) + ); + break; + + case "reexport-namespace-object": + initFragments.push( + this.getReexportFragment( + module, + "reexport module object", + moduleGraph.getExportsInfo(module).getUsedName(mode.name, runtime), + importVar, + "", + runtimeRequirements + ) + ); + break; + + case "normal-reexport": + for (const { name, ids, checked, hidden } of mode.items) { + if (hidden) continue; + if (checked) { + initFragments.push( + new InitFragment( + "/* harmony reexport (checked) */ " + + this.getConditionalReexportStatement( + module, + name, + importVar, + ids, + runtimeRequirements + ), + moduleGraph.isAsync(importedModule) + ? InitFragment.STAGE_ASYNC_HARMONY_IMPORTS + : InitFragment.STAGE_HARMONY_IMPORTS, + dep.sourceOrder + ) + ); + } else { + initFragments.push( + this.getReexportFragment( + module, + "reexport safe", + moduleGraph.getExportsInfo(module).getUsedName(name, runtime), + importVar, + moduleGraph + .getExportsInfo(importedModule) + .getUsedName(ids, runtime), + runtimeRequirements + ) + ); + } + } + break; + case "dynamic-reexport": { + const ignored = mode.hidden + ? combine(mode.ignored, mode.hidden) + : mode.ignored; + const modern = + runtimeTemplate.supportsConst() && + runtimeTemplate.supportsArrowFunction(); + let content = + "/* harmony reexport (unknown) */ var __WEBPACK_REEXPORT_OBJECT__ = {};\n" + + `/* harmony reexport (unknown) */ for(${ + modern ? "const" : "var" + } __WEBPACK_IMPORT_KEY__ in ${importVar}) `; + // Filter out exports which are defined by other exports + // and filter out default export because it cannot be reexported with * + if (ignored.size > 1) { + content += + "if(" + + JSON.stringify(Array.from(ignored)) + + ".indexOf(__WEBPACK_IMPORT_KEY__) < 0) "; + } else if (ignored.size === 1) { + content += `if(__WEBPACK_IMPORT_KEY__ !== ${JSON.stringify( + first(ignored) + )}) `; + } -const { UsageState } = __webpack_require__(4295); -const makeSerializable = __webpack_require__(26522); -const { filterRuntime } = __webpack_require__(19655); -const NullDependency = __webpack_require__(65845); + content += `__WEBPACK_REEXPORT_OBJECT__[__WEBPACK_IMPORT_KEY__] = `; + if (modern) { + content += `() => ${importVar}[__WEBPACK_IMPORT_KEY__]`; + } else { + content += `function(key) { return ${importVar}[key]; }.bind(0, __WEBPACK_IMPORT_KEY__)`; + } -/** @typedef {import("webpack-sources").ReplaceSource} ReplaceSource */ -/** @typedef {import("../ChunkGraph")} ChunkGraph */ -/** @typedef {import("../Dependency")} Dependency */ -/** @typedef {import("../Dependency").UpdateHashContext} UpdateHashContext */ -/** @typedef {import("../DependencyTemplate").DependencyTemplateContext} DependencyTemplateContext */ -/** @typedef {import("../ModuleGraph")} ModuleGraph */ -/** @typedef {import("../ModuleGraphConnection").ConnectionState} ConnectionState */ -/** @typedef {import("../util/Hash")} Hash */ + runtimeRequirements.add(RuntimeGlobals.exports); + runtimeRequirements.add(RuntimeGlobals.definePropertyGetters); -class PureExpressionDependency extends NullDependency { - /** - * @param {[number, number]} range the source range - */ - constructor(range) { - super(); - this.range = range; - /** @type {Set | false} */ - this.usedByExports = false; - this._hashUpdate = undefined; - } + const exportsName = module.exportsArgument; + initFragments.push( + new InitFragment( + `${content}\n/* harmony reexport (unknown) */ ${RuntimeGlobals.definePropertyGetters}(${exportsName}, __WEBPACK_REEXPORT_OBJECT__);\n`, + moduleGraph.isAsync(importedModule) + ? InitFragment.STAGE_ASYNC_HARMONY_IMPORTS + : InitFragment.STAGE_HARMONY_IMPORTS, + dep.sourceOrder + ) + ); + break; + } - /** - * Update the hash - * @param {Hash} hash hash to be updated - * @param {UpdateHashContext} context context - * @returns {void} - */ - updateHash(hash, context) { - if (this._hashUpdate === undefined) { - this._hashUpdate = this.range + ""; + default: + throw new Error(`Unknown mode ${mode.type}`); } - hash.update(this._hashUpdate); } - /** - * @param {ModuleGraph} moduleGraph the module graph - * @returns {ConnectionState} how this dependency connects the module to referencing modules - */ - getModuleEvaluationSideEffectsState(moduleGraph) { - return false; - } + getReexportFragment( + module, + comment, + key, + name, + valueKey, + runtimeRequirements + ) { + const returnValue = this.getReturnValue(name, valueKey); - serialize(context) { - const { write } = context; - write(this.range); - write(this.usedByExports); - super.serialize(context); - } + runtimeRequirements.add(RuntimeGlobals.exports); + runtimeRequirements.add(RuntimeGlobals.definePropertyGetters); - deserialize(context) { - const { read } = context; - this.range = read(); - this.usedByExports = read(); - super.deserialize(context); - } -} + const map = new Map(); + map.set(key, `/* ${comment} */ ${returnValue}`); -makeSerializable( - PureExpressionDependency, - "webpack/lib/dependencies/PureExpressionDependency" -); + return new HarmonyExportInitFragment(module.exportsArgument, map); + } -PureExpressionDependency.Template = class PureExpressionDependencyTemplate extends ( - NullDependency.Template -) { - /** - * @param {Dependency} dependency the dependency for which the template should be applied - * @param {ReplaceSource} source the current replace source which can be modified - * @param {DependencyTemplateContext} templateContext the context object - * @returns {void} - */ - apply( - dependency, - source, - { chunkGraph, moduleGraph, runtime, runtimeTemplate, runtimeRequirements } + getReexportFakeNamespaceObjectFragments( + module, + key, + name, + fakeType, + runtimeRequirements ) { - const dep = /** @type {PureExpressionDependency} */ (dependency); - - const usedByExports = dep.usedByExports; - if (usedByExports !== false) { - const selfModule = moduleGraph.getParentModule(dep); - const exportsInfo = moduleGraph.getExportsInfo(selfModule); - const runtimeCondition = filterRuntime(runtime, runtime => { - for (const exportName of usedByExports) { - if (exportsInfo.getUsed(exportName, runtime) !== UsageState.Unused) { - return true; - } - } - return false; - }); - if (runtimeCondition === true) return; - if (runtimeCondition !== false) { - const condition = runtimeTemplate.runtimeConditionExpression({ - chunkGraph, - runtime, - runtimeCondition, - runtimeRequirements - }); - source.insert( - dep.range[0], - `(/* runtime-dependent pure expression or super */ ${condition} ? (` - ); - source.insert(dep.range[1], ") : null)"); - return; - } - } + runtimeRequirements.add(RuntimeGlobals.exports); + runtimeRequirements.add(RuntimeGlobals.definePropertyGetters); + runtimeRequirements.add(RuntimeGlobals.createFakeNamespaceObject); - source.insert( - dep.range[0], - `(/* unused pure expression or super */ null && (` + const map = new Map(); + map.set( + key, + `/* reexport fake namespace object from non-harmony */ ${name}_namespace_cache || (${name}_namespace_cache = ${ + RuntimeGlobals.createFakeNamespaceObject + }(${name}${fakeType ? `, ${fakeType}` : ""}))` ); - source.insert(dep.range[1], "))"); - } -}; - -module.exports = PureExpressionDependency; + return [ + new InitFragment( + `var ${name}_namespace_cache;\n`, + InitFragment.STAGE_CONSTANTS, + -1, + `${name}_namespace_cache` + ), + new HarmonyExportInitFragment(module.exportsArgument, map) + ]; + } -/***/ }), + getConditionalReexportStatement( + module, + key, + name, + valueKey, + runtimeRequirements + ) { + if (valueKey === false) { + return "/* unused export */\n"; + } -/***/ 98854: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + const exportsName = module.exportsArgument; + const returnValue = this.getReturnValue(name, valueKey); -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ + runtimeRequirements.add(RuntimeGlobals.exports); + runtimeRequirements.add(RuntimeGlobals.definePropertyGetters); + runtimeRequirements.add(RuntimeGlobals.hasOwnProperty); + return `if(${RuntimeGlobals.hasOwnProperty}(${name}, ${JSON.stringify( + valueKey[0] + )})) ${ + RuntimeGlobals.definePropertyGetters + }(${exportsName}, { ${JSON.stringify( + key + )}: function() { return ${returnValue}; } });\n`; + } + getReturnValue(name, valueKey) { + if (valueKey === null) { + return `${name}_default.a`; + } -const makeSerializable = __webpack_require__(26522); -const ContextDependency = __webpack_require__(67840); -const ModuleDependencyTemplateAsRequireId = __webpack_require__(77802); + if (valueKey === "") { + return name; + } -class RequireContextDependency extends ContextDependency { - constructor(options, range) { - super(options); + if (valueKey === false) { + return "/* unused export */ undefined"; + } - this.range = range; + return `${name}${propertyAccess(valueKey)}`; } +}; - get type() { - return "require.context"; +class HarmonyStarExportsList { + constructor() { + /** @type {HarmonyExportImportedSpecifierDependency[]} */ + this.dependencies = []; } - serialize(context) { - const { write } = context; - - write(this.range); - - super.serialize(context); + /** + * @param {HarmonyExportImportedSpecifierDependency} dep dependency + * @returns {void} + */ + push(dep) { + this.dependencies.push(dep); } - deserialize(context) { - const { read } = context; + slice() { + return this.dependencies.slice(); + } - this.range = read(); + serialize({ write, setCircularReference }) { + setCircularReference(this); + write(this.dependencies); + } - super.deserialize(context); + deserialize({ read, setCircularReference }) { + setCircularReference(this); + this.dependencies = read(); } } makeSerializable( - RequireContextDependency, - "webpack/lib/dependencies/RequireContextDependency" + HarmonyStarExportsList, + "webpack/lib/dependencies/HarmonyExportImportedSpecifierDependency", + "HarmonyStarExportsList" ); -RequireContextDependency.Template = ModuleDependencyTemplateAsRequireId; - -module.exports = RequireContextDependency; +module.exports.HarmonyStarExportsList = HarmonyStarExportsList; /***/ }), -/***/ 18885: +/***/ 68664: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; @@ -84125,220 +82006,169 @@ module.exports = RequireContextDependency; -const RequireContextDependency = __webpack_require__(98854); +const InitFragment = __webpack_require__(51739); +const RuntimeGlobals = __webpack_require__(49404); +const { first } = __webpack_require__(34715); -module.exports = class RequireContextDependencyParserPlugin { - apply(parser) { - parser.hooks.call - .for("require.context") - .tap("RequireContextDependencyParserPlugin", expr => { - let regExp = /^\.\/.*$/; - let recursive = true; - let mode = "sync"; - switch (expr.arguments.length) { - case 4: { - const modeExpr = parser.evaluateExpression(expr.arguments[3]); - if (!modeExpr.isString()) return; - mode = modeExpr.string; - } - // falls through - case 3: { - const regExpExpr = parser.evaluateExpression(expr.arguments[2]); - if (!regExpExpr.isRegExp()) return; - regExp = regExpExpr.regExp; - } - // falls through - case 2: { - const recursiveExpr = parser.evaluateExpression(expr.arguments[1]); - if (!recursiveExpr.isBoolean()) return; - recursive = recursiveExpr.bool; - } - // falls through - case 1: { - const requestExpr = parser.evaluateExpression(expr.arguments[0]); - if (!requestExpr.isString()) return; - const dep = new RequireContextDependency( - { - request: requestExpr.string, - recursive, - regExp, - mode, - category: "commonjs" - }, - expr.range - ); - dep.loc = expr.loc; - dep.optional = !!parser.scope.inTry; - parser.state.current.addDependency(dep); - return true; - } - } - }); +/** @typedef {import("webpack-sources").Source} Source */ +/** @typedef {import("../Generator").GenerateContext} GenerateContext */ + +const joinIterableWithComma = iterable => { + // This is more performant than Array.from().join(", ") + // as it doesn't create an array + let str = ""; + let first = true; + for (const item of iterable) { + if (first) { + first = false; + } else { + str += ", "; + } + str += item; } + return str; }; +const EMPTY_MAP = new Map(); +const EMPTY_SET = new Set(); -/***/ }), - -/***/ 30738: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ - - - -const { cachedSetProperty } = __webpack_require__(11217); -const ContextElementDependency = __webpack_require__(83853); -const RequireContextDependency = __webpack_require__(98854); -const RequireContextDependencyParserPlugin = __webpack_require__(18885); - -/** @typedef {import("../../declarations/WebpackOptions").ResolveOptions} ResolveOptions */ -/** @typedef {import("../Compiler")} Compiler */ - -/** @type {ResolveOptions} */ -const EMPTY_RESOLVE_OPTIONS = {}; - -class RequireContextPlugin { +/** + * @typedef {GenerateContext} Context + */ +class HarmonyExportInitFragment extends InitFragment { /** - * Apply the plugin - * @param {Compiler} compiler the compiler instance - * @returns {void} - */ - apply(compiler) { - compiler.hooks.compilation.tap( - "RequireContextPlugin", - (compilation, { contextModuleFactory, normalModuleFactory }) => { - compilation.dependencyFactories.set( - RequireContextDependency, - contextModuleFactory - ); - compilation.dependencyTemplates.set( - RequireContextDependency, - new RequireContextDependency.Template() - ); - - compilation.dependencyFactories.set( - ContextElementDependency, - normalModuleFactory - ); - - const handler = (parser, parserOptions) => { - if ( - parserOptions.requireContext !== undefined && - !parserOptions.requireContext - ) - return; - - new RequireContextDependencyParserPlugin().apply(parser); - }; - - normalModuleFactory.hooks.parser - .for("javascript/auto") - .tap("RequireContextPlugin", handler); - normalModuleFactory.hooks.parser - .for("javascript/dynamic") - .tap("RequireContextPlugin", handler); - - contextModuleFactory.hooks.alternativeRequests.tap( - "RequireContextPlugin", - (items, options) => { - if (items.length === 0) return items; - - const finalResolveOptions = compiler.resolverFactory.get( - "normal", - cachedSetProperty( - options.resolveOptions || EMPTY_RESOLVE_OPTIONS, - "dependencyType", - options.category - ) - ).options; - - let newItems; - if (!finalResolveOptions.fullySpecified) { - newItems = []; - for (const item of items) { - const { request, context } = item; - for (const ext of finalResolveOptions.extensions) { - if (request.endsWith(ext)) { - newItems.push({ - context, - request: request.slice(0, -ext.length) - }); - } - } - if (!finalResolveOptions.enforceExtension) { - newItems.push(item); - } - } - items = newItems; - - newItems = []; - for (const obj of items) { - const { request, context } = obj; - for (const mainFile of finalResolveOptions.mainFiles) { - if (request.endsWith(`/${mainFile}`)) { - newItems.push({ - context, - request: request.slice(0, -mainFile.length) - }); - newItems.push({ - context, - request: request.slice(0, -mainFile.length - 1) - }); - } - } - newItems.push(obj); - } - items = newItems; - } - - newItems = []; - for (const item of items) { - let hideOriginal = false; - for (const modulesItems of finalResolveOptions.modules) { - if (Array.isArray(modulesItems)) { - for (const dir of modulesItems) { - if (item.request.startsWith(`./${dir}/`)) { - newItems.push({ - context: item.context, - request: item.request.slice(dir.length + 3) - }); - hideOriginal = true; - } - } - } else { - const dir = modulesItems.replace(/\\/g, "/"); - const fullPath = - item.context.replace(/\\/g, "/") + item.request.slice(1); - if (fullPath.startsWith(dir)) { - newItems.push({ - context: item.context, - request: fullPath.slice(dir.length + 1) - }); - } - } - } - if (!hideOriginal) { - newItems.push(item); - } - } - return newItems; + * @param {string} exportsArgument the exports identifier + * @param {Map} exportMap mapping from used name to exposed variable name + * @param {Set} unusedExports list of unused export names + */ + constructor( + exportsArgument, + exportMap = EMPTY_MAP, + unusedExports = EMPTY_SET + ) { + super(undefined, InitFragment.STAGE_HARMONY_EXPORTS, 1, "harmony-exports"); + this.exportsArgument = exportsArgument; + this.exportMap = exportMap; + this.unusedExports = unusedExports; + } + + /** + * @param {HarmonyExportInitFragment[]} fragments all fragments to merge + * @returns {HarmonyExportInitFragment} merged fragment + */ + mergeAll(fragments) { + let exportMap; + let exportMapOwned = false; + let unusedExports; + let unusedExportsOwned = false; + + for (const fragment of fragments) { + if (fragment.exportMap.size !== 0) { + if (exportMap === undefined) { + exportMap = fragment.exportMap; + exportMapOwned = false; + } else { + if (!exportMapOwned) { + exportMap = new Map(exportMap); + exportMapOwned = true; } - ); + for (const [key, value] of fragment.exportMap) { + if (!exportMap.has(key)) exportMap.set(key, value); + } + } + } + if (fragment.unusedExports.size !== 0) { + if (unusedExports === undefined) { + unusedExports = fragment.unusedExports; + unusedExportsOwned = false; + } else { + if (!unusedExportsOwned) { + unusedExports = new Set(unusedExports); + unusedExportsOwned = true; + } + for (const value of fragment.unusedExports) { + unusedExports.add(value); + } + } + } + } + return new HarmonyExportInitFragment( + this.exportsArgument, + exportMap, + unusedExports + ); + } + + merge(other) { + let exportMap; + if (this.exportMap.size === 0) { + exportMap = other.exportMap; + } else if (other.exportMap.size === 0) { + exportMap = this.exportMap; + } else { + exportMap = new Map(other.exportMap); + for (const [key, value] of this.exportMap) { + if (!exportMap.has(key)) exportMap.set(key, value); + } + } + let unusedExports; + if (this.unusedExports.size === 0) { + unusedExports = other.unusedExports; + } else if (other.unusedExports.size === 0) { + unusedExports = this.unusedExports; + } else { + unusedExports = new Set(other.unusedExports); + for (const value of this.unusedExports) { + unusedExports.add(value); } + } + return new HarmonyExportInitFragment( + this.exportsArgument, + exportMap, + unusedExports ); } + + /** + * @param {Context} context context + * @returns {string|Source} the source code that will be included as initialization code + */ + getContent({ runtimeTemplate, runtimeRequirements }) { + runtimeRequirements.add(RuntimeGlobals.exports); + runtimeRequirements.add(RuntimeGlobals.definePropertyGetters); + + const unusedPart = + this.unusedExports.size > 1 + ? `/* unused harmony exports ${joinIterableWithComma( + this.unusedExports + )} */\n` + : this.unusedExports.size > 0 + ? `/* unused harmony export ${first(this.unusedExports)} */\n` + : ""; + const definitions = []; + for (const [key, value] of this.exportMap) { + definitions.push( + `\n/* harmony export */ ${JSON.stringify( + key + )}: ${runtimeTemplate.returningFunction(value)}` + ); + } + const definePart = + this.exportMap.size > 0 + ? `/* harmony export */ ${RuntimeGlobals.definePropertyGetters}(${ + this.exportsArgument + }, {${definitions.join(",")}\n/* harmony export */ });\n` + : ""; + return `${definePart}${unusedPart}`; + } } -module.exports = RequireContextPlugin; + +module.exports = HarmonyExportInitFragment; /***/ }), -/***/ 91421: +/***/ 59042: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; @@ -84349,27 +82179,116 @@ module.exports = RequireContextPlugin; -const AsyncDependenciesBlock = __webpack_require__(11315); const makeSerializable = __webpack_require__(26522); +const HarmonyExportInitFragment = __webpack_require__(68664); +const NullDependency = __webpack_require__(65845); -class RequireEnsureDependenciesBlock extends AsyncDependenciesBlock { - constructor(chunkName, loc) { - super(chunkName, loc, null); +/** @typedef {import("webpack-sources").ReplaceSource} ReplaceSource */ +/** @typedef {import("../Dependency")} Dependency */ +/** @typedef {import("../Dependency").ExportsSpec} ExportsSpec */ +/** @typedef {import("../DependencyTemplate").DependencyTemplateContext} DependencyTemplateContext */ +/** @typedef {import("../ModuleGraph")} ModuleGraph */ +/** @typedef {import("../ModuleGraphConnection").ConnectionState} ConnectionState */ + +class HarmonyExportSpecifierDependency extends NullDependency { + constructor(id, name) { + super(); + this.id = id; + this.name = name; + } + + get type() { + return "harmony export specifier"; + } + + /** + * Returns the exported names + * @param {ModuleGraph} moduleGraph module graph + * @returns {ExportsSpec | undefined} export names + */ + getExports(moduleGraph) { + return { + exports: [this.name], + priority: 1, + terminalBinding: true, + dependencies: undefined + }; + } + + /** + * @param {ModuleGraph} moduleGraph the module graph + * @returns {ConnectionState} how this dependency connects the module to referencing modules + */ + getModuleEvaluationSideEffectsState(moduleGraph) { + return false; + } + + serialize(context) { + const { write } = context; + write(this.id); + write(this.name); + super.serialize(context); + } + + deserialize(context) { + const { read } = context; + this.id = read(); + this.name = read(); + super.deserialize(context); } } makeSerializable( - RequireEnsureDependenciesBlock, - "webpack/lib/dependencies/RequireEnsureDependenciesBlock" + HarmonyExportSpecifierDependency, + "webpack/lib/dependencies/HarmonyExportSpecifierDependency" ); -module.exports = RequireEnsureDependenciesBlock; +HarmonyExportSpecifierDependency.Template = class HarmonyExportSpecifierDependencyTemplate extends ( + NullDependency.Template +) { + /** + * @param {Dependency} dependency the dependency for which the template should be applied + * @param {ReplaceSource} source the current replace source which can be modified + * @param {DependencyTemplateContext} templateContext the context object + * @returns {void} + */ + apply( + dependency, + source, + { module, moduleGraph, initFragments, runtime, concatenationScope } + ) { + const dep = /** @type {HarmonyExportSpecifierDependency} */ (dependency); + if (concatenationScope) { + concatenationScope.registerExport(dep.name, dep.id); + return; + } + const used = moduleGraph + .getExportsInfo(module) + .getUsedName(dep.name, runtime); + if (!used) { + const set = new Set(); + set.add(dep.name || "namespace"); + initFragments.push( + new HarmonyExportInitFragment(module.exportsArgument, undefined, set) + ); + return; + } + + const map = new Map(); + map.set(used, `/* binding */ ${dep.id}`); + initFragments.push( + new HarmonyExportInitFragment(module.exportsArgument, map, undefined) + ); + } +}; + +module.exports = HarmonyExportSpecifierDependency; /***/ }), -/***/ 95195: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { +/***/ 37637: +/***/ (function(__unused_webpack_module, exports) { "use strict"; /* @@ -84379,125 +82298,44 @@ module.exports = RequireEnsureDependenciesBlock; -const RequireEnsureDependenciesBlock = __webpack_require__(91421); -const RequireEnsureDependency = __webpack_require__(975); -const RequireEnsureItemDependency = __webpack_require__(56867); -const getFunctionExpression = __webpack_require__(70108); - -module.exports = class RequireEnsureDependenciesBlockParserPlugin { - apply(parser) { - parser.hooks.call - .for("require.ensure") - .tap("RequireEnsureDependenciesBlockParserPlugin", expr => { - let chunkName = null; - let errorExpressionArg = null; - let errorExpression = null; - switch (expr.arguments.length) { - case 4: { - const chunkNameExpr = parser.evaluateExpression(expr.arguments[3]); - if (!chunkNameExpr.isString()) return; - chunkName = chunkNameExpr.string; - } - // falls through - case 3: { - errorExpressionArg = expr.arguments[2]; - errorExpression = getFunctionExpression(errorExpressionArg); - - if (!errorExpression && !chunkName) { - const chunkNameExpr = parser.evaluateExpression( - expr.arguments[2] - ); - if (!chunkNameExpr.isString()) return; - chunkName = chunkNameExpr.string; - } - } - // falls through - case 2: { - const dependenciesExpr = parser.evaluateExpression( - expr.arguments[0] - ); - const dependenciesItems = dependenciesExpr.isArray() - ? dependenciesExpr.items - : [dependenciesExpr]; - const successExpressionArg = expr.arguments[1]; - const successExpression = - getFunctionExpression(successExpressionArg); +/** @typedef {import("../Parser").ParserState} ParserState */ - if (successExpression) { - parser.walkExpressions(successExpression.expressions); - } - if (errorExpression) { - parser.walkExpressions(errorExpression.expressions); - } +/** @type {WeakMap} */ +const parserStateExportsState = new WeakMap(); - const depBlock = new RequireEnsureDependenciesBlock( - chunkName, - expr.loc - ); - const errorCallbackExists = - expr.arguments.length === 4 || - (!chunkName && expr.arguments.length === 3); - const dep = new RequireEnsureDependency( - expr.range, - expr.arguments[1].range, - errorCallbackExists && expr.arguments[2].range - ); - dep.loc = expr.loc; - depBlock.addDependency(dep); - const old = parser.state.current; - parser.state.current = depBlock; - try { - let failed = false; - parser.inScope([], () => { - for (const ee of dependenciesItems) { - if (ee.isString()) { - const ensureDependency = new RequireEnsureItemDependency( - ee.string - ); - ensureDependency.loc = ee.loc || expr.loc; - depBlock.addDependency(ensureDependency); - } else { - failed = true; - } - } - }); - if (failed) { - return; - } - if (successExpression) { - if (successExpression.fn.body.type === "BlockStatement") { - parser.walkStatement(successExpression.fn.body); - } else { - parser.walkExpression(successExpression.fn.body); - } - } - old.addBlock(depBlock); - } finally { - parser.state.current = old; - } - if (!successExpression) { - parser.walkExpression(successExpressionArg); - } - if (errorExpression) { - if (errorExpression.fn.body.type === "BlockStatement") { - parser.walkStatement(errorExpression.fn.body); - } else { - parser.walkExpression(errorExpression.fn.body); - } - } else if (errorExpressionArg) { - parser.walkExpression(errorExpressionArg); - } - return true; - } - } - }); +/** + * @param {ParserState} parserState parser state + * @param {boolean} isStrictHarmony strict harmony mode should be enabled + * @returns {void} + */ +exports.enable = (parserState, isStrictHarmony) => { + const value = parserStateExportsState.get(parserState); + if (value === false) return; + parserStateExportsState.set(parserState, true); + if (value !== true) { + parserState.module.buildMeta.exportsType = "namespace"; + parserState.module.buildInfo.strict = true; + parserState.module.buildInfo.exportsArgument = "__webpack_exports__"; + if (isStrictHarmony) { + parserState.module.buildMeta.strictHarmonyModule = true; + parserState.module.buildInfo.moduleArgument = "__webpack_module__"; + } } }; +/** + * @param {ParserState} parserState parser state + * @returns {boolean} true, when enabled + */ +exports.isEnabled = parserState => { + const value = parserStateExportsState.get(parserState); + return value === true; +}; + /***/ }), -/***/ 975: +/***/ 19577: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; @@ -84508,56 +82346,244 @@ module.exports = class RequireEnsureDependenciesBlockParserPlugin { -const RuntimeGlobals = __webpack_require__(49404); -const makeSerializable = __webpack_require__(26522); -const NullDependency = __webpack_require__(65845); +const ConditionalInitFragment = __webpack_require__(90921); +const Dependency = __webpack_require__(50384); +const HarmonyLinkingError = __webpack_require__(42766); +const InitFragment = __webpack_require__(51739); +const Template = __webpack_require__(92066); +const AwaitDependenciesInitFragment = __webpack_require__(20911); +const { filterRuntime, mergeRuntime } = __webpack_require__(19655); +const ModuleDependency = __webpack_require__(80944); /** @typedef {import("webpack-sources").ReplaceSource} ReplaceSource */ -/** @typedef {import("../AsyncDependenciesBlock")} AsyncDependenciesBlock */ -/** @typedef {import("../Dependency")} Dependency */ +/** @typedef {import("webpack-sources").Source} Source */ +/** @typedef {import("../ChunkGraph")} ChunkGraph */ +/** @typedef {import("../Dependency").ReferencedExport} ReferencedExport */ +/** @typedef {import("../Dependency").UpdateHashContext} UpdateHashContext */ /** @typedef {import("../DependencyTemplate").DependencyTemplateContext} DependencyTemplateContext */ +/** @typedef {import("../Module")} Module */ +/** @typedef {import("../ModuleGraph")} ModuleGraph */ +/** @typedef {import("../RuntimeTemplate")} RuntimeTemplate */ +/** @typedef {import("../WebpackError")} WebpackError */ +/** @typedef {import("../util/Hash")} Hash */ +/** @typedef {import("../util/runtime").RuntimeSpec} RuntimeSpec */ -class RequireEnsureDependency extends NullDependency { - constructor(range, contentRange, errorHandlerRange) { - super(); +const ExportPresenceModes = { + NONE: /** @type {0} */ (0), + WARN: /** @type {1} */ (1), + AUTO: /** @type {2} */ (2), + ERROR: /** @type {3} */ (3), + fromUserOption(str) { + switch (str) { + case "error": + return ExportPresenceModes.ERROR; + case "warn": + return ExportPresenceModes.WARN; + case "auto": + return ExportPresenceModes.AUTO; + case false: + return ExportPresenceModes.NONE; + default: + throw new Error(`Invalid export presence value ${str}`); + } + } +}; + +class HarmonyImportDependency extends ModuleDependency { + /** + * + * @param {string} request request string + * @param {number} sourceOrder source order + * @param {Record=} assertions import assertions + */ + constructor(request, sourceOrder, assertions) { + super(request); + this.sourceOrder = sourceOrder; + this.assertions = assertions; + } + + get category() { + return "esm"; + } + + /** + * Returns list of exports referenced by this dependency + * @param {ModuleGraph} moduleGraph module graph + * @param {RuntimeSpec} runtime the runtime for which the module is analysed + * @returns {(string[] | ReferencedExport)[]} referenced exports + */ + getReferencedExports(moduleGraph, runtime) { + return Dependency.NO_EXPORTS_REFERENCED; + } + + /** + * @param {ModuleGraph} moduleGraph the module graph + * @returns {string} name of the variable for the import + */ + getImportVar(moduleGraph) { + const module = moduleGraph.getParentModule(this); + const meta = moduleGraph.getMeta(module); + let importVarMap = meta.importVarMap; + if (!importVarMap) meta.importVarMap = importVarMap = new Map(); + let importVar = importVarMap.get(moduleGraph.getModule(this)); + if (importVar) return importVar; + importVar = `${Template.toIdentifier( + `${this.userRequest}` + )}__WEBPACK_IMPORTED_MODULE_${importVarMap.size}__`; + importVarMap.set(moduleGraph.getModule(this), importVar); + return importVar; + } + + /** + * @param {boolean} update create new variables or update existing one + * @param {DependencyTemplateContext} templateContext the template context + * @returns {[string, string]} the import statement and the compat statement + */ + getImportStatement( + update, + { runtimeTemplate, module, moduleGraph, chunkGraph, runtimeRequirements } + ) { + return runtimeTemplate.importStatement({ + update, + module: moduleGraph.getModule(this), + chunkGraph, + importVar: this.getImportVar(moduleGraph), + request: this.request, + originModule: module, + runtimeRequirements + }); + } + + /** + * @param {ModuleGraph} moduleGraph module graph + * @param {string[]} ids imported ids + * @param {string} additionalMessage extra info included in the error message + * @returns {WebpackError[] | undefined} errors + */ + getLinkingErrors(moduleGraph, ids, additionalMessage) { + const importedModule = moduleGraph.getModule(this); + // ignore errors for missing or failed modules + if (!importedModule || importedModule.getNumberOfErrors() > 0) { + return; + } + + const parentModule = moduleGraph.getParentModule(this); + const exportsType = importedModule.getExportsType( + moduleGraph, + parentModule.buildMeta.strictHarmonyModule + ); + if (exportsType === "namespace" || exportsType === "default-with-named") { + if (ids.length === 0) { + return; + } + + if ( + (exportsType !== "default-with-named" || ids[0] !== "default") && + moduleGraph.isExportProvided(importedModule, ids) === false + ) { + // We are sure that it's not provided - this.range = range; - this.contentRange = contentRange; - this.errorHandlerRange = errorHandlerRange; - } + // Try to provide detailed info in the error message + let pos = 0; + let exportsInfo = moduleGraph.getExportsInfo(importedModule); + while (pos < ids.length && exportsInfo) { + const id = ids[pos++]; + const exportInfo = exportsInfo.getReadOnlyExportInfo(id); + if (exportInfo.provided === false) { + // We are sure that it's not provided + const providedExports = exportsInfo.getProvidedExports(); + const moreInfo = !Array.isArray(providedExports) + ? " (possible exports unknown)" + : providedExports.length === 0 + ? " (module has no exports)" + : ` (possible exports: ${providedExports.join(", ")})`; + return [ + new HarmonyLinkingError( + `export ${ids + .slice(0, pos) + .map(id => `'${id}'`) + .join(".")} ${additionalMessage} was not found in '${ + this.userRequest + }'${moreInfo}` + ) + ]; + } + exportsInfo = exportInfo.getNestedExportsInfo(); + } - get type() { - return "require.ensure"; + // General error message + return [ + new HarmonyLinkingError( + `export ${ids + .map(id => `'${id}'`) + .join(".")} ${additionalMessage} was not found in '${ + this.userRequest + }'` + ) + ]; + } + } + switch (exportsType) { + case "default-only": + // It's has only a default export + if (ids.length > 0 && ids[0] !== "default") { + // In strict harmony modules we only support the default export + return [ + new HarmonyLinkingError( + `Can't import the named export ${ids + .map(id => `'${id}'`) + .join( + "." + )} ${additionalMessage} from default-exporting module (only default export is available)` + ) + ]; + } + break; + case "default-with-named": + // It has a default export and named properties redirect + // In some cases we still want to warn here + if ( + ids.length > 0 && + ids[0] !== "default" && + importedModule.buildMeta.defaultObject === "redirect-warn" + ) { + // For these modules only the default export is supported + return [ + new HarmonyLinkingError( + `Should not import the named export ${ids + .map(id => `'${id}'`) + .join( + "." + )} ${additionalMessage} from default-exporting module (only default export is available soon)` + ) + ]; + } + break; + } } serialize(context) { const { write } = context; - - write(this.range); - write(this.contentRange); - write(this.errorHandlerRange); - + write(this.sourceOrder); + write(this.assertions); super.serialize(context); } deserialize(context) { const { read } = context; - - this.range = read(); - this.contentRange = read(); - this.errorHandlerRange = read(); - + this.sourceOrder = read(); + this.assertions = read(); super.deserialize(context); } } -makeSerializable( - RequireEnsureDependency, - "webpack/lib/dependencies/RequireEnsureDependency" -); +module.exports = HarmonyImportDependency; -RequireEnsureDependency.Template = class RequireEnsureDependencyTemplate extends ( - NullDependency.Template +/** @type {WeakMap>} */ +const importEmittedMap = new WeakMap(); + +HarmonyImportDependency.Template = class HarmonyImportDependencyTemplate extends ( + ModuleDependency.Template ) { /** * @param {Dependency} dependency the dependency for which the template should be applied @@ -84565,89 +82591,118 @@ RequireEnsureDependency.Template = class RequireEnsureDependencyTemplate extends * @param {DependencyTemplateContext} templateContext the context object * @returns {void} */ - apply( - dependency, - source, - { runtimeTemplate, moduleGraph, chunkGraph, runtimeRequirements } - ) { - const dep = /** @type {RequireEnsureDependency} */ (dependency); - const depBlock = /** @type {AsyncDependenciesBlock} */ ( - moduleGraph.getParentBlock(dep) - ); - const promise = runtimeTemplate.blockPromise({ - chunkGraph, - block: depBlock, - message: "require.ensure", - runtimeRequirements - }); - const range = dep.range; - const contentRange = dep.contentRange; - const errorHandlerRange = dep.errorHandlerRange; - source.replace(range[0], contentRange[0] - 1, `${promise}.then((`); - if (errorHandlerRange) { - source.replace( - contentRange[1], - errorHandlerRange[0] - 1, - ").bind(null, __webpack_require__))['catch'](" - ); - source.replace(errorHandlerRange[1], range[1] - 1, ")"); - } else { - source.replace( - contentRange[1], - range[1] - 1, - `).bind(null, __webpack_require__))['catch'](${RuntimeGlobals.uncaughtErrorHandler})` - ); - } - } -}; - -module.exports = RequireEnsureDependency; - - -/***/ }), + apply(dependency, source, templateContext) { + const dep = /** @type {HarmonyImportDependency} */ (dependency); + const { module, chunkGraph, moduleGraph, runtime } = templateContext; -/***/ 56867: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + const connection = moduleGraph.getConnection(dep); + if (connection && !connection.isTargetActive(runtime)) return; -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ + const referencedModule = connection && connection.module; + if ( + connection && + connection.weak && + referencedModule && + chunkGraph.getModuleId(referencedModule) === null + ) { + // in weak references, module might not be in any chunk + // but that's ok, we don't need that logic in this case + return; + } + const moduleKey = referencedModule + ? referencedModule.identifier() + : dep.request; + const key = `harmony import ${moduleKey}`; -const makeSerializable = __webpack_require__(26522); -const ModuleDependency = __webpack_require__(80944); -const NullDependency = __webpack_require__(65845); + const runtimeCondition = dep.weak + ? false + : connection + ? filterRuntime(runtime, r => connection.isTargetActive(r)) + : true; -class RequireEnsureItemDependency extends ModuleDependency { - constructor(request) { - super(request); - } + if (module && referencedModule) { + let emittedModules = importEmittedMap.get(module); + if (emittedModules === undefined) { + emittedModules = new WeakMap(); + importEmittedMap.set(module, emittedModules); + } + let mergedRuntimeCondition = runtimeCondition; + const oldRuntimeCondition = emittedModules.get(referencedModule) || false; + if (oldRuntimeCondition !== false && mergedRuntimeCondition !== true) { + if (mergedRuntimeCondition === false || oldRuntimeCondition === true) { + mergedRuntimeCondition = oldRuntimeCondition; + } else { + mergedRuntimeCondition = mergeRuntime( + oldRuntimeCondition, + mergedRuntimeCondition + ); + } + } + emittedModules.set(referencedModule, mergedRuntimeCondition); + } - get type() { - return "require.ensure item"; + const importStatement = dep.getImportStatement(false, templateContext); + if ( + referencedModule && + templateContext.moduleGraph.isAsync(referencedModule) + ) { + templateContext.initFragments.push( + new ConditionalInitFragment( + importStatement[0], + InitFragment.STAGE_HARMONY_IMPORTS, + dep.sourceOrder, + key, + runtimeCondition + ) + ); + templateContext.initFragments.push( + new AwaitDependenciesInitFragment( + new Set([dep.getImportVar(templateContext.moduleGraph)]) + ) + ); + templateContext.initFragments.push( + new ConditionalInitFragment( + importStatement[1], + InitFragment.STAGE_ASYNC_HARMONY_IMPORTS, + dep.sourceOrder, + key + " compat", + runtimeCondition + ) + ); + } else { + templateContext.initFragments.push( + new ConditionalInitFragment( + importStatement[0] + importStatement[1], + InitFragment.STAGE_HARMONY_IMPORTS, + dep.sourceOrder, + key, + runtimeCondition + ) + ); + } } - get category() { - return "commonjs"; + /** + * + * @param {Module} module the module + * @param {Module} referencedModule the referenced module + * @returns {RuntimeSpec | boolean} runtimeCondition in which this import has been emitted + */ + static getImportEmittedRuntime(module, referencedModule) { + const emittedModules = importEmittedMap.get(module); + if (emittedModules === undefined) return false; + return emittedModules.get(referencedModule) || false; } -} - -makeSerializable( - RequireEnsureItemDependency, - "webpack/lib/dependencies/RequireEnsureItemDependency" -); - -RequireEnsureItemDependency.Template = NullDependency.Template; +}; -module.exports = RequireEnsureItemDependency; +module.exports.ExportPresenceModes = ExportPresenceModes; /***/ }), -/***/ 66697: +/***/ 76581: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; @@ -84658,70 +82713,260 @@ module.exports = RequireEnsureItemDependency; -const RequireEnsureDependency = __webpack_require__(975); -const RequireEnsureItemDependency = __webpack_require__(56867); - -const RequireEnsureDependenciesBlockParserPlugin = __webpack_require__(95195); +const HotModuleReplacementPlugin = __webpack_require__(616); +const InnerGraph = __webpack_require__(92886); +const ConstDependency = __webpack_require__(60864); +const HarmonyAcceptDependency = __webpack_require__(38421); +const HarmonyAcceptImportDependency = __webpack_require__(35316); +const HarmonyExports = __webpack_require__(37637); +const { ExportPresenceModes } = __webpack_require__(19577); +const HarmonyImportSideEffectDependency = __webpack_require__(76853); +const HarmonyImportSpecifierDependency = __webpack_require__(61994); -const { - evaluateToString, - toConstantDependency -} = __webpack_require__(28723); +/** @typedef {import("estree").ExportAllDeclaration} ExportAllDeclaration */ +/** @typedef {import("estree").ExportNamedDeclaration} ExportNamedDeclaration */ +/** @typedef {import("estree").Identifier} Identifier */ +/** @typedef {import("estree").ImportDeclaration} ImportDeclaration */ +/** @typedef {import("estree").ImportExpression} ImportExpression */ +/** @typedef {import("../../declarations/WebpackOptions").JavascriptParserOptions} JavascriptParserOptions */ +/** @typedef {import("../javascript/JavascriptParser")} JavascriptParser */ +/** @typedef {import("../optimize/InnerGraph").InnerGraph} InnerGraph */ +/** @typedef {import("../optimize/InnerGraph").TopLevelSymbol} TopLevelSymbol */ +/** @typedef {import("./HarmonyImportDependency")} HarmonyImportDependency */ -class RequireEnsurePlugin { - apply(compiler) { - compiler.hooks.compilation.tap( - "RequireEnsurePlugin", - (compilation, { normalModuleFactory }) => { - compilation.dependencyFactories.set( - RequireEnsureItemDependency, - normalModuleFactory - ); - compilation.dependencyTemplates.set( - RequireEnsureItemDependency, - new RequireEnsureItemDependency.Template() - ); +const harmonySpecifierTag = Symbol("harmony import"); - compilation.dependencyTemplates.set( - RequireEnsureDependency, - new RequireEnsureDependency.Template() - ); +/** + * @typedef {Object} HarmonySettings + * @property {string[]} ids + * @property {string} source + * @property {number} sourceOrder + * @property {string} name + * @property {boolean} await + * @property {Record | undefined} assertions + */ - const handler = (parser, parserOptions) => { - if ( - parserOptions.requireEnsure !== undefined && - !parserOptions.requireEnsure - ) - return; +/** + * @param {ImportDeclaration | ExportNamedDeclaration | ExportAllDeclaration | ImportExpression} node node with assertions + * @returns {Record | undefined} assertions + */ +function getAssertions(node) { + // TODO remove cast when @types/estree has been updated to import assertions + const assertions = /** @type {{ assertions?: ImportAttributeNode[] }} */ ( + node + ).assertions; + if (assertions === undefined) { + return undefined; + } + const result = {}; + for (const assertion of assertions) { + const key = + assertion.key.type === "Identifier" + ? assertion.key.name + : assertion.key.value; + result[key] = assertion.value.value; + } + return result; +} - new RequireEnsureDependenciesBlockParserPlugin().apply(parser); - parser.hooks.evaluateTypeof - .for("require.ensure") - .tap("RequireEnsurePlugin", evaluateToString("function")); - parser.hooks.typeof - .for("require.ensure") - .tap( - "RequireEnsurePlugin", - toConstantDependency(parser, JSON.stringify("function")) - ); - }; +module.exports = class HarmonyImportDependencyParserPlugin { + /** + * @param {JavascriptParserOptions} options options + */ + constructor(options) { + this.exportPresenceMode = + options.importExportsPresence !== undefined + ? ExportPresenceModes.fromUserOption(options.importExportsPresence) + : options.exportsPresence !== undefined + ? ExportPresenceModes.fromUserOption(options.exportsPresence) + : options.strictExportPresence + ? ExportPresenceModes.ERROR + : ExportPresenceModes.AUTO; + this.strictThisContextOnImports = options.strictThisContextOnImports; + } - normalModuleFactory.hooks.parser - .for("javascript/auto") - .tap("RequireEnsurePlugin", handler); - normalModuleFactory.hooks.parser - .for("javascript/dynamic") - .tap("RequireEnsurePlugin", handler); + /** + * @param {JavascriptParser} parser the parser + * @returns {void} + */ + apply(parser) { + const { exportPresenceMode } = this; + parser.hooks.isPure + .for("Identifier") + .tap("HarmonyImportDependencyParserPlugin", expression => { + const expr = /** @type {Identifier} */ (expression); + if ( + parser.isVariableDefined(expr.name) || + parser.getTagData(expr.name, harmonySpecifierTag) + ) { + return true; + } + }); + parser.hooks.import.tap( + "HarmonyImportDependencyParserPlugin", + (statement, source) => { + parser.state.lastHarmonyImportOrder = + (parser.state.lastHarmonyImportOrder || 0) + 1; + const clearDep = new ConstDependency( + parser.isAsiPosition(statement.range[0]) ? ";" : "", + statement.range + ); + clearDep.loc = statement.loc; + parser.state.module.addPresentationalDependency(clearDep); + parser.unsetAsiPosition(statement.range[1]); + const assertions = getAssertions(statement); + const sideEffectDep = new HarmonyImportSideEffectDependency( + source, + parser.state.lastHarmonyImportOrder, + assertions + ); + sideEffectDep.loc = statement.loc; + parser.state.module.addDependency(sideEffectDep); + return true; + } + ); + parser.hooks.importSpecifier.tap( + "HarmonyImportDependencyParserPlugin", + (statement, source, id, name) => { + const ids = id === null ? [] : [id]; + parser.tagVariable(name, harmonySpecifierTag, { + name, + source, + ids, + sourceOrder: parser.state.lastHarmonyImportOrder, + assertions: getAssertions(statement) + }); + return true; + } + ); + parser.hooks.expression + .for(harmonySpecifierTag) + .tap("HarmonyImportDependencyParserPlugin", expr => { + const settings = /** @type {HarmonySettings} */ (parser.currentTagData); + const dep = new HarmonyImportSpecifierDependency( + settings.source, + settings.sourceOrder, + settings.ids, + settings.name, + expr.range, + exportPresenceMode, + settings.assertions + ); + dep.shorthand = parser.scope.inShorthand; + dep.directImport = true; + dep.asiSafe = !parser.isAsiPosition(expr.range[0]); + dep.loc = expr.loc; + parser.state.module.addDependency(dep); + InnerGraph.onUsage(parser.state, e => (dep.usedByExports = e)); + return true; + }); + parser.hooks.expressionMemberChain + .for(harmonySpecifierTag) + .tap("HarmonyImportDependencyParserPlugin", (expr, members) => { + const settings = /** @type {HarmonySettings} */ (parser.currentTagData); + const ids = settings.ids.concat(members); + const dep = new HarmonyImportSpecifierDependency( + settings.source, + settings.sourceOrder, + ids, + settings.name, + expr.range, + exportPresenceMode, + settings.assertions + ); + dep.asiSafe = !parser.isAsiPosition(expr.range[0]); + dep.loc = expr.loc; + parser.state.module.addDependency(dep); + InnerGraph.onUsage(parser.state, e => (dep.usedByExports = e)); + return true; + }); + parser.hooks.callMemberChain + .for(harmonySpecifierTag) + .tap("HarmonyImportDependencyParserPlugin", (expr, members) => { + const { arguments: args, callee } = expr; + const settings = /** @type {HarmonySettings} */ (parser.currentTagData); + const ids = settings.ids.concat(members); + const dep = new HarmonyImportSpecifierDependency( + settings.source, + settings.sourceOrder, + ids, + settings.name, + callee.range, + exportPresenceMode, + settings.assertions + ); + dep.directImport = members.length === 0; + dep.call = true; + dep.asiSafe = !parser.isAsiPosition(callee.range[0]); + // only in case when we strictly follow the spec we need a special case here + dep.namespaceObjectAsContext = + members.length > 0 && this.strictThisContextOnImports; + dep.loc = callee.loc; + parser.state.module.addDependency(dep); + if (args) parser.walkExpressions(args); + InnerGraph.onUsage(parser.state, e => (dep.usedByExports = e)); + return true; + }); + const { hotAcceptCallback, hotAcceptWithoutCallback } = + HotModuleReplacementPlugin.getParserHooks(parser); + hotAcceptCallback.tap( + "HarmonyImportDependencyParserPlugin", + (expr, requests) => { + if (!HarmonyExports.isEnabled(parser.state)) { + // This is not a harmony module, skip it + return; + } + const dependencies = requests.map(request => { + const dep = new HarmonyAcceptImportDependency(request); + dep.loc = expr.loc; + parser.state.module.addDependency(dep); + return dep; + }); + if (dependencies.length > 0) { + const dep = new HarmonyAcceptDependency( + expr.range, + dependencies, + true + ); + dep.loc = expr.loc; + parser.state.module.addDependency(dep); + } + } + ); + hotAcceptWithoutCallback.tap( + "HarmonyImportDependencyParserPlugin", + (expr, requests) => { + if (!HarmonyExports.isEnabled(parser.state)) { + // This is not a harmony module, skip it + return; + } + const dependencies = requests.map(request => { + const dep = new HarmonyAcceptImportDependency(request); + dep.loc = expr.loc; + parser.state.module.addDependency(dep); + return dep; + }); + if (dependencies.length > 0) { + const dep = new HarmonyAcceptDependency( + expr.range, + dependencies, + false + ); + dep.loc = expr.loc; + parser.state.module.addDependency(dep); + } } ); } -} -module.exports = RequireEnsurePlugin; +}; + +module.exports.harmonySpecifierTag = harmonySpecifierTag; +module.exports.getAssertions = getAssertions; /***/ }), -/***/ 57010: +/***/ 76853: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; @@ -84732,41 +82977,59 @@ module.exports = RequireEnsurePlugin; -const RuntimeGlobals = __webpack_require__(49404); const makeSerializable = __webpack_require__(26522); -const NullDependency = __webpack_require__(65845); +const HarmonyImportDependency = __webpack_require__(19577); /** @typedef {import("webpack-sources").ReplaceSource} ReplaceSource */ /** @typedef {import("../Dependency")} Dependency */ /** @typedef {import("../DependencyTemplate").DependencyTemplateContext} DependencyTemplateContext */ +/** @typedef {import("../InitFragment")} InitFragment */ +/** @typedef {import("../Module")} Module */ +/** @typedef {import("../ModuleGraph")} ModuleGraph */ +/** @typedef {import("../ModuleGraphConnection")} ModuleGraphConnection */ +/** @typedef {import("../ModuleGraphConnection").ConnectionState} ConnectionState */ +/** @typedef {import("../util/Hash")} Hash */ +/** @typedef {import("../util/runtime").RuntimeSpec} RuntimeSpec */ -class RequireHeaderDependency extends NullDependency { - constructor(range) { - super(); - if (!Array.isArray(range)) throw new Error("range must be valid"); - this.range = range; +class HarmonyImportSideEffectDependency extends HarmonyImportDependency { + constructor(request, sourceOrder, assertions) { + super(request, sourceOrder, assertions); } - serialize(context) { - const { write } = context; - write(this.range); - super.serialize(context); + get type() { + return "harmony side effect evaluation"; } - static deserialize(context) { - const obj = new RequireHeaderDependency(context.read()); - obj.deserialize(context); - return obj; + /** + * @param {ModuleGraph} moduleGraph module graph + * @returns {null | false | function(ModuleGraphConnection, RuntimeSpec): ConnectionState} function to determine if the connection is active + */ + getCondition(moduleGraph) { + return connection => { + const refModule = connection.resolvedModule; + if (!refModule) return true; + return refModule.getSideEffectsConnectionState(moduleGraph); + }; + } + + /** + * @param {ModuleGraph} moduleGraph the module graph + * @returns {ConnectionState} how this dependency connects the module to referencing modules + */ + getModuleEvaluationSideEffectsState(moduleGraph) { + const refModule = moduleGraph.getModule(this); + if (!refModule) return true; + return refModule.getSideEffectsConnectionState(moduleGraph); } } makeSerializable( - RequireHeaderDependency, - "webpack/lib/dependencies/RequireHeaderDependency" + HarmonyImportSideEffectDependency, + "webpack/lib/dependencies/HarmonyImportSideEffectDependency" ); -RequireHeaderDependency.Template = class RequireHeaderDependencyTemplate extends ( - NullDependency.Template +HarmonyImportSideEffectDependency.Template = class HarmonyImportSideEffectDependencyTemplate extends ( + HarmonyImportDependency.Template ) { /** * @param {Dependency} dependency the dependency for which the template should be applied @@ -84774,19 +83037,24 @@ RequireHeaderDependency.Template = class RequireHeaderDependencyTemplate extends * @param {DependencyTemplateContext} templateContext the context object * @returns {void} */ - apply(dependency, source, { runtimeRequirements }) { - const dep = /** @type {RequireHeaderDependency} */ (dependency); - runtimeRequirements.add(RuntimeGlobals.require); - source.replace(dep.range[0], dep.range[1] - 1, "__webpack_require__"); + apply(dependency, source, templateContext) { + const { moduleGraph, concatenationScope } = templateContext; + if (concatenationScope) { + const module = moduleGraph.getModule(dependency); + if (concatenationScope.isModuleInScope(module)) { + return; + } + } + super.apply(dependency, source, templateContext); } }; -module.exports = RequireHeaderDependency; +module.exports = HarmonyImportSideEffectDependency; /***/ }), -/***/ 17046: +/***/ 61994: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; @@ -84798,21 +83066,111 @@ module.exports = RequireHeaderDependency; const Dependency = __webpack_require__(50384); -const Template = __webpack_require__(92066); +const { + getDependencyUsedByExportsCondition +} = __webpack_require__(92886); const makeSerializable = __webpack_require__(26522); -const ModuleDependency = __webpack_require__(80944); +const propertyAccess = __webpack_require__(86709); +const HarmonyImportDependency = __webpack_require__(19577); /** @typedef {import("webpack-sources").ReplaceSource} ReplaceSource */ +/** @typedef {import("../ChunkGraph")} ChunkGraph */ +/** @typedef {import("../Dependency").ExportsSpec} ExportsSpec */ /** @typedef {import("../Dependency").ReferencedExport} ReferencedExport */ +/** @typedef {import("../Dependency").UpdateHashContext} UpdateHashContext */ /** @typedef {import("../DependencyTemplate").DependencyTemplateContext} DependencyTemplateContext */ /** @typedef {import("../ModuleGraph")} ModuleGraph */ +/** @typedef {import("../ModuleGraphConnection")} ModuleGraphConnection */ +/** @typedef {import("../ModuleGraphConnection").ConnectionState} ConnectionState */ +/** @typedef {import("../WebpackError")} WebpackError */ +/** @typedef {import("../util/Hash")} Hash */ /** @typedef {import("../util/runtime").RuntimeSpec} RuntimeSpec */ -class RequireIncludeDependency extends ModuleDependency { - constructor(request, range) { - super(request); +const idsSymbol = Symbol("HarmonyImportSpecifierDependency.ids"); + +const { ExportPresenceModes } = HarmonyImportDependency; +class HarmonyImportSpecifierDependency extends HarmonyImportDependency { + constructor( + request, + sourceOrder, + ids, + name, + range, + exportPresenceMode, + assertions + ) { + super(request, sourceOrder, assertions); + this.ids = ids; + this.name = name; this.range = range; + this.exportPresenceMode = exportPresenceMode; + this.namespaceObjectAsContext = false; + this.call = undefined; + this.directImport = undefined; + this.shorthand = undefined; + this.asiSafe = undefined; + /** @type {Set | boolean} */ + this.usedByExports = undefined; + } + + // TODO webpack 6 remove + get id() { + throw new Error("id was renamed to ids and type changed to string[]"); + } + + // TODO webpack 6 remove + getId() { + throw new Error("id was renamed to ids and type changed to string[]"); + } + + // TODO webpack 6 remove + setId() { + throw new Error("id was renamed to ids and type changed to string[]"); + } + + get type() { + return "harmony import specifier"; + } + + /** + * @param {ModuleGraph} moduleGraph the module graph + * @returns {string[]} the imported ids + */ + getIds(moduleGraph) { + const meta = moduleGraph.getMetaIfExisting(this); + if (meta === undefined) return this.ids; + const ids = meta[idsSymbol]; + return ids !== undefined ? ids : this.ids; + } + + /** + * @param {ModuleGraph} moduleGraph the module graph + * @param {string[]} ids the imported ids + * @returns {void} + */ + setIds(moduleGraph, ids) { + moduleGraph.getMeta(this)[idsSymbol] = ids; + } + + /** + * @param {ModuleGraph} moduleGraph module graph + * @returns {null | false | function(ModuleGraphConnection, RuntimeSpec): ConnectionState} function to determine if the connection is active + */ + getCondition(moduleGraph) { + return getDependencyUsedByExportsCondition( + this, + this.usedByExports, + moduleGraph + ); + } + + /** + * @param {ModuleGraph} moduleGraph the module graph + * @returns {ConnectionState} how this dependency connects the module to referencing modules + */ + getModuleEvaluationSideEffectsState(moduleGraph) { + return false; } /** @@ -84822,26 +83180,138 @@ class RequireIncludeDependency extends ModuleDependency { * @returns {(string[] | ReferencedExport)[]} referenced exports */ getReferencedExports(moduleGraph, runtime) { - // This doesn't use any export - return Dependency.NO_EXPORTS_REFERENCED; + let ids = this.getIds(moduleGraph); + if (ids.length === 0) return Dependency.EXPORTS_OBJECT_REFERENCED; + let namespaceObjectAsContext = this.namespaceObjectAsContext; + if (ids[0] === "default") { + const selfModule = moduleGraph.getParentModule(this); + const importedModule = moduleGraph.getModule(this); + switch ( + importedModule.getExportsType( + moduleGraph, + selfModule.buildMeta.strictHarmonyModule + ) + ) { + case "default-only": + case "default-with-named": + if (ids.length === 1) return Dependency.EXPORTS_OBJECT_REFERENCED; + ids = ids.slice(1); + namespaceObjectAsContext = true; + break; + case "dynamic": + return Dependency.EXPORTS_OBJECT_REFERENCED; + } + } + + if ( + this.call && + !this.directImport && + (namespaceObjectAsContext || ids.length > 1) + ) { + if (ids.length === 1) return Dependency.EXPORTS_OBJECT_REFERENCED; + ids = ids.slice(0, -1); + } + + return [ids]; } - get type() { - return "require.include"; + /** + * @param {ModuleGraph} moduleGraph module graph + * @returns {number} effective mode + */ + _getEffectiveExportPresenceLevel(moduleGraph) { + if (this.exportPresenceMode !== ExportPresenceModes.AUTO) + return this.exportPresenceMode; + return moduleGraph.getParentModule(this).buildMeta.strictHarmonyModule + ? ExportPresenceModes.ERROR + : ExportPresenceModes.WARN; } - get category() { - return "commonjs"; + /** + * Returns warnings + * @param {ModuleGraph} moduleGraph module graph + * @returns {WebpackError[]} warnings + */ + getWarnings(moduleGraph) { + const exportsPresence = this._getEffectiveExportPresenceLevel(moduleGraph); + if (exportsPresence === ExportPresenceModes.WARN) { + return this._getErrors(moduleGraph); + } + return null; + } + + /** + * Returns errors + * @param {ModuleGraph} moduleGraph module graph + * @returns {WebpackError[]} errors + */ + getErrors(moduleGraph) { + const exportsPresence = this._getEffectiveExportPresenceLevel(moduleGraph); + if (exportsPresence === ExportPresenceModes.ERROR) { + return this._getErrors(moduleGraph); + } + return null; + } + + /** + * @param {ModuleGraph} moduleGraph module graph + * @returns {WebpackError[] | undefined} errors + */ + _getErrors(moduleGraph) { + const ids = this.getIds(moduleGraph); + return this.getLinkingErrors( + moduleGraph, + ids, + `(imported as '${this.name}')` + ); + } + + /** + * implement this method to allow the occurrence order plugin to count correctly + * @returns {number} count how often the id is used in this dependency + */ + getNumberOfIdOccurrences() { + return 0; + } + + serialize(context) { + const { write } = context; + write(this.ids); + write(this.name); + write(this.range); + write(this.exportPresenceMode); + write(this.namespaceObjectAsContext); + write(this.call); + write(this.directImport); + write(this.shorthand); + write(this.asiSafe); + write(this.usedByExports); + super.serialize(context); + } + + deserialize(context) { + const { read } = context; + this.ids = read(); + this.name = read(); + this.range = read(); + this.exportPresenceMode = read(); + this.namespaceObjectAsContext = read(); + this.call = read(); + this.directImport = read(); + this.shorthand = read(); + this.asiSafe = read(); + this.usedByExports = read(); + super.deserialize(context); } } makeSerializable( - RequireIncludeDependency, - "webpack/lib/dependencies/RequireIncludeDependency" + HarmonyImportSpecifierDependency, + "webpack/lib/dependencies/HarmonyImportSpecifierDependency" ); -RequireIncludeDependency.Template = class RequireIncludeDependencyTemplate extends ( - ModuleDependency.Template +HarmonyImportSpecifierDependency.Template = class HarmonyImportSpecifierDependencyTemplate extends ( + HarmonyImportDependency.Template ) { /** * @param {Dependency} dependency the dependency for which the template should be applied @@ -84849,26 +83319,81 @@ RequireIncludeDependency.Template = class RequireIncludeDependencyTemplate exten * @param {DependencyTemplateContext} templateContext the context object * @returns {void} */ - apply(dependency, source, { runtimeTemplate }) { - const dep = /** @type {RequireIncludeDependency} */ (dependency); - const comment = runtimeTemplate.outputOptions.pathinfo - ? Template.toComment( - `require.include ${runtimeTemplate.requestShortener.shorten( - dep.request - )}` - ) - : ""; + apply(dependency, source, templateContext) { + const dep = /** @type {HarmonyImportSpecifierDependency} */ (dependency); + const { moduleGraph, module, runtime, concatenationScope } = + templateContext; + const connection = moduleGraph.getConnection(dep); + // Skip rendering depending when dependency is conditional + if (connection && !connection.isTargetActive(runtime)) return; - source.replace(dep.range[0], dep.range[1] - 1, `undefined${comment}`); + const ids = dep.getIds(moduleGraph); + + let exportExpr; + if ( + connection && + concatenationScope && + concatenationScope.isModuleInScope(connection.module) + ) { + if (ids.length === 0) { + exportExpr = concatenationScope.createModuleReference( + connection.module, + { + asiSafe: dep.asiSafe + } + ); + } else if (dep.namespaceObjectAsContext && ids.length === 1) { + exportExpr = + concatenationScope.createModuleReference(connection.module, { + asiSafe: dep.asiSafe + }) + propertyAccess(ids); + } else { + exportExpr = concatenationScope.createModuleReference( + connection.module, + { + ids, + call: dep.call, + directImport: dep.directImport, + asiSafe: dep.asiSafe + } + ); + } + } else { + super.apply(dependency, source, templateContext); + + const { runtimeTemplate, initFragments, runtimeRequirements } = + templateContext; + + exportExpr = runtimeTemplate.exportFromImport({ + moduleGraph, + module: moduleGraph.getModule(dep), + request: dep.request, + exportName: ids, + originModule: module, + asiSafe: dep.shorthand ? true : dep.asiSafe, + isCall: dep.call, + callContext: !dep.directImport, + defaultInterop: true, + importVar: dep.getImportVar(moduleGraph), + initFragments, + runtime, + runtimeRequirements + }); + } + if (dep.shorthand) { + source.insert(dep.range[1], `: ${exportExpr}`); + } else { + source.replace(dep.range[0], dep.range[1] - 1, exportExpr); + } } }; -module.exports = RequireIncludeDependency; +module.exports = HarmonyImportSpecifierDependency; /***/ }), -/***/ 29984: +/***/ 73365: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; @@ -84879,131 +83404,160 @@ module.exports = RequireIncludeDependency; -const WebpackError = __webpack_require__(68422); -const { - evaluateToString, - toConstantDependency -} = __webpack_require__(28723); -const makeSerializable = __webpack_require__(26522); -const RequireIncludeDependency = __webpack_require__(17046); - -module.exports = class RequireIncludeDependencyParserPlugin { - constructor(warn) { - this.warn = warn; - } - apply(parser) { - const { warn } = this; - parser.hooks.call - .for("require.include") - .tap("RequireIncludeDependencyParserPlugin", expr => { - if (expr.arguments.length !== 1) return; - const param = parser.evaluateExpression(expr.arguments[0]); - if (!param.isString()) return; - - if (warn) { - parser.state.module.addWarning( - new RequireIncludeDeprecationWarning(expr.loc) - ); - } - - const dep = new RequireIncludeDependency(param.string, expr.range); - dep.loc = expr.loc; - parser.state.current.addDependency(dep); - return true; - }); - parser.hooks.evaluateTypeof - .for("require.include") - .tap("RequireIncludePlugin", expr => { - if (warn) { - parser.state.module.addWarning( - new RequireIncludeDeprecationWarning(expr.loc) - ); - } - return evaluateToString("function")(expr); - }); - parser.hooks.typeof - .for("require.include") - .tap("RequireIncludePlugin", expr => { - if (warn) { - parser.state.module.addWarning( - new RequireIncludeDeprecationWarning(expr.loc) - ); - } - return toConstantDependency(parser, JSON.stringify("function"))(expr); - }); - } -}; +const HarmonyAcceptDependency = __webpack_require__(38421); +const HarmonyAcceptImportDependency = __webpack_require__(35316); +const HarmonyCompatibilityDependency = __webpack_require__(56164); +const HarmonyExportExpressionDependency = __webpack_require__(22705); +const HarmonyExportHeaderDependency = __webpack_require__(67159); +const HarmonyExportImportedSpecifierDependency = __webpack_require__(77952); +const HarmonyExportSpecifierDependency = __webpack_require__(59042); +const HarmonyImportSideEffectDependency = __webpack_require__(76853); +const HarmonyImportSpecifierDependency = __webpack_require__(61994); -class RequireIncludeDeprecationWarning extends WebpackError { - constructor(loc) { - super("require.include() is deprecated and will be removed soon."); +const HarmonyDetectionParserPlugin = __webpack_require__(63683); +const HarmonyExportDependencyParserPlugin = __webpack_require__(70925); +const HarmonyImportDependencyParserPlugin = __webpack_require__(76581); +const HarmonyTopLevelThisParserPlugin = __webpack_require__(79065); - this.name = "RequireIncludeDeprecationWarning"; +/** @typedef {import("../Compiler")} Compiler */ - this.loc = loc; +class HarmonyModulesPlugin { + constructor(options) { + this.options = options; } -} -makeSerializable( - RequireIncludeDeprecationWarning, - "webpack/lib/dependencies/RequireIncludeDependencyParserPlugin", - "RequireIncludeDeprecationWarning" -); + /** + * Apply the plugin + * @param {Compiler} compiler the compiler instance + * @returns {void} + */ + apply(compiler) { + compiler.hooks.compilation.tap( + "HarmonyModulesPlugin", + (compilation, { normalModuleFactory }) => { + compilation.dependencyTemplates.set( + HarmonyCompatibilityDependency, + new HarmonyCompatibilityDependency.Template() + ); + compilation.dependencyFactories.set( + HarmonyImportSideEffectDependency, + normalModuleFactory + ); + compilation.dependencyTemplates.set( + HarmonyImportSideEffectDependency, + new HarmonyImportSideEffectDependency.Template() + ); -/***/ }), + compilation.dependencyFactories.set( + HarmonyImportSpecifierDependency, + normalModuleFactory + ); + compilation.dependencyTemplates.set( + HarmonyImportSpecifierDependency, + new HarmonyImportSpecifierDependency.Template() + ); -/***/ 83683: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + compilation.dependencyTemplates.set( + HarmonyExportHeaderDependency, + new HarmonyExportHeaderDependency.Template() + ); -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ + compilation.dependencyTemplates.set( + HarmonyExportExpressionDependency, + new HarmonyExportExpressionDependency.Template() + ); + compilation.dependencyTemplates.set( + HarmonyExportSpecifierDependency, + new HarmonyExportSpecifierDependency.Template() + ); + compilation.dependencyFactories.set( + HarmonyExportImportedSpecifierDependency, + normalModuleFactory + ); + compilation.dependencyTemplates.set( + HarmonyExportImportedSpecifierDependency, + new HarmonyExportImportedSpecifierDependency.Template() + ); -const RequireIncludeDependency = __webpack_require__(17046); -const RequireIncludeDependencyParserPlugin = __webpack_require__(29984); + compilation.dependencyTemplates.set( + HarmonyAcceptDependency, + new HarmonyAcceptDependency.Template() + ); -class RequireIncludePlugin { - apply(compiler) { - compiler.hooks.compilation.tap( - "RequireIncludePlugin", - (compilation, { normalModuleFactory }) => { compilation.dependencyFactories.set( - RequireIncludeDependency, + HarmonyAcceptImportDependency, normalModuleFactory ); compilation.dependencyTemplates.set( - RequireIncludeDependency, - new RequireIncludeDependency.Template() + HarmonyAcceptImportDependency, + new HarmonyAcceptImportDependency.Template() ); const handler = (parser, parserOptions) => { - if (parserOptions.requireInclude === false) return; - const warn = parserOptions.requireInclude === undefined; + // TODO webpack 6: rename harmony to esm or module + if (parserOptions.harmony !== undefined && !parserOptions.harmony) + return; - new RequireIncludeDependencyParserPlugin(warn).apply(parser); + new HarmonyDetectionParserPlugin(this.options).apply(parser); + new HarmonyImportDependencyParserPlugin(parserOptions).apply(parser); + new HarmonyExportDependencyParserPlugin(parserOptions).apply(parser); + new HarmonyTopLevelThisParserPlugin().apply(parser); }; normalModuleFactory.hooks.parser .for("javascript/auto") - .tap("RequireIncludePlugin", handler); + .tap("HarmonyModulesPlugin", handler); normalModuleFactory.hooks.parser - .for("javascript/dynamic") - .tap("RequireIncludePlugin", handler); + .for("javascript/esm") + .tap("HarmonyModulesPlugin", handler); } ); } } -module.exports = RequireIncludePlugin; +module.exports = HarmonyModulesPlugin; /***/ }), -/***/ 48789: +/***/ 79065: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Florent Cailhol @ooflorent +*/ + + + +const ConstDependency = __webpack_require__(60864); +const HarmonyExports = __webpack_require__(37637); + +class HarmonyTopLevelThisParserPlugin { + apply(parser) { + parser.hooks.expression + .for("this") + .tap("HarmonyTopLevelThisParserPlugin", node => { + if (!parser.scope.topLevelScope) return; + if (HarmonyExports.isEnabled(parser.state)) { + const dep = new ConstDependency("undefined", node.range, null); + dep.loc = node.loc; + parser.state.module.addPresentationalDependency(dep); + return this; + } + }); + } +} + +module.exports = HarmonyTopLevelThisParserPlugin; + + +/***/ }), + +/***/ 75785: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; @@ -85016,9 +83570,9 @@ module.exports = RequireIncludePlugin; const makeSerializable = __webpack_require__(26522); const ContextDependency = __webpack_require__(67840); -const ContextDependencyTemplateAsId = __webpack_require__(95080); +const ContextDependencyTemplateAsRequireCall = __webpack_require__(18259); -class RequireResolveContextDependency extends ContextDependency { +class ImportContextDependency extends ContextDependency { constructor(options, range, valueRange) { super(options); @@ -85027,7 +83581,11 @@ class RequireResolveContextDependency extends ContextDependency { } get type() { - return "amd require context"; + return `import() context ${this.options.mode}`; + } + + get category() { + return "esm"; } serialize(context) { @@ -85050,18 +83608,18 @@ class RequireResolveContextDependency extends ContextDependency { } makeSerializable( - RequireResolveContextDependency, - "webpack/lib/dependencies/RequireResolveContextDependency" + ImportContextDependency, + "webpack/lib/dependencies/ImportContextDependency" ); -RequireResolveContextDependency.Template = ContextDependencyTemplateAsId; +ImportContextDependency.Template = ContextDependencyTemplateAsRequireCall; -module.exports = RequireResolveContextDependency; +module.exports = ImportContextDependency; /***/ }), -/***/ 93172: +/***/ 16727: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; @@ -85075,25 +83633,32 @@ module.exports = RequireResolveContextDependency; const Dependency = __webpack_require__(50384); const makeSerializable = __webpack_require__(26522); const ModuleDependency = __webpack_require__(80944); -const ModuleDependencyAsId = __webpack_require__(35795); +/** @typedef {import("webpack-sources").ReplaceSource} ReplaceSource */ +/** @typedef {import("../AsyncDependenciesBlock")} AsyncDependenciesBlock */ /** @typedef {import("../Dependency").ReferencedExport} ReferencedExport */ +/** @typedef {import("../DependencyTemplate").DependencyTemplateContext} DependencyTemplateContext */ /** @typedef {import("../ModuleGraph")} ModuleGraph */ /** @typedef {import("../util/runtime").RuntimeSpec} RuntimeSpec */ -class RequireResolveDependency extends ModuleDependency { - constructor(request, range) { +class ImportDependency extends ModuleDependency { + /** + * @param {string} request the request + * @param {[number, number]} range expression range + * @param {string[][]=} referencedExports list of referenced exports + */ + constructor(request, range, referencedExports) { super(request); - this.range = range; + this.referencedExports = referencedExports; } get type() { - return "require.resolve"; + return "import()"; } get category() { - return "commonjs"; + return "esm"; } /** @@ -85103,159 +83668,31 @@ class RequireResolveDependency extends ModuleDependency { * @returns {(string[] | ReferencedExport)[]} referenced exports */ getReferencedExports(moduleGraph, runtime) { - // This doesn't use any export - return Dependency.NO_EXPORTS_REFERENCED; - } -} - -makeSerializable( - RequireResolveDependency, - "webpack/lib/dependencies/RequireResolveDependency" -); - -RequireResolveDependency.Template = ModuleDependencyAsId; - -module.exports = RequireResolveDependency; - - -/***/ }), - -/***/ 24128: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ - - - -const makeSerializable = __webpack_require__(26522); -const NullDependency = __webpack_require__(65845); - -/** @typedef {import("webpack-sources").ReplaceSource} ReplaceSource */ -/** @typedef {import("../Dependency")} Dependency */ -/** @typedef {import("../DependencyTemplate").DependencyTemplateContext} DependencyTemplateContext */ - -class RequireResolveHeaderDependency extends NullDependency { - constructor(range) { - super(); - - if (!Array.isArray(range)) throw new Error("range must be valid"); - - this.range = range; - } - - serialize(context) { - const { write } = context; - - write(this.range); - - super.serialize(context); - } - - static deserialize(context) { - const obj = new RequireResolveHeaderDependency(context.read()); - obj.deserialize(context); - return obj; - } -} - -makeSerializable( - RequireResolveHeaderDependency, - "webpack/lib/dependencies/RequireResolveHeaderDependency" -); - -RequireResolveHeaderDependency.Template = class RequireResolveHeaderDependencyTemplate extends ( - NullDependency.Template -) { - /** - * @param {Dependency} dependency the dependency for which the template should be applied - * @param {ReplaceSource} source the current replace source which can be modified - * @param {DependencyTemplateContext} templateContext the context object - * @returns {void} - */ - apply(dependency, source, templateContext) { - const dep = /** @type {RequireResolveHeaderDependency} */ (dependency); - source.replace(dep.range[0], dep.range[1] - 1, "/*require.resolve*/"); - } - - applyAsTemplateArgument(name, dep, source) { - source.replace(dep.range[0], dep.range[1] - 1, "/*require.resolve*/"); - } -}; - -module.exports = RequireResolveHeaderDependency; - - -/***/ }), - -/***/ 75941: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ - - - -const makeSerializable = __webpack_require__(26522); -const NullDependency = __webpack_require__(65845); - -/** @typedef {import("webpack-sources").ReplaceSource} ReplaceSource */ -/** @typedef {import("../ChunkGraph")} ChunkGraph */ -/** @typedef {import("../Dependency")} Dependency */ -/** @typedef {import("../Dependency").UpdateHashContext} UpdateHashContext */ -/** @typedef {import("../DependencyTemplate").DependencyTemplateContext} DependencyTemplateContext */ -/** @typedef {import("../ModuleGraph")} ModuleGraph */ -/** @typedef {import("../util/Hash")} Hash */ - -class RuntimeRequirementsDependency extends NullDependency { - /** - * @param {string[]} runtimeRequirements runtime requirements - */ - constructor(runtimeRequirements) { - super(); - this.runtimeRequirements = new Set(runtimeRequirements); - this._hashUpdate = undefined; - } - - /** - * Update the hash - * @param {Hash} hash hash to be updated - * @param {UpdateHashContext} context context - * @returns {void} - */ - updateHash(hash, context) { - if (this._hashUpdate === undefined) { - this._hashUpdate = Array.from(this.runtimeRequirements).join() + ""; - } - hash.update(this._hashUpdate); + return this.referencedExports + ? this.referencedExports.map(e => ({ + name: e, + canMangle: false + })) + : Dependency.EXPORTS_OBJECT_REFERENCED; } serialize(context) { - const { write } = context; - write(this.runtimeRequirements); + context.write(this.range); + context.write(this.referencedExports); super.serialize(context); } deserialize(context) { - const { read } = context; - this.runtimeRequirements = read(); + this.range = context.read(); + this.referencedExports = context.read(); super.deserialize(context); } } -makeSerializable( - RuntimeRequirementsDependency, - "webpack/lib/dependencies/RuntimeRequirementsDependency" -); +makeSerializable(ImportDependency, "webpack/lib/dependencies/ImportDependency"); -RuntimeRequirementsDependency.Template = class RuntimeRequirementsDependencyTemplate extends ( - NullDependency.Template +ImportDependency.Template = class ImportDependencyTemplate extends ( + ModuleDependency.Template ) { /** * @param {Dependency} dependency the dependency for which the template should be applied @@ -85263,285 +83700,155 @@ RuntimeRequirementsDependency.Template = class RuntimeRequirementsDependencyTemp * @param {DependencyTemplateContext} templateContext the context object * @returns {void} */ - apply(dependency, source, { runtimeRequirements }) { - const dep = /** @type {RuntimeRequirementsDependency} */ (dependency); - for (const req of dep.runtimeRequirements) { - runtimeRequirements.add(req); - } - } -}; - -module.exports = RuntimeRequirementsDependency; - - -/***/ }), - -/***/ 67967: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ - - - -const makeSerializable = __webpack_require__(26522); -const NullDependency = __webpack_require__(65845); - -/** @typedef {import("../ChunkGraph")} ChunkGraph */ -/** @typedef {import("../Dependency").ExportSpec} ExportSpec */ -/** @typedef {import("../Dependency").ExportsSpec} ExportsSpec */ -/** @typedef {import("../Dependency").UpdateHashContext} UpdateHashContext */ -/** @typedef {import("../ModuleGraph")} ModuleGraph */ -/** @typedef {import("../util/Hash")} Hash */ - -class StaticExportsDependency extends NullDependency { - /** - * @param {string[] | true} exports export names - * @param {boolean} canMangle true, if mangling exports names is allowed - */ - constructor(exports, canMangle) { - super(); - this.exports = exports; - this.canMangle = canMangle; - } - - get type() { - return "static exports"; - } - - /** - * Returns the exported names - * @param {ModuleGraph} moduleGraph module graph - * @returns {ExportsSpec | undefined} export names - */ - getExports(moduleGraph) { - return { - exports: this.exports, - canMangle: this.canMangle, - dependencies: undefined - }; - } - - serialize(context) { - const { write } = context; - write(this.exports); - write(this.canMangle); - super.serialize(context); - } + apply( + dependency, + source, + { runtimeTemplate, module, moduleGraph, chunkGraph, runtimeRequirements } + ) { + const dep = /** @type {ImportDependency} */ (dependency); + const block = /** @type {AsyncDependenciesBlock} */ ( + moduleGraph.getParentBlock(dep) + ); + const content = runtimeTemplate.moduleNamespacePromise({ + chunkGraph, + block: block, + module: moduleGraph.getModule(dep), + request: dep.request, + strict: module.buildMeta.strictHarmonyModule, + message: "import()", + runtimeRequirements + }); - deserialize(context) { - const { read } = context; - this.exports = read(); - this.canMangle = read(); - super.deserialize(context); + source.replace(dep.range[0], dep.range[1] - 1, content); } -} - -makeSerializable( - StaticExportsDependency, - "webpack/lib/dependencies/StaticExportsDependency" -); +}; -module.exports = StaticExportsDependency; +module.exports = ImportDependency; /***/ }), -/***/ 88768: +/***/ 91941: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; /* MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ - - - -const RuntimeGlobals = __webpack_require__(49404); -const WebpackError = __webpack_require__(68422); -const { - evaluateToString, - expressionIsUnsupported, - toConstantDependency -} = __webpack_require__(28723); -const makeSerializable = __webpack_require__(26522); -const ConstDependency = __webpack_require__(60864); -const SystemRuntimeModule = __webpack_require__(45964); - -/** @typedef {import("../Compiler")} Compiler */ - -class SystemPlugin { - /** - * Apply the plugin - * @param {Compiler} compiler the compiler instance - * @returns {void} - */ - apply(compiler) { - compiler.hooks.compilation.tap( - "SystemPlugin", - (compilation, { normalModuleFactory }) => { - compilation.hooks.runtimeRequirementInModule - .for(RuntimeGlobals.system) - .tap("SystemPlugin", (module, set) => { - set.add(RuntimeGlobals.requireScope); - }); - - compilation.hooks.runtimeRequirementInTree - .for(RuntimeGlobals.system) - .tap("SystemPlugin", (chunk, set) => { - compilation.addRuntimeModule(chunk, new SystemRuntimeModule()); - }); - - const handler = (parser, parserOptions) => { - if (parserOptions.system === undefined || !parserOptions.system) { - return; - } - - const setNotSupported = name => { - parser.hooks.evaluateTypeof - .for(name) - .tap("SystemPlugin", evaluateToString("undefined")); - parser.hooks.expression - .for(name) - .tap( - "SystemPlugin", - expressionIsUnsupported( - parser, - name + " is not supported by webpack." - ) - ); - }; - - parser.hooks.typeof - .for("System.import") - .tap( - "SystemPlugin", - toConstantDependency(parser, JSON.stringify("function")) - ); - parser.hooks.evaluateTypeof - .for("System.import") - .tap("SystemPlugin", evaluateToString("function")); - parser.hooks.typeof - .for("System") - .tap( - "SystemPlugin", - toConstantDependency(parser, JSON.stringify("object")) - ); - parser.hooks.evaluateTypeof - .for("System") - .tap("SystemPlugin", evaluateToString("object")); + Author Tobias Koppers @sokra +*/ - setNotSupported("System.set"); - setNotSupported("System.get"); - setNotSupported("System.register"); - parser.hooks.expression.for("System").tap("SystemPlugin", expr => { - const dep = new ConstDependency(RuntimeGlobals.system, expr.range, [ - RuntimeGlobals.system - ]); - dep.loc = expr.loc; - parser.state.module.addPresentationalDependency(dep); - return true; - }); - parser.hooks.call.for("System.import").tap("SystemPlugin", expr => { - parser.state.module.addWarning( - new SystemImportDeprecationWarning(expr.loc) - ); +const makeSerializable = __webpack_require__(26522); +const ImportDependency = __webpack_require__(16727); - return parser.hooks.importCall.call({ - type: "ImportExpression", - source: expr.arguments[0], - loc: expr.loc, - range: expr.range - }); - }); - }; +/** @typedef {import("webpack-sources").ReplaceSource} ReplaceSource */ +/** @typedef {import("../Dependency")} Dependency */ +/** @typedef {import("../Dependency").ReferencedExport} ReferencedExport */ +/** @typedef {import("../DependencyTemplate").DependencyTemplateContext} DependencyTemplateContext */ +/** @typedef {import("../ModuleGraph")} ModuleGraph */ - normalModuleFactory.hooks.parser - .for("javascript/auto") - .tap("SystemPlugin", handler); - normalModuleFactory.hooks.parser - .for("javascript/dynamic") - .tap("SystemPlugin", handler); - } - ); +class ImportEagerDependency extends ImportDependency { + /** + * @param {string} request the request + * @param {[number, number]} range expression range + * @param {string[][]=} referencedExports list of referenced exports + */ + constructor(request, range, referencedExports) { + super(request, range, referencedExports); } -} - -class SystemImportDeprecationWarning extends WebpackError { - constructor(loc) { - super( - "System.import() is deprecated and will be removed soon. Use import() instead.\n" + - "For more info visit https://webpack.js.org/guides/code-splitting/" - ); - this.name = "SystemImportDeprecationWarning"; + get type() { + return "import() eager"; + } - this.loc = loc; + get category() { + return "esm"; } } makeSerializable( - SystemImportDeprecationWarning, - "webpack/lib/dependencies/SystemPlugin", - "SystemImportDeprecationWarning" + ImportEagerDependency, + "webpack/lib/dependencies/ImportEagerDependency" ); -module.exports = SystemPlugin; -module.exports.SystemImportDeprecationWarning = SystemImportDeprecationWarning; +ImportEagerDependency.Template = class ImportEagerDependencyTemplate extends ( + ImportDependency.Template +) { + /** + * @param {Dependency} dependency the dependency for which the template should be applied + * @param {ReplaceSource} source the current replace source which can be modified + * @param {DependencyTemplateContext} templateContext the context object + * @returns {void} + */ + apply( + dependency, + source, + { runtimeTemplate, module, moduleGraph, chunkGraph, runtimeRequirements } + ) { + const dep = /** @type {ImportEagerDependency} */ (dependency); + const content = runtimeTemplate.moduleNamespacePromise({ + chunkGraph, + module: moduleGraph.getModule(dep), + request: dep.request, + strict: module.buildMeta.strictHarmonyModule, + message: "import() eager", + runtimeRequirements + }); + + source.replace(dep.range[0], dep.range[1] - 1, content); + } +}; + +module.exports = ImportEagerDependency; /***/ }), -/***/ 45964: +/***/ 58287: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; /* MIT License http://www.opensource.org/licenses/mit-license.php - Author Florent Cailhol @ooflorent + Author Ivan Kopeykin @vankop */ -const RuntimeGlobals = __webpack_require__(49404); -const RuntimeModule = __webpack_require__(61439); -const Template = __webpack_require__(92066); +const makeSerializable = __webpack_require__(26522); +const ModuleDependency = __webpack_require__(80944); +const ModuleDependencyTemplateAsId = __webpack_require__(35795); -class SystemRuntimeModule extends RuntimeModule { - constructor() { - super("system"); +class ImportMetaHotAcceptDependency extends ModuleDependency { + constructor(request, range) { + super(request); + this.range = range; + this.weak = true; } - /** - * @returns {string} runtime code - */ - generate() { - return Template.asString([ - `${RuntimeGlobals.system} = {`, - Template.indent([ - "import: function () {", - Template.indent( - "throw new Error('System.import cannot be used indirectly');" - ), - "}" - ]), - "};" - ]); + get type() { + return "import.meta.webpackHot.accept"; + } + + get category() { + return "esm"; } } -module.exports = SystemRuntimeModule; +makeSerializable( + ImportMetaHotAcceptDependency, + "webpack/lib/dependencies/ImportMetaHotAcceptDependency" +); + +ImportMetaHotAcceptDependency.Template = ModuleDependencyTemplateAsId; + +module.exports = ImportMetaHotAcceptDependency; /***/ }), -/***/ 30990: +/***/ 89911: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; @@ -85552,167 +83859,40 @@ module.exports = SystemRuntimeModule; -const RuntimeGlobals = __webpack_require__(49404); -const { - getDependencyUsedByExportsCondition -} = __webpack_require__(92886); const makeSerializable = __webpack_require__(26522); -const memoize = __webpack_require__(84297); const ModuleDependency = __webpack_require__(80944); +const ModuleDependencyTemplateAsId = __webpack_require__(35795); -/** @typedef {import("webpack-sources").ReplaceSource} ReplaceSource */ -/** @typedef {import("../ChunkGraph")} ChunkGraph */ -/** @typedef {import("../Dependency")} Dependency */ -/** @typedef {import("../Dependency").UpdateHashContext} UpdateHashContext */ -/** @typedef {import("../DependencyTemplate").DependencyTemplateContext} DependencyTemplateContext */ -/** @typedef {import("../Module")} Module */ -/** @typedef {import("../ModuleGraph")} ModuleGraph */ -/** @typedef {import("../ModuleGraphConnection")} ModuleGraphConnection */ -/** @typedef {import("../ModuleGraphConnection").ConnectionState} ConnectionState */ -/** @typedef {import("../util/Hash")} Hash */ -/** @typedef {import("../util/runtime").RuntimeSpec} RuntimeSpec */ - -const getRawModule = memoize(() => __webpack_require__(82329)); - -class URLDependency extends ModuleDependency { - /** - * @param {string} request request - * @param {[number, number]} range range of the arguments of new URL( |> ... <| ) - * @param {[number, number]} outerRange range of the full |> new URL(...) <| - * @param {boolean=} relative use relative urls instead of absolute with base uri - */ - constructor(request, range, outerRange, relative) { +class ImportMetaHotDeclineDependency extends ModuleDependency { + constructor(request, range) { super(request); + this.range = range; - this.outerRange = outerRange; - this.relative = relative || false; - /** @type {Set | boolean} */ - this.usedByExports = undefined; + this.weak = true; } get type() { - return "new URL()"; + return "import.meta.webpackHot.decline"; } get category() { - return "url"; - } - - /** - * @param {ModuleGraph} moduleGraph module graph - * @returns {null | false | function(ModuleGraphConnection, RuntimeSpec): ConnectionState} function to determine if the connection is active - */ - getCondition(moduleGraph) { - return getDependencyUsedByExportsCondition( - this, - this.usedByExports, - moduleGraph - ); - } - - /** - * @param {string} context context directory - * @returns {Module} a module - */ - createIgnoredModule(context) { - const RawModule = getRawModule(); - return new RawModule( - 'module.exports = "data:,";', - `ignored-asset`, - `(ignored asset)`, - new Set([RuntimeGlobals.module]) - ); - } - - serialize(context) { - const { write } = context; - write(this.outerRange); - write(this.relative); - write(this.usedByExports); - super.serialize(context); - } - - deserialize(context) { - const { read } = context; - this.outerRange = read(); - this.relative = read(); - this.usedByExports = read(); - super.deserialize(context); + return "esm"; } } -URLDependency.Template = class URLDependencyTemplate extends ( - ModuleDependency.Template -) { - /** - * @param {Dependency} dependency the dependency for which the template should be applied - * @param {ReplaceSource} source the current replace source which can be modified - * @param {DependencyTemplateContext} templateContext the context object - * @returns {void} - */ - apply(dependency, source, templateContext) { - const { - chunkGraph, - moduleGraph, - runtimeRequirements, - runtimeTemplate, - runtime - } = templateContext; - const dep = /** @type {URLDependency} */ (dependency); - const connection = moduleGraph.getConnection(dep); - // Skip rendering depending when dependency is conditional - if (connection && !connection.isTargetActive(runtime)) { - source.replace( - dep.outerRange[0], - dep.outerRange[1] - 1, - "/* unused asset import */ undefined" - ); - return; - } - - runtimeRequirements.add(RuntimeGlobals.require); - - if (dep.relative) { - runtimeRequirements.add(RuntimeGlobals.relativeUrl); - source.replace( - dep.outerRange[0], - dep.outerRange[1] - 1, - `/* asset import */ new ${ - RuntimeGlobals.relativeUrl - }(${runtimeTemplate.moduleRaw({ - chunkGraph, - module: moduleGraph.getModule(dep), - request: dep.request, - runtimeRequirements, - weak: false - })})` - ); - } else { - runtimeRequirements.add(RuntimeGlobals.baseURI); - - source.replace( - dep.range[0], - dep.range[1] - 1, - `/* asset import */ ${runtimeTemplate.moduleRaw({ - chunkGraph, - module: moduleGraph.getModule(dep), - request: dep.request, - runtimeRequirements, - weak: false - })}, ${RuntimeGlobals.baseURI}` - ); - } - } -}; +makeSerializable( + ImportMetaHotDeclineDependency, + "webpack/lib/dependencies/ImportMetaHotDeclineDependency" +); -makeSerializable(URLDependency, "webpack/lib/dependencies/URLDependency"); +ImportMetaHotDeclineDependency.Template = ModuleDependencyTemplateAsId; -module.exports = URLDependency; +module.exports = ImportMetaHotDeclineDependency; /***/ }), -/***/ 97950: +/***/ 81841: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; @@ -85723,195 +83903,188 @@ module.exports = URLDependency; -const { approve } = __webpack_require__(28723); -const InnerGraph = __webpack_require__(92886); -const URLDependency = __webpack_require__(30990); +const { pathToFileURL } = __webpack_require__(78835); +const ModuleDependencyWarning = __webpack_require__(61528); +const Template = __webpack_require__(92066); +const BasicEvaluatedExpression = __webpack_require__(2412); +const { + evaluateToIdentifier, + toConstantDependency, + evaluateToString, + evaluateToNumber +} = __webpack_require__(28723); +const memoize = __webpack_require__(84297); +const propertyAccess = __webpack_require__(86709); +const ConstDependency = __webpack_require__(60864); -/** @typedef {import("estree").NewExpression} NewExpressionNode */ +/** @typedef {import("estree").MemberExpression} MemberExpression */ /** @typedef {import("../Compiler")} Compiler */ -/** @typedef {import("../javascript/JavascriptParser")} JavascriptParser */ +/** @typedef {import("../NormalModule")} NormalModule */ +/** @typedef {import("../javascript/JavascriptParser")} Parser */ -class URLPlugin { +const getCriticalDependencyWarning = memoize(() => + __webpack_require__(14190) +); + +class ImportMetaPlugin { /** * @param {Compiler} compiler compiler */ apply(compiler) { compiler.hooks.compilation.tap( - "URLPlugin", + "ImportMetaPlugin", (compilation, { normalModuleFactory }) => { - compilation.dependencyFactories.set(URLDependency, normalModuleFactory); - compilation.dependencyTemplates.set( - URLDependency, - new URLDependency.Template() - ); - /** - * @param {JavascriptParser} parser parser - * @param {object} parserOptions options + * @param {NormalModule} module module + * @returns {string} file url */ - const parserCallback = (parser, parserOptions) => { - if (parserOptions.url === false) return; - const relative = parserOptions.url === "relative"; - - /** - * @param {NewExpressionNode} expr expression - * @returns {undefined | string} request - */ - const getUrlRequest = expr => { - if (expr.arguments.length !== 2) return; - - const [arg1, arg2] = expr.arguments; - - if ( - arg2.type !== "MemberExpression" || - arg1.type === "SpreadElement" - ) - return; - - const chain = parser.extractMemberExpressionChain(arg2); - - if ( - chain.members.length !== 1 || - chain.object.type !== "MetaProperty" || - chain.object.meta.name !== "import" || - chain.object.property.name !== "meta" || - chain.members[0] !== "url" - ) - return; - - const request = parser.evaluateExpression(arg1).asString(); - - return request; - }; - - parser.hooks.canRename.for("URL").tap("URLPlugin", approve); - parser.hooks.new.for("URL").tap("URLPlugin", _expr => { - const expr = /** @type {NewExpressionNode} */ (_expr); - - const request = getUrlRequest(expr); - - if (!request) return; + const getUrl = module => { + return pathToFileURL(module.resource).toString(); + }; + /** + * @param {Parser} parser parser + * @param {Object} parserOptions parserOptions + * @returns {void} + */ + const parserHandler = (parser, parserOptions) => { + /// import.meta direct /// + parser.hooks.typeof + .for("import.meta") + .tap( + "ImportMetaPlugin", + toConstantDependency(parser, JSON.stringify("object")) + ); + parser.hooks.expression + .for("import.meta") + .tap("ImportMetaPlugin", metaProperty => { + const CriticalDependencyWarning = getCriticalDependencyWarning(); + parser.state.module.addWarning( + new ModuleDependencyWarning( + parser.state.module, + new CriticalDependencyWarning( + "Accessing import.meta directly is unsupported (only property access is supported)" + ), + metaProperty.loc + ) + ); + const dep = new ConstDependency( + `${parser.isAsiPosition(metaProperty.range[0]) ? ";" : ""}({})`, + metaProperty.range + ); + dep.loc = metaProperty.loc; + parser.state.module.addPresentationalDependency(dep); + return true; + }); + parser.hooks.evaluateTypeof + .for("import.meta") + .tap("ImportMetaPlugin", evaluateToString("object")); + parser.hooks.evaluateIdentifier.for("import.meta").tap( + "ImportMetaPlugin", + evaluateToIdentifier("import.meta", "import.meta", () => [], true) + ); - const [arg1, arg2] = expr.arguments; - const dep = new URLDependency( - request, - [arg1.range[0], arg2.range[1]], - expr.range, - relative + /// import.meta.url /// + parser.hooks.typeof + .for("import.meta.url") + .tap( + "ImportMetaPlugin", + toConstantDependency(parser, JSON.stringify("string")) ); - dep.loc = expr.loc; - parser.state.current.addDependency(dep); - InnerGraph.onUsage(parser.state, e => (dep.usedByExports = e)); - return true; - }); - parser.hooks.isPure.for("NewExpression").tap("URLPlugin", _expr => { - const expr = /** @type {NewExpressionNode} */ (_expr); - const { callee } = expr; - if (callee.type !== "Identifier") return; - const calleeInfo = parser.getFreeInfoFromVariable(callee.name); - if (!calleeInfo || calleeInfo.name !== "URL") return; + parser.hooks.expression + .for("import.meta.url") + .tap("ImportMetaPlugin", expr => { + const dep = new ConstDependency( + JSON.stringify(getUrl(parser.state.module)), + expr.range + ); + dep.loc = expr.loc; + parser.state.module.addPresentationalDependency(dep); + return true; + }); + parser.hooks.evaluateTypeof + .for("import.meta.url") + .tap("ImportMetaPlugin", evaluateToString("string")); + parser.hooks.evaluateIdentifier + .for("import.meta.url") + .tap("ImportMetaPlugin", expr => { + return new BasicEvaluatedExpression() + .setString(getUrl(parser.state.module)) + .setRange(expr.range); + }); - const request = getUrlRequest(expr); + /// import.meta.webpack /// + const webpackVersion = parseInt( + __webpack_require__(87168)/* .version */ .i8, + 10 + ); + parser.hooks.typeof + .for("import.meta.webpack") + .tap( + "ImportMetaPlugin", + toConstantDependency(parser, JSON.stringify("number")) + ); + parser.hooks.expression + .for("import.meta.webpack") + .tap( + "ImportMetaPlugin", + toConstantDependency(parser, JSON.stringify(webpackVersion)) + ); + parser.hooks.evaluateTypeof + .for("import.meta.webpack") + .tap("ImportMetaPlugin", evaluateToString("number")); + parser.hooks.evaluateIdentifier + .for("import.meta.webpack") + .tap("ImportMetaPlugin", evaluateToNumber(webpackVersion)); - if (request) return true; - }); + /// Unknown properties /// + parser.hooks.unhandledExpressionMemberChain + .for("import.meta") + .tap("ImportMetaPlugin", (expr, members) => { + const dep = new ConstDependency( + `${Template.toNormalComment( + "unsupported import.meta." + members.join(".") + )} undefined${propertyAccess(members, 1)}`, + expr.range + ); + dep.loc = expr.loc; + parser.state.module.addPresentationalDependency(dep); + return true; + }); + parser.hooks.evaluate + .for("MemberExpression") + .tap("ImportMetaPlugin", expression => { + const expr = /** @type {MemberExpression} */ (expression); + if ( + expr.object.type === "MetaProperty" && + expr.object.meta.name === "import" && + expr.object.property.name === "meta" && + expr.property.type === + (expr.computed ? "Literal" : "Identifier") + ) { + return new BasicEvaluatedExpression() + .setUndefined() + .setRange(expr.range); + } + }); }; normalModuleFactory.hooks.parser .for("javascript/auto") - .tap("URLPlugin", parserCallback); - + .tap("ImportMetaPlugin", parserHandler); normalModuleFactory.hooks.parser .for("javascript/esm") - .tap("URLPlugin", parserCallback); + .tap("ImportMetaPlugin", parserHandler); } ); } } -module.exports = URLPlugin; - - -/***/ }), - -/***/ 41381: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ - - - -const makeSerializable = __webpack_require__(26522); -const NullDependency = __webpack_require__(65845); - -/** @typedef {import("webpack-sources").ReplaceSource} ReplaceSource */ -/** @typedef {import("../Dependency")} Dependency */ -/** @typedef {import("../DependencyTemplate").DependencyTemplateContext} DependencyTemplateContext */ - -class UnsupportedDependency extends NullDependency { - constructor(request, range) { - super(); - - this.request = request; - this.range = range; - } - - serialize(context) { - const { write } = context; - - write(this.request); - write(this.range); - - super.serialize(context); - } - - deserialize(context) { - const { read } = context; - - this.request = read(); - this.range = read(); - - super.deserialize(context); - } -} - -makeSerializable( - UnsupportedDependency, - "webpack/lib/dependencies/UnsupportedDependency" -); - -UnsupportedDependency.Template = class UnsupportedDependencyTemplate extends ( - NullDependency.Template -) { - /** - * @param {Dependency} dependency the dependency for which the template should be applied - * @param {ReplaceSource} source the current replace source which can be modified - * @param {DependencyTemplateContext} templateContext the context object - * @returns {void} - */ - apply(dependency, source, { runtimeTemplate }) { - const dep = /** @type {UnsupportedDependency} */ (dependency); - - source.replace( - dep.range[0], - dep.range[1], - runtimeTemplate.missingModule({ - request: dep.request - }) - ); - } -}; - -module.exports = UnsupportedDependency; +module.exports = ImportMetaPlugin; /***/ }), -/***/ 18248: +/***/ 44136: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; @@ -85922,83 +84095,271 @@ module.exports = UnsupportedDependency; -const Dependency = __webpack_require__(50384); -const makeSerializable = __webpack_require__(26522); -const ModuleDependency = __webpack_require__(80944); - -/** @typedef {import("../Dependency").ReferencedExport} ReferencedExport */ -/** @typedef {import("../Dependency").TRANSITIVE} TRANSITIVE */ -/** @typedef {import("../ModuleGraph")} ModuleGraph */ -/** @typedef {import("../util/runtime").RuntimeSpec} RuntimeSpec */ - -class WebAssemblyExportImportedDependency extends ModuleDependency { - constructor(exportName, request, name, valueType) { - super(request); - /** @type {string} */ - this.exportName = exportName; - /** @type {string} */ - this.name = name; - /** @type {string} */ - this.valueType = valueType; - } +const AsyncDependenciesBlock = __webpack_require__(11315); +const CommentCompilationWarning = __webpack_require__(28151); +const UnsupportedFeatureWarning = __webpack_require__(9532); +const ContextDependencyHelpers = __webpack_require__(7114); +const ImportContextDependency = __webpack_require__(75785); +const ImportDependency = __webpack_require__(16727); +const ImportEagerDependency = __webpack_require__(91941); +const ImportWeakDependency = __webpack_require__(58426); - /** - * @returns {boolean | TRANSITIVE} true, when changes to the referenced module could affect the referencing module; TRANSITIVE, when changes to the referenced module could affect referencing modules of the referencing module - */ - couldAffectReferencingModule() { - return Dependency.TRANSITIVE; - } +/** @typedef {import("../ChunkGroup").RawChunkGroupOptions} RawChunkGroupOptions */ +/** @typedef {import("../ContextModule").ContextMode} ContextMode */ - /** - * Returns list of exports referenced by this dependency - * @param {ModuleGraph} moduleGraph module graph - * @param {RuntimeSpec} runtime the runtime for which the module is analysed - * @returns {(string[] | ReferencedExport)[]} referenced exports - */ - getReferencedExports(moduleGraph, runtime) { - return [[this.name]]; +class ImportParserPlugin { + constructor(options) { + this.options = options; } - get type() { - return "wasm export import"; - } + apply(parser) { + parser.hooks.importCall.tap("ImportParserPlugin", expr => { + const param = parser.evaluateExpression(expr.source); - get category() { - return "wasm"; - } + let chunkName = null; + /** @type {ContextMode} */ + let mode = "lazy"; + let include = null; + let exclude = null; + /** @type {string[][] | null} */ + let exports = null; + /** @type {RawChunkGroupOptions} */ + const groupOptions = {}; - serialize(context) { - const { write } = context; + const { options: importOptions, errors: commentErrors } = + parser.parseCommentOptions(expr.range); - write(this.exportName); - write(this.name); - write(this.valueType); + if (commentErrors) { + for (const e of commentErrors) { + const { comment } = e; + parser.state.module.addWarning( + new CommentCompilationWarning( + `Compilation error while processing magic comment(-s): /*${comment.value}*/: ${e.message}`, + comment.loc + ) + ); + } + } - super.serialize(context); - } + if (importOptions) { + if (importOptions.webpackIgnore !== undefined) { + if (typeof importOptions.webpackIgnore !== "boolean") { + parser.state.module.addWarning( + new UnsupportedFeatureWarning( + `\`webpackIgnore\` expected a boolean, but received: ${importOptions.webpackIgnore}.`, + expr.loc + ) + ); + } else { + // Do not instrument `import()` if `webpackIgnore` is `true` + if (importOptions.webpackIgnore) { + return false; + } + } + } + if (importOptions.webpackChunkName !== undefined) { + if (typeof importOptions.webpackChunkName !== "string") { + parser.state.module.addWarning( + new UnsupportedFeatureWarning( + `\`webpackChunkName\` expected a string, but received: ${importOptions.webpackChunkName}.`, + expr.loc + ) + ); + } else { + chunkName = importOptions.webpackChunkName; + } + } + if (importOptions.webpackMode !== undefined) { + if (typeof importOptions.webpackMode !== "string") { + parser.state.module.addWarning( + new UnsupportedFeatureWarning( + `\`webpackMode\` expected a string, but received: ${importOptions.webpackMode}.`, + expr.loc + ) + ); + } else { + mode = importOptions.webpackMode; + } + } + if (importOptions.webpackPrefetch !== undefined) { + if (importOptions.webpackPrefetch === true) { + groupOptions.prefetchOrder = 0; + } else if (typeof importOptions.webpackPrefetch === "number") { + groupOptions.prefetchOrder = importOptions.webpackPrefetch; + } else { + parser.state.module.addWarning( + new UnsupportedFeatureWarning( + `\`webpackPrefetch\` expected true or a number, but received: ${importOptions.webpackPrefetch}.`, + expr.loc + ) + ); + } + } + if (importOptions.webpackPreload !== undefined) { + if (importOptions.webpackPreload === true) { + groupOptions.preloadOrder = 0; + } else if (typeof importOptions.webpackPreload === "number") { + groupOptions.preloadOrder = importOptions.webpackPreload; + } else { + parser.state.module.addWarning( + new UnsupportedFeatureWarning( + `\`webpackPreload\` expected true or a number, but received: ${importOptions.webpackPreload}.`, + expr.loc + ) + ); + } + } + if (importOptions.webpackInclude !== undefined) { + if ( + !importOptions.webpackInclude || + importOptions.webpackInclude.constructor.name !== "RegExp" + ) { + parser.state.module.addWarning( + new UnsupportedFeatureWarning( + `\`webpackInclude\` expected a regular expression, but received: ${importOptions.webpackInclude}.`, + expr.loc + ) + ); + } else { + include = new RegExp(importOptions.webpackInclude); + } + } + if (importOptions.webpackExclude !== undefined) { + if ( + !importOptions.webpackExclude || + importOptions.webpackExclude.constructor.name !== "RegExp" + ) { + parser.state.module.addWarning( + new UnsupportedFeatureWarning( + `\`webpackExclude\` expected a regular expression, but received: ${importOptions.webpackExclude}.`, + expr.loc + ) + ); + } else { + exclude = new RegExp(importOptions.webpackExclude); + } + } + if (importOptions.webpackExports !== undefined) { + if ( + !( + typeof importOptions.webpackExports === "string" || + (Array.isArray(importOptions.webpackExports) && + importOptions.webpackExports.every( + item => typeof item === "string" + )) + ) + ) { + parser.state.module.addWarning( + new UnsupportedFeatureWarning( + `\`webpackExports\` expected a string or an array of strings, but received: ${importOptions.webpackExports}.`, + expr.loc + ) + ); + } else { + if (typeof importOptions.webpackExports === "string") { + exports = [[importOptions.webpackExports]]; + } else { + exports = Array.from(importOptions.webpackExports, e => [e]); + } + } + } + } - deserialize(context) { - const { read } = context; + if (param.isString()) { + if (mode !== "lazy" && mode !== "eager" && mode !== "weak") { + parser.state.module.addWarning( + new UnsupportedFeatureWarning( + `\`webpackMode\` expected 'lazy', 'eager' or 'weak', but received: ${mode}.`, + expr.loc + ) + ); + } - this.exportName = read(); - this.name = read(); - this.valueType = read(); + if (mode === "eager") { + const dep = new ImportEagerDependency( + param.string, + expr.range, + exports + ); + parser.state.current.addDependency(dep); + } else if (mode === "weak") { + const dep = new ImportWeakDependency( + param.string, + expr.range, + exports + ); + parser.state.current.addDependency(dep); + } else { + const depBlock = new AsyncDependenciesBlock( + { + ...groupOptions, + name: chunkName + }, + expr.loc, + param.string + ); + const dep = new ImportDependency(param.string, expr.range, exports); + dep.loc = expr.loc; + depBlock.addDependency(dep); + parser.state.current.addBlock(depBlock); + } + return true; + } else { + if ( + mode !== "lazy" && + mode !== "lazy-once" && + mode !== "eager" && + mode !== "weak" + ) { + parser.state.module.addWarning( + new UnsupportedFeatureWarning( + `\`webpackMode\` expected 'lazy', 'lazy-once', 'eager' or 'weak', but received: ${mode}.`, + expr.loc + ) + ); + mode = "lazy"; + } - super.deserialize(context); + if (mode === "weak") { + mode = "async-weak"; + } + const dep = ContextDependencyHelpers.create( + ImportContextDependency, + expr.range, + param, + expr, + this.options, + { + chunkName, + groupOptions, + include, + exclude, + mode, + namespaceObject: parser.state.module.buildMeta.strictHarmonyModule + ? "strict" + : true, + typePrefix: "import()", + category: "esm", + referencedExports: exports + }, + parser + ); + if (!dep) return; + dep.loc = expr.loc; + dep.optional = !!parser.scope.inTry; + parser.state.current.addDependency(dep); + return true; + } + }); } } -makeSerializable( - WebAssemblyExportImportedDependency, - "webpack/lib/dependencies/WebAssemblyExportImportedDependency" -); - -module.exports = WebAssemblyExportImportedDependency; +module.exports = ImportParserPlugin; /***/ }), -/***/ 97093: +/***/ 77199: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; @@ -86009,157 +84370,128 @@ module.exports = WebAssemblyExportImportedDependency; -const makeSerializable = __webpack_require__(26522); -const UnsupportedWebAssemblyFeatureError = __webpack_require__(13475); -const ModuleDependency = __webpack_require__(80944); - -/** @typedef {import("@webassemblyjs/ast").ModuleImportDescription} ModuleImportDescription */ -/** @typedef {import("../Dependency").ReferencedExport} ReferencedExport */ -/** @typedef {import("../ModuleGraph")} ModuleGraph */ -/** @typedef {import("../WebpackError")} WebpackError */ -/** @typedef {import("../util/runtime").RuntimeSpec} RuntimeSpec */ - -class WebAssemblyImportDependency extends ModuleDependency { - /** - * @param {string} request the request - * @param {string} name the imported name - * @param {ModuleImportDescription} description the WASM ast node - * @param {false | string} onlyDirectImport if only direct imports are allowed - */ - constructor(request, name, description, onlyDirectImport) { - super(request); - /** @type {string} */ - this.name = name; - /** @type {ModuleImportDescription} */ - this.description = description; - /** @type {false | string} */ - this.onlyDirectImport = onlyDirectImport; - } - - get type() { - return "wasm import"; - } - - get category() { - return "wasm"; - } +const ImportContextDependency = __webpack_require__(75785); +const ImportDependency = __webpack_require__(16727); +const ImportEagerDependency = __webpack_require__(91941); +const ImportParserPlugin = __webpack_require__(44136); +const ImportWeakDependency = __webpack_require__(58426); - /** - * Returns list of exports referenced by this dependency - * @param {ModuleGraph} moduleGraph module graph - * @param {RuntimeSpec} runtime the runtime for which the module is analysed - * @returns {(string[] | ReferencedExport)[]} referenced exports - */ - getReferencedExports(moduleGraph, runtime) { - return [[this.name]]; - } +/** @typedef {import("../Compiler")} Compiler */ +class ImportPlugin { /** - * Returns errors - * @param {ModuleGraph} moduleGraph module graph - * @returns {WebpackError[]} errors + * Apply the plugin + * @param {Compiler} compiler the compiler instance + * @returns {void} */ - getErrors(moduleGraph) { - const module = moduleGraph.getModule(this); - - if ( - this.onlyDirectImport && - module && - !module.type.startsWith("webassembly") - ) { - return [ - new UnsupportedWebAssemblyFeatureError( - `Import "${this.name}" from "${this.request}" with ${this.onlyDirectImport} can only be used for direct wasm to wasm dependencies` - ) - ]; - } - } + apply(compiler) { + compiler.hooks.compilation.tap( + "ImportPlugin", + (compilation, { contextModuleFactory, normalModuleFactory }) => { + compilation.dependencyFactories.set( + ImportDependency, + normalModuleFactory + ); + compilation.dependencyTemplates.set( + ImportDependency, + new ImportDependency.Template() + ); - serialize(context) { - const { write } = context; + compilation.dependencyFactories.set( + ImportEagerDependency, + normalModuleFactory + ); + compilation.dependencyTemplates.set( + ImportEagerDependency, + new ImportEagerDependency.Template() + ); - write(this.name); - write(this.description); - write(this.onlyDirectImport); + compilation.dependencyFactories.set( + ImportWeakDependency, + normalModuleFactory + ); + compilation.dependencyTemplates.set( + ImportWeakDependency, + new ImportWeakDependency.Template() + ); - super.serialize(context); - } + compilation.dependencyFactories.set( + ImportContextDependency, + contextModuleFactory + ); + compilation.dependencyTemplates.set( + ImportContextDependency, + new ImportContextDependency.Template() + ); - deserialize(context) { - const { read } = context; + const handler = (parser, parserOptions) => { + if (parserOptions.import !== undefined && !parserOptions.import) + return; - this.name = read(); - this.description = read(); - this.onlyDirectImport = read(); + new ImportParserPlugin(parserOptions).apply(parser); + }; - super.deserialize(context); + normalModuleFactory.hooks.parser + .for("javascript/auto") + .tap("ImportPlugin", handler); + normalModuleFactory.hooks.parser + .for("javascript/dynamic") + .tap("ImportPlugin", handler); + normalModuleFactory.hooks.parser + .for("javascript/esm") + .tap("ImportPlugin", handler); + } + ); } } - -makeSerializable( - WebAssemblyImportDependency, - "webpack/lib/dependencies/WebAssemblyImportDependency" -); - -module.exports = WebAssemblyImportDependency; +module.exports = ImportPlugin; /***/ }), -/***/ 41744: +/***/ 58426: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; /* MIT License http://www.opensource.org/licenses/mit-license.php - Author Ivan Kopeykin @vankop + Author Tobias Koppers @sokra */ -const Dependency = __webpack_require__(50384); -const Template = __webpack_require__(92066); const makeSerializable = __webpack_require__(26522); -const ModuleDependency = __webpack_require__(80944); +const ImportDependency = __webpack_require__(16727); /** @typedef {import("webpack-sources").ReplaceSource} ReplaceSource */ -/** @typedef {import("../Compilation")} Compilation */ +/** @typedef {import("../Dependency")} Dependency */ /** @typedef {import("../Dependency").ReferencedExport} ReferencedExport */ /** @typedef {import("../DependencyTemplate").DependencyTemplateContext} DependencyTemplateContext */ /** @typedef {import("../ModuleGraph")} ModuleGraph */ -/** @typedef {import("../util/runtime").RuntimeSpec} RuntimeSpec */ - -class WebpackIsIncludedDependency extends ModuleDependency { - constructor(request, range) { - super(request); - - this.weak = true; - this.range = range; - } +class ImportWeakDependency extends ImportDependency { /** - * Returns list of exports referenced by this dependency - * @param {ModuleGraph} moduleGraph module graph - * @param {RuntimeSpec} runtime the runtime for which the module is analysed - * @returns {(string[] | ReferencedExport)[]} referenced exports + * @param {string} request the request + * @param {[number, number]} range expression range + * @param {string[][]=} referencedExports list of referenced exports */ - getReferencedExports(moduleGraph, runtime) { - // This doesn't use any export - return Dependency.NO_EXPORTS_REFERENCED; + constructor(request, range, referencedExports) { + super(request, range, referencedExports); + this.weak = true; } get type() { - return "__webpack_is_included__"; + return "import() weak"; } } makeSerializable( - WebpackIsIncludedDependency, - "webpack/lib/dependencies/WebpackIsIncludedDependency" + ImportWeakDependency, + "webpack/lib/dependencies/ImportWeakDependency" ); -WebpackIsIncludedDependency.Template = class WebpackIsIncludedDependencyTemplate extends ( - ModuleDependency.Template +ImportWeakDependency.Template = class ImportDependencyTemplate extends ( + ImportDependency.Template ) { /** * @param {Dependency} dependency the dependency for which the template should be applied @@ -86167,556 +84499,179 @@ WebpackIsIncludedDependency.Template = class WebpackIsIncludedDependencyTemplate * @param {DependencyTemplateContext} templateContext the context object * @returns {void} */ - apply(dependency, source, { runtimeTemplate, chunkGraph, moduleGraph }) { - const dep = /** @type {WebpackIsIncludedDependency} */ (dependency); - const connection = moduleGraph.getConnection(dep); - const included = connection - ? chunkGraph.getNumberOfModuleChunks(connection.module) > 0 - : false; - const comment = runtimeTemplate.outputOptions.pathinfo - ? Template.toComment( - `__webpack_is_included__ ${runtimeTemplate.requestShortener.shorten( - dep.request - )}` - ) - : ""; + apply( + dependency, + source, + { runtimeTemplate, module, moduleGraph, chunkGraph, runtimeRequirements } + ) { + const dep = /** @type {ImportWeakDependency} */ (dependency); + const content = runtimeTemplate.moduleNamespacePromise({ + chunkGraph, + module: moduleGraph.getModule(dep), + request: dep.request, + strict: module.buildMeta.strictHarmonyModule, + message: "import() weak", + weak: true, + runtimeRequirements + }); - source.replace( - dep.range[0], - dep.range[1] - 1, - `${comment}${JSON.stringify(included)}` - ); + source.replace(dep.range[0], dep.range[1] - 1, content); } }; -module.exports = WebpackIsIncludedDependency; +module.exports = ImportWeakDependency; /***/ }), -/***/ 73016: +/***/ 36986: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; /* MIT License http://www.opensource.org/licenses/mit-license.php - Author Ivan Kopeykin @vankop + Author Tobias Koppers @sokra */ -const Dependency = __webpack_require__(50384); -const RuntimeGlobals = __webpack_require__(49404); const makeSerializable = __webpack_require__(26522); -const ModuleDependency = __webpack_require__(80944); +const NullDependency = __webpack_require__(65845); -/** @typedef {import("webpack-sources").ReplaceSource} ReplaceSource */ -/** @typedef {import("../AsyncDependenciesBlock")} AsyncDependenciesBlock */ /** @typedef {import("../ChunkGraph")} ChunkGraph */ -/** @typedef {import("../Dependency").ReferencedExport} ReferencedExport */ +/** @typedef {import("../Dependency").ExportSpec} ExportSpec */ +/** @typedef {import("../Dependency").ExportsSpec} ExportsSpec */ /** @typedef {import("../Dependency").UpdateHashContext} UpdateHashContext */ -/** @typedef {import("../DependencyTemplate").DependencyTemplateContext} DependencyTemplateContext */ -/** @typedef {import("../Entrypoint")} Entrypoint */ /** @typedef {import("../ModuleGraph")} ModuleGraph */ /** @typedef {import("../util/Hash")} Hash */ -/** @typedef {import("../util/runtime").RuntimeSpec} RuntimeSpec */ -class WorkerDependency extends ModuleDependency { - /** - * @param {string} request request - * @param {[number, number]} range range - */ - constructor(request, range) { - super(request); - this.range = range; +const getExportsFromData = data => { + if (data && typeof data === "object") { + if (Array.isArray(data)) { + return data.map((item, idx) => { + return { + name: `${idx}`, + canMangle: true, + exports: getExportsFromData(item) + }; + }); + } else { + const exports = []; + for (const key of Object.keys(data)) { + exports.push({ + name: key, + canMangle: true, + exports: getExportsFromData(data[key]) + }); + } + return exports; + } } + return undefined; +}; +class JsonExportsDependency extends NullDependency { /** - * Returns list of exports referenced by this dependency - * @param {ModuleGraph} moduleGraph module graph - * @param {RuntimeSpec} runtime the runtime for which the module is analysed - * @returns {(string[] | ReferencedExport)[]} referenced exports + * @param {(string | ExportSpec)[]} exports json exports */ - getReferencedExports(moduleGraph, runtime) { - return Dependency.NO_EXPORTS_REFERENCED; + constructor(exports) { + super(); + this.exports = exports; + this._hashUpdate = undefined; } get type() { - return "new Worker()"; - } - - get category() { - return "worker"; + return "json exports"; } -} -WorkerDependency.Template = class WorkerDependencyTemplate extends ( - ModuleDependency.Template -) { /** - * @param {Dependency} dependency the dependency for which the template should be applied - * @param {ReplaceSource} source the current replace source which can be modified - * @param {DependencyTemplateContext} templateContext the context object - * @returns {void} + * Returns the exported names + * @param {ModuleGraph} moduleGraph module graph + * @returns {ExportsSpec | undefined} export names */ - apply(dependency, source, templateContext) { - const { chunkGraph, moduleGraph, runtimeRequirements } = templateContext; - const dep = /** @type {WorkerDependency} */ (dependency); - const block = /** @type {AsyncDependenciesBlock} */ ( - moduleGraph.getParentBlock(dependency) - ); - const entrypoint = /** @type {Entrypoint} */ ( - chunkGraph.getBlockChunkGroup(block) - ); - const chunk = entrypoint.getEntrypointChunk(); - - runtimeRequirements.add(RuntimeGlobals.publicPath); - runtimeRequirements.add(RuntimeGlobals.baseURI); - runtimeRequirements.add(RuntimeGlobals.getChunkScriptFilename); - - source.replace( - dep.range[0], - dep.range[1] - 1, - `/* worker import */ ${RuntimeGlobals.publicPath} + ${ - RuntimeGlobals.getChunkScriptFilename - }(${JSON.stringify(chunk.id)}), ${RuntimeGlobals.baseURI}` - ); + getExports(moduleGraph) { + return { + exports: this.exports, + dependencies: undefined + }; } -}; - -makeSerializable(WorkerDependency, "webpack/lib/dependencies/WorkerDependency"); - -module.exports = WorkerDependency; - - -/***/ }), - -/***/ 93493: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ - - - -const { pathToFileURL } = __webpack_require__(78835); -const AsyncDependenciesBlock = __webpack_require__(11315); -const CommentCompilationWarning = __webpack_require__(28151); -const UnsupportedFeatureWarning = __webpack_require__(9532); -const EnableChunkLoadingPlugin = __webpack_require__(34726); -const { equals } = __webpack_require__(21537); -const createHash = __webpack_require__(24123); -const { contextify } = __webpack_require__(96236); -const EnableWasmLoadingPlugin = __webpack_require__(93943); -const ConstDependency = __webpack_require__(60864); -const CreateScriptUrlDependency = __webpack_require__(29829); -const { - harmonySpecifierTag -} = __webpack_require__(76581); -const WorkerDependency = __webpack_require__(73016); - -/** @typedef {import("estree").Expression} Expression */ -/** @typedef {import("estree").ObjectExpression} ObjectExpression */ -/** @typedef {import("estree").Pattern} Pattern */ -/** @typedef {import("estree").Property} Property */ -/** @typedef {import("estree").SpreadElement} SpreadElement */ -/** @typedef {import("../Compiler")} Compiler */ -/** @typedef {import("../Entrypoint").EntryOptions} EntryOptions */ -/** @typedef {import("../Parser").ParserState} ParserState */ -/** @typedef {import("../javascript/BasicEvaluatedExpression")} BasicEvaluatedExpression */ -/** @typedef {import("../javascript/JavascriptParser")} JavascriptParser */ -/** @typedef {import("./HarmonyImportDependencyParserPlugin").HarmonySettings} HarmonySettings */ - -const getUrl = module => { - return pathToFileURL(module.resource).toString(); -}; - -const DEFAULT_SYNTAX = [ - "Worker", - "SharedWorker", - "navigator.serviceWorker.register()", - "Worker from worker_threads" -]; - -/** @type {WeakMap} */ -const workerIndexMap = new WeakMap(); -class WorkerPlugin { - constructor(chunkLoading, wasmLoading, module) { - this._chunkLoading = chunkLoading; - this._wasmLoading = wasmLoading; - this._module = module; - } /** - * Apply the plugin - * @param {Compiler} compiler the compiler instance + * Update the hash + * @param {Hash} hash hash to be updated + * @param {UpdateHashContext} context context * @returns {void} */ - apply(compiler) { - if (this._chunkLoading) { - new EnableChunkLoadingPlugin(this._chunkLoading).apply(compiler); - } - if (this._wasmLoading) { - new EnableWasmLoadingPlugin(this._wasmLoading).apply(compiler); + updateHash(hash, context) { + if (this._hashUpdate === undefined) { + this._hashUpdate = this.exports + ? JSON.stringify(this.exports) + : "undefined"; } - const cachedContextify = contextify.bindContextCache( - compiler.context, - compiler.root - ); - compiler.hooks.thisCompilation.tap( - "WorkerPlugin", - (compilation, { normalModuleFactory }) => { - compilation.dependencyFactories.set( - WorkerDependency, - normalModuleFactory - ); - compilation.dependencyTemplates.set( - WorkerDependency, - new WorkerDependency.Template() - ); - compilation.dependencyTemplates.set( - CreateScriptUrlDependency, - new CreateScriptUrlDependency.Template() - ); - - /** - * @param {JavascriptParser} parser the parser - * @param {Expression} expr expression - * @returns {[BasicEvaluatedExpression, [number, number]]} parsed - */ - const parseModuleUrl = (parser, expr) => { - if ( - expr.type !== "NewExpression" || - expr.callee.type === "Super" || - expr.arguments.length !== 2 - ) - return; - const [arg1, arg2] = expr.arguments; - if (arg1.type === "SpreadElement") return; - if (arg2.type === "SpreadElement") return; - const callee = parser.evaluateExpression(expr.callee); - if (!callee.isIdentifier() || callee.identifier !== "URL") return; - const arg2Value = parser.evaluateExpression(arg2); - if ( - !arg2Value.isString() || - !arg2Value.string.startsWith("file://") || - arg2Value.string !== getUrl(parser.state.module) - ) { - return; - } - const arg1Value = parser.evaluateExpression(arg1); - return [arg1Value, [arg1.range[0], arg2.range[1]]]; - }; - - /** - * @param {JavascriptParser} parser the parser - * @param {ObjectExpression} expr expression - * @returns {{ expressions: Record, otherElements: (Property | SpreadElement)[], values: Record, spread: boolean, insertType: "comma" | "single", insertLocation: number }} parsed object - */ - const parseObjectExpression = (parser, expr) => { - /** @type {Record} */ - const values = {}; - /** @type {Record} */ - const expressions = {}; - /** @type {(Property | SpreadElement)[]} */ - const otherElements = []; - let spread = false; - for (const prop of expr.properties) { - if (prop.type === "SpreadElement") { - spread = true; - } else if ( - prop.type === "Property" && - !prop.method && - !prop.computed && - prop.key.type === "Identifier" - ) { - expressions[prop.key.name] = prop.value; - if (!prop.shorthand && !prop.value.type.endsWith("Pattern")) { - const value = parser.evaluateExpression( - /** @type {Expression} */ (prop.value) - ); - if (value.isCompileTimeValue()) - values[prop.key.name] = value.asCompileTimeValue(); - } - } else { - otherElements.push(prop); - } - } - const insertType = expr.properties.length > 0 ? "comma" : "single"; - const insertLocation = - expr.properties[expr.properties.length - 1].range[1]; - return { - expressions, - otherElements, - values, - spread, - insertType, - insertLocation - }; - }; - - /** - * @param {JavascriptParser} parser the parser - * @param {object} parserOptions options - */ - const parserPlugin = (parser, parserOptions) => { - if (parserOptions.worker === false) return; - const options = !Array.isArray(parserOptions.worker) - ? ["..."] - : parserOptions.worker; - const handleNewWorker = expr => { - if (expr.arguments.length === 0 || expr.arguments.length > 2) - return; - const [arg1, arg2] = expr.arguments; - if (arg1.type === "SpreadElement") return; - if (arg2 && arg2.type === "SpreadElement") return; - const parsedUrl = parseModuleUrl(parser, arg1); - if (!parsedUrl) return; - const [url, range] = parsedUrl; - if (!url.isString()) return; - const { - expressions, - otherElements, - values: options, - spread: hasSpreadInOptions, - insertType, - insertLocation - } = arg2 && arg2.type === "ObjectExpression" - ? parseObjectExpression(parser, arg2) - : { - expressions: {}, - otherElements: [], - values: {}, - spread: false, - insertType: arg2 ? "spread" : "argument", - insertLocation: arg2 ? arg2.range : arg1.range[1] - }; - const { options: importOptions, errors: commentErrors } = - parser.parseCommentOptions(expr.range); - - if (commentErrors) { - for (const e of commentErrors) { - const { comment } = e; - parser.state.module.addWarning( - new CommentCompilationWarning( - `Compilation error while processing magic comment(-s): /*${comment.value}*/: ${e.message}`, - comment.loc - ) - ); - } - } + hash.update(this._hashUpdate); + } - /** @type {EntryOptions} */ - let entryOptions = {}; + serialize(context) { + const { write } = context; + write(this.exports); + super.serialize(context); + } - if (importOptions) { - if (importOptions.webpackIgnore !== undefined) { - if (typeof importOptions.webpackIgnore !== "boolean") { - parser.state.module.addWarning( - new UnsupportedFeatureWarning( - `\`webpackIgnore\` expected a boolean, but received: ${importOptions.webpackIgnore}.`, - expr.loc - ) - ); - } else { - if (importOptions.webpackIgnore) { - return false; - } - } - } - if (importOptions.webpackEntryOptions !== undefined) { - if ( - typeof importOptions.webpackEntryOptions !== "object" || - importOptions.webpackEntryOptions === null - ) { - parser.state.module.addWarning( - new UnsupportedFeatureWarning( - `\`webpackEntryOptions\` expected a object, but received: ${importOptions.webpackEntryOptions}.`, - expr.loc - ) - ); - } else { - Object.assign( - entryOptions, - importOptions.webpackEntryOptions - ); - } - } - if (importOptions.webpackChunkName !== undefined) { - if (typeof importOptions.webpackChunkName !== "string") { - parser.state.module.addWarning( - new UnsupportedFeatureWarning( - `\`webpackChunkName\` expected a string, but received: ${importOptions.webpackChunkName}.`, - expr.loc - ) - ); - } else { - entryOptions.name = importOptions.webpackChunkName; - } - } - } + deserialize(context) { + const { read } = context; + this.exports = read(); + super.deserialize(context); + } +} - if ( - !Object.prototype.hasOwnProperty.call(entryOptions, "name") && - options && - typeof options.name === "string" - ) { - entryOptions.name = options.name; - } +makeSerializable( + JsonExportsDependency, + "webpack/lib/dependencies/JsonExportsDependency" +); - if (entryOptions.runtime === undefined) { - let i = workerIndexMap.get(parser.state) || 0; - workerIndexMap.set(parser.state, i + 1); - let name = `${cachedContextify( - parser.state.module.identifier() - )}|${i}`; - const hash = createHash(compilation.outputOptions.hashFunction); - hash.update(name); - const digest = /** @type {string} */ ( - hash.digest(compilation.outputOptions.hashDigest) - ); - entryOptions.runtime = digest.slice( - 0, - compilation.outputOptions.hashDigestLength - ); - } +module.exports = JsonExportsDependency; +module.exports.getExportsFromData = getExportsFromData; - const block = new AsyncDependenciesBlock({ - name: entryOptions.name, - entryOptions: { - chunkLoading: this._chunkLoading, - wasmLoading: this._wasmLoading, - ...entryOptions - } - }); - block.loc = expr.loc; - const dep = new WorkerDependency(url.string, range); - dep.loc = expr.loc; - block.addDependency(dep); - parser.state.module.addBlock(block); - if (compilation.outputOptions.trustedTypes) { - const dep = new CreateScriptUrlDependency( - expr.arguments[0].range - ); - dep.loc = expr.loc; - parser.state.module.addDependency(dep); - } +/***/ }), - if (expressions.type) { - const expr = expressions.type; - if (options.type !== false) { - const dep = new ConstDependency( - this._module ? '"module"' : "undefined", - expr.range - ); - dep.loc = expr.loc; - parser.state.module.addPresentationalDependency(dep); - expressions.type = undefined; - } - } else if (insertType === "comma") { - if (this._module || hasSpreadInOptions) { - const dep = new ConstDependency( - `, type: ${this._module ? '"module"' : "undefined"}`, - insertLocation - ); - dep.loc = expr.loc; - parser.state.module.addPresentationalDependency(dep); - } - } else if (insertType === "spread") { - const dep1 = new ConstDependency( - "Object.assign({}, ", - insertLocation[0] - ); - const dep2 = new ConstDependency( - `, { type: ${this._module ? '"module"' : "undefined"} })`, - insertLocation[1] - ); - dep1.loc = expr.loc; - dep2.loc = expr.loc; - parser.state.module.addPresentationalDependency(dep1); - parser.state.module.addPresentationalDependency(dep2); - } else if (insertType === "argument") { - if (this._module) { - const dep = new ConstDependency( - ', { type: "module" }', - insertLocation - ); - dep.loc = expr.loc; - parser.state.module.addPresentationalDependency(dep); - } - } +/***/ 52067: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - parser.walkExpression(expr.callee); - for (const key of Object.keys(expressions)) { - if (expressions[key]) parser.walkExpression(expressions[key]); - } - for (const prop of otherElements) { - parser.walkProperty(prop); - } - if (insertType === "spread") { - parser.walkExpression(arg2); - } +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ - return true; - }; - const processItem = item => { - if (item.endsWith("()")) { - parser.hooks.call - .for(item.slice(0, -2)) - .tap("WorkerPlugin", handleNewWorker); - } else { - const match = /^(.+?)(\(\))?\s+from\s+(.+)$/.exec(item); - if (match) { - const ids = match[1].split("."); - const call = match[2]; - const source = match[3]; - (call ? parser.hooks.call : parser.hooks.new) - .for(harmonySpecifierTag) - .tap("WorkerPlugin", expr => { - const settings = /** @type {HarmonySettings} */ ( - parser.currentTagData - ); - if ( - !settings || - settings.source !== source || - !equals(settings.ids, ids) - ) { - return; - } - return handleNewWorker(expr); - }); - } else { - parser.hooks.new.for(item).tap("WorkerPlugin", handleNewWorker); - } - } - }; - for (const item of options) { - if (item === "...") { - DEFAULT_SYNTAX.forEach(processItem); - } else processItem(item); - } - }; - normalModuleFactory.hooks.parser - .for("javascript/auto") - .tap("WorkerPlugin", parserPlugin); - normalModuleFactory.hooks.parser - .for("javascript/esm") - .tap("WorkerPlugin", parserPlugin); - } - ); + + +const ModuleDependency = __webpack_require__(80944); + +class LoaderDependency extends ModuleDependency { + /** + * @param {string} request request string + */ + constructor(request) { + super(request); + } + + get type() { + return "loader"; + } + + get category() { + return "loader"; } } -module.exports = WorkerPlugin; + +module.exports = LoaderDependency; /***/ }), -/***/ 70108: -/***/ (function(module) { +/***/ 33824: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; /* @@ -86726,59 +84681,32 @@ module.exports = WorkerPlugin; -module.exports = expr => { - // - if ( - expr.type === "FunctionExpression" || - expr.type === "ArrowFunctionExpression" - ) { - return { - fn: expr, - expressions: [], - needThis: false - }; +const ModuleDependency = __webpack_require__(80944); + +class LoaderImportDependency extends ModuleDependency { + /** + * @param {string} request request string + */ + constructor(request) { + super(request); + this.weak = true; } - // .bind() - if ( - expr.type === "CallExpression" && - expr.callee.type === "MemberExpression" && - expr.callee.object.type === "FunctionExpression" && - expr.callee.property.type === "Identifier" && - expr.callee.property.name === "bind" && - expr.arguments.length === 1 - ) { - return { - fn: expr.callee.object, - expressions: [expr.arguments[0]], - needThis: undefined - }; + get type() { + return "loader import"; } - // (function(_this) {return })(this) (Coffeescript) - if ( - expr.type === "CallExpression" && - expr.callee.type === "FunctionExpression" && - expr.callee.body.type === "BlockStatement" && - expr.arguments.length === 1 && - expr.arguments[0].type === "ThisExpression" && - expr.callee.body.body && - expr.callee.body.body.length === 1 && - expr.callee.body.body[0].type === "ReturnStatement" && - expr.callee.body.body[0].argument && - expr.callee.body.body[0].argument.type === "FunctionExpression" - ) { - return { - fn: expr.callee.body.body[0].argument, - expressions: [], - needThis: true - }; + + get category() { + return "loaderImport"; } -}; +} + +module.exports = LoaderImportDependency; /***/ }), -/***/ 35873: +/***/ 34204: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; @@ -86789,69 +84717,263 @@ module.exports = expr => { -const { UsageState } = __webpack_require__(4295); +const NormalModule = __webpack_require__(11026); +const LazySet = __webpack_require__(59534); +const LoaderDependency = __webpack_require__(52067); +const LoaderImportDependency = __webpack_require__(33824); -/** @typedef {import("../ExportsInfo").ExportInfo} ExportInfo */ -/** @typedef {import("../util/runtime").RuntimeSpec} RuntimeSpec */ +/** @typedef {import("../Compilation").DepConstructor} DepConstructor */ +/** @typedef {import("../Compiler")} Compiler */ +/** @typedef {import("../Module")} Module */ /** - * @param {RuntimeSpec} runtime the runtime - * @param {string[][]} referencedExports list of referenced exports, will be added to - * @param {string[]} prefix export prefix - * @param {ExportInfo=} exportInfo the export info - * @param {boolean} defaultPointsToSelf when true, using default will reference itself - * @param {Set} alreadyVisited already visited export info (to handle circular reexports) + * @callback LoadModuleCallback + * @param {Error=} err error object + * @param {string | Buffer=} source source code + * @param {object=} map source map + * @param {Module=} module loaded module if successful */ -const processExportInfo = ( - runtime, - referencedExports, - prefix, - exportInfo, - defaultPointsToSelf = false, - alreadyVisited = new Set() -) => { - if (!exportInfo) { - referencedExports.push(prefix); - return; - } - const used = exportInfo.getUsed(runtime); - if (used === UsageState.Unused) return; - if (alreadyVisited.has(exportInfo)) { - referencedExports.push(prefix); - return; - } - alreadyVisited.add(exportInfo); - if ( - used !== UsageState.OnlyPropertiesUsed || - !exportInfo.exportsInfo || - exportInfo.exportsInfo.otherExportsInfo.getUsed(runtime) !== - UsageState.Unused - ) { - alreadyVisited.delete(exportInfo); - referencedExports.push(prefix); - return; - } - const exportsInfo = exportInfo.exportsInfo; - for (const exportInfo of exportsInfo.orderedExports) { - processExportInfo( - runtime, - referencedExports, - defaultPointsToSelf && exportInfo.name === "default" - ? prefix - : prefix.concat(exportInfo.name), - exportInfo, - false, - alreadyVisited + +/** + * @callback ImportModuleCallback + * @param {Error=} err error object + * @param {any=} exports exports of the evaluated module + */ + +/** + * @typedef {Object} ImportModuleOptions + * @property {string=} layer the target layer + * @property {string=} publicPath the target public path + */ + +class LoaderPlugin { + /** + * @param {Object} options options + */ + constructor(options = {}) {} + + /** + * Apply the plugin + * @param {Compiler} compiler the compiler instance + * @returns {void} + */ + apply(compiler) { + compiler.hooks.compilation.tap( + "LoaderPlugin", + (compilation, { normalModuleFactory }) => { + compilation.dependencyFactories.set( + LoaderDependency, + normalModuleFactory + ); + compilation.dependencyFactories.set( + LoaderImportDependency, + normalModuleFactory + ); + } ); + + compiler.hooks.compilation.tap("LoaderPlugin", compilation => { + const moduleGraph = compilation.moduleGraph; + NormalModule.getCompilationHooks(compilation).loader.tap( + "LoaderPlugin", + loaderContext => { + /** + * @param {string} request the request string to load the module from + * @param {LoadModuleCallback} callback callback returning the loaded module or error + * @returns {void} + */ + loaderContext.loadModule = (request, callback) => { + const dep = new LoaderDependency(request); + dep.loc = { + name: request + }; + const factory = compilation.dependencyFactories.get( + /** @type {DepConstructor} */ (dep.constructor) + ); + if (factory === undefined) { + return callback( + new Error( + `No module factory available for dependency type: ${dep.constructor.name}` + ) + ); + } + compilation.buildQueue.increaseParallelism(); + compilation.handleModuleCreation( + { + factory, + dependencies: [dep], + originModule: loaderContext._module, + context: loaderContext.context, + recursive: false + }, + err => { + compilation.buildQueue.decreaseParallelism(); + if (err) { + return callback(err); + } + const referencedModule = moduleGraph.getModule(dep); + if (!referencedModule) { + return callback(new Error("Cannot load the module")); + } + if (referencedModule.getNumberOfErrors() > 0) { + return callback( + new Error("The loaded module contains errors") + ); + } + const moduleSource = referencedModule.originalSource(); + if (!moduleSource) { + return callback( + new Error( + "The module created for a LoaderDependency must have an original source" + ) + ); + } + let source, map; + if (moduleSource.sourceAndMap) { + const sourceAndMap = moduleSource.sourceAndMap(); + map = sourceAndMap.map; + source = sourceAndMap.source; + } else { + map = moduleSource.map(); + source = moduleSource.source(); + } + const fileDependencies = new LazySet(); + const contextDependencies = new LazySet(); + const missingDependencies = new LazySet(); + const buildDependencies = new LazySet(); + referencedModule.addCacheDependencies( + fileDependencies, + contextDependencies, + missingDependencies, + buildDependencies + ); + + for (const d of fileDependencies) { + loaderContext.addDependency(d); + } + for (const d of contextDependencies) { + loaderContext.addContextDependency(d); + } + for (const d of missingDependencies) { + loaderContext.addMissingDependency(d); + } + for (const d of buildDependencies) { + loaderContext.addBuildDependency(d); + } + return callback(null, source, map, referencedModule); + } + ); + }; + + /** + * @param {string} request the request string to load the module from + * @param {ImportModuleOptions=} options options + * @param {ImportModuleCallback=} callback callback returning the exports + * @returns {void} + */ + const importModule = (request, options, callback) => { + const dep = new LoaderImportDependency(request); + dep.loc = { + name: request + }; + const factory = compilation.dependencyFactories.get( + /** @type {DepConstructor} */ (dep.constructor) + ); + if (factory === undefined) { + return callback( + new Error( + `No module factory available for dependency type: ${dep.constructor.name}` + ) + ); + } + compilation.buildQueue.increaseParallelism(); + compilation.handleModuleCreation( + { + factory, + dependencies: [dep], + originModule: loaderContext._module, + contextInfo: { + issuerLayer: options.layer + }, + context: loaderContext.context, + connectOrigin: false + }, + err => { + compilation.buildQueue.decreaseParallelism(); + if (err) { + return callback(err); + } + const referencedModule = moduleGraph.getModule(dep); + if (!referencedModule) { + return callback(new Error("Cannot load the module")); + } + compilation.executeModule( + referencedModule, + { + entryOptions: { + publicPath: options.publicPath + } + }, + (err, result) => { + if (err) return callback(err); + for (const d of result.fileDependencies) { + loaderContext.addDependency(d); + } + for (const d of result.contextDependencies) { + loaderContext.addContextDependency(d); + } + for (const d of result.missingDependencies) { + loaderContext.addMissingDependency(d); + } + for (const d of result.buildDependencies) { + loaderContext.addBuildDependency(d); + } + if (result.cacheable === false) + loaderContext.cacheable(false); + for (const [name, { source, info }] of result.assets) { + const { buildInfo } = loaderContext._module; + if (!buildInfo.assets) { + buildInfo.assets = Object.create(null); + buildInfo.assetsInfo = new Map(); + } + buildInfo.assets[name] = source; + buildInfo.assetsInfo.set(name, info); + } + callback(null, result.exports); + } + ); + } + ); + }; + + /** + * @param {string} request the request string to load the module from + * @param {ImportModuleOptions} options options + * @param {ImportModuleCallback=} callback callback returning the exports + * @returns {Promise | void} exports + */ + loaderContext.importModule = (request, options, callback) => { + if (!callback) { + return new Promise((resolve, reject) => { + importModule(request, options || {}, (err, result) => { + if (err) reject(err); + else resolve(result); + }); + }); + } + return importModule(request, options || {}, callback); + }; + } + ); + }); } - alreadyVisited.delete(exportInfo); -}; -module.exports = processExportInfo; +} +module.exports = LoaderPlugin; /***/ }), -/***/ 88362: +/***/ 930: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; @@ -86862,72 +84984,48 @@ module.exports = processExportInfo; -const ExternalsPlugin = __webpack_require__(361); +const makeSerializable = __webpack_require__(26522); -/** @typedef {import("../Compiler")} Compiler */ +class LocalModule { + constructor(name, idx) { + this.name = name; + this.idx = idx; + this.used = false; + } -class ElectronTargetPlugin { - /** - * @param {"main" | "preload" | "renderer"=} context in main, preload or renderer context? - */ - constructor(context) { - this._context = context; + flagUsed() { + this.used = true; } - /** - * Apply the plugin - * @param {Compiler} compiler the compiler instance - * @returns {void} - */ - apply(compiler) { - new ExternalsPlugin("node-commonjs", [ - "clipboard", - "crash-reporter", - "electron", - "ipc", - "native-image", - "original-fs", - "screen", - "shell" - ]).apply(compiler); - switch (this._context) { - case "main": - new ExternalsPlugin("node-commonjs", [ - "app", - "auto-updater", - "browser-window", - "content-tracing", - "dialog", - "global-shortcut", - "ipc-main", - "menu", - "menu-item", - "power-monitor", - "power-save-blocker", - "protocol", - "session", - "tray", - "web-contents" - ]).apply(compiler); - break; - case "preload": - case "renderer": - new ExternalsPlugin("node-commonjs", [ - "desktop-capturer", - "ipc-renderer", - "remote", - "web-frame" - ]).apply(compiler); - break; - } + + variableName() { + return "__WEBPACK_LOCAL_MODULE_" + this.idx + "__"; + } + + serialize(context) { + const { write } = context; + + write(this.name); + write(this.idx); + write(this.used); + } + + deserialize(context) { + const { read } = context; + + this.name = read(); + this.idx = read(); + this.used = read(); } } -module.exports = ElectronTargetPlugin; +makeSerializable(LocalModule, "webpack/lib/dependencies/LocalModule"); + +module.exports = LocalModule; /***/ }), -/***/ 1808: +/***/ 67494: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; @@ -86938,68 +85036,131 @@ module.exports = ElectronTargetPlugin; -const WebpackError = __webpack_require__(68422); +const makeSerializable = __webpack_require__(26522); +const NullDependency = __webpack_require__(65845); -/** @typedef {import("../Module")} Module */ +/** @typedef {import("webpack-sources").ReplaceSource} ReplaceSource */ +/** @typedef {import("../Dependency")} Dependency */ +/** @typedef {import("../DependencyTemplate").DependencyTemplateContext} DependencyTemplateContext */ -class BuildCycleError extends WebpackError { - /** - * Creates an instance of ModuleDependencyError. - * @param {Module} module the module starting the cycle - */ - constructor(module) { - super( - "There is a circular build dependency, which makes it impossible to create this module" - ); +class LocalModuleDependency extends NullDependency { + constructor(localModule, range, callNew) { + super(); - this.name = "BuildCycleError"; - this.module = module; + this.localModule = localModule; + this.range = range; + this.callNew = callNew; + } + + serialize(context) { + const { write } = context; + + write(this.localModule); + write(this.range); + write(this.callNew); + + super.serialize(context); + } + + deserialize(context) { + const { read } = context; + + this.localModule = read(); + this.range = read(); + this.callNew = read(); + + super.deserialize(context); } } -module.exports = BuildCycleError; +makeSerializable( + LocalModuleDependency, + "webpack/lib/dependencies/LocalModuleDependency" +); + +LocalModuleDependency.Template = class LocalModuleDependencyTemplate extends ( + NullDependency.Template +) { + /** + * @param {Dependency} dependency the dependency for which the template should be applied + * @param {ReplaceSource} source the current replace source which can be modified + * @param {DependencyTemplateContext} templateContext the context object + * @returns {void} + */ + apply(dependency, source, templateContext) { + const dep = /** @type {LocalModuleDependency} */ (dependency); + if (!dep.range) return; + const moduleInstance = dep.callNew + ? `new (function () { return ${dep.localModule.variableName()}; })()` + : dep.localModule.variableName(); + source.replace(dep.range[0], dep.range[1] - 1, moduleInstance); + } +}; + +module.exports = LocalModuleDependency; /***/ }), -/***/ 80744: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { +/***/ 6311: +/***/ (function(__unused_webpack_module, exports, __webpack_require__) { "use strict"; /* MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra */ -const RuntimeModule = __webpack_require__(61439); +const LocalModule = __webpack_require__(930); -class ExportWebpackRequireRuntimeModule extends RuntimeModule { - constructor() { - super("export webpack runtime", RuntimeModule.STAGE_ATTACH); - } +const lookup = (parent, mod) => { + if (mod.charAt(0) !== ".") return mod; - /** - * @returns {boolean} true, if the runtime module should get it's own scope - */ - shouldIsolate() { - return false; + var path = parent.split("/"); + var segments = mod.split("/"); + path.pop(); + + for (let i = 0; i < segments.length; i++) { + const seg = segments[i]; + if (seg === "..") { + path.pop(); + } else if (seg !== ".") { + path.push(seg); + } } - /** - * @returns {string} runtime code - */ - generate() { - return "export default __webpack_require__;"; + return path.join("/"); +}; + +exports.addLocalModule = (state, name) => { + if (!state.localModules) { + state.localModules = []; } -} + const m = new LocalModule(name, state.localModules.length); + state.localModules.push(m); + return m; +}; -module.exports = ExportWebpackRequireRuntimeModule; +exports.getLocalModule = (state, name, namedModule) => { + if (!state.localModules) return null; + if (namedModule) { + // resolve dependency name relative to the defining named module + name = lookup(namedModule, name); + } + for (let i = 0; i < state.localModules.length; i++) { + if (state.localModules[i].name === name) { + return state.localModules[i]; + } + } + return null; +}; /***/ }), -/***/ 29181: +/***/ 58969: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; @@ -87010,181 +85171,133 @@ module.exports = ExportWebpackRequireRuntimeModule; -const { ConcatSource, RawSource } = __webpack_require__(96192); -const { RuntimeGlobals } = __webpack_require__(48169); -const HotUpdateChunk = __webpack_require__(39222); -const Template = __webpack_require__(92066); -const { - getCompilationHooks, - getChunkFilenameTemplate -} = __webpack_require__(76767); -const { - generateEntryStartup, - updateHashForEntryStartup -} = __webpack_require__(30951); +const Dependency = __webpack_require__(50384); +const InitFragment = __webpack_require__(51739); +const RuntimeGlobals = __webpack_require__(49404); +const makeSerializable = __webpack_require__(26522); +const NullDependency = __webpack_require__(65845); -/** @typedef {import("../Compiler")} Compiler */ +/** @typedef {import("webpack-sources").ReplaceSource} ReplaceSource */ +/** @typedef {import("../ChunkGraph")} ChunkGraph */ +/** @typedef {import("../Dependency").ReferencedExport} ReferencedExport */ +/** @typedef {import("../Dependency").UpdateHashContext} UpdateHashContext */ +/** @typedef {import("../DependencyTemplate").DependencyTemplateContext} DependencyTemplateContext */ +/** @typedef {import("../DependencyTemplates")} DependencyTemplates */ +/** @typedef {import("../ModuleGraph")} ModuleGraph */ +/** @typedef {import("../util/Hash")} Hash */ +/** @typedef {import("../util/runtime").RuntimeSpec} RuntimeSpec */ -class ModuleChunkFormatPlugin { +class ModuleDecoratorDependency extends NullDependency { /** - * Apply the plugin - * @param {Compiler} compiler the compiler instance + * @param {string} decorator the decorator requirement + * @param {boolean} allowExportsAccess allow to access exports from module + */ + constructor(decorator, allowExportsAccess) { + super(); + this.decorator = decorator; + this.allowExportsAccess = allowExportsAccess; + this._hashUpdate = undefined; + } + + /** + * @returns {string} a display name for the type of dependency + */ + get type() { + return "module decorator"; + } + + get category() { + return "self"; + } + + /** + * @returns {string | null} an identifier to merge equal requests + */ + getResourceIdentifier() { + return `self`; + } + + /** + * Returns list of exports referenced by this dependency + * @param {ModuleGraph} moduleGraph module graph + * @param {RuntimeSpec} runtime the runtime for which the module is analysed + * @returns {(string[] | ReferencedExport)[]} referenced exports + */ + getReferencedExports(moduleGraph, runtime) { + return this.allowExportsAccess + ? Dependency.EXPORTS_OBJECT_REFERENCED + : Dependency.NO_EXPORTS_REFERENCED; + } + + /** + * Update the hash + * @param {Hash} hash hash to be updated + * @param {UpdateHashContext} context context * @returns {void} */ - apply(compiler) { - compiler.hooks.thisCompilation.tap( - "ModuleChunkFormatPlugin", - compilation => { - compilation.hooks.additionalChunkRuntimeRequirements.tap( - "ModuleChunkFormatPlugin", - (chunk, set) => { - if (chunk.hasRuntime()) return; - if (compilation.chunkGraph.getNumberOfEntryModules(chunk) > 0) { - set.add(RuntimeGlobals.require); - set.add(RuntimeGlobals.startupEntrypoint); - set.add(RuntimeGlobals.externalInstallChunk); - } - } - ); - const hooks = getCompilationHooks(compilation); - hooks.renderChunk.tap( - "ModuleChunkFormatPlugin", - (modules, renderContext) => { - const { chunk, chunkGraph, runtimeTemplate } = renderContext; - const hotUpdateChunk = - chunk instanceof HotUpdateChunk ? chunk : null; - const source = new ConcatSource(); - if (hotUpdateChunk) { - throw new Error( - "HMR is not implemented for module chunk format yet" - ); - } else { - source.add(`export const id = ${JSON.stringify(chunk.id)};\n`); - source.add(`export const ids = ${JSON.stringify(chunk.ids)};\n`); - source.add(`export const modules = `); - source.add(modules); - source.add(`;\n`); - const runtimeModules = - chunkGraph.getChunkRuntimeModulesInOrder(chunk); - if (runtimeModules.length > 0) { - source.add("export const runtime =\n"); - source.add( - Template.renderChunkRuntimeModules( - runtimeModules, - renderContext - ) - ); - } - const entries = Array.from( - chunkGraph.getChunkEntryModulesWithChunkGroupIterable(chunk) - ); - if (entries.length > 0) { - const runtimeChunk = entries[0][1].getRuntimeChunk(); - const currentOutputName = compilation - .getPath( - getChunkFilenameTemplate(chunk, compilation.outputOptions), - { - chunk, - contentHashType: "javascript" - } - ) - .split("/"); - const runtimeOutputName = compilation - .getPath( - getChunkFilenameTemplate( - runtimeChunk, - compilation.outputOptions - ), - { - chunk: runtimeChunk, - contentHashType: "javascript" - } - ) - .split("/"); + updateHash(hash, context) { + if (this._hashUpdate === undefined) { + this._hashUpdate = `${this.decorator}${this.allowExportsAccess}`; + } + hash.update(this._hashUpdate); + } - // remove filename, we only need the directory - const outputFilename = currentOutputName.pop(); + serialize(context) { + const { write } = context; + write(this.decorator); + write(this.allowExportsAccess); + super.serialize(context); + } - // remove common parts - while ( - currentOutputName.length > 0 && - runtimeOutputName.length > 0 && - currentOutputName[0] === runtimeOutputName[0] - ) { - currentOutputName.shift(); - runtimeOutputName.shift(); - } + deserialize(context) { + const { read } = context; + this.decorator = read(); + this.allowExportsAccess = read(); + super.deserialize(context); + } +} - // create final path - const runtimePath = - (currentOutputName.length > 0 - ? "../".repeat(currentOutputName.length) - : "./") + runtimeOutputName.join("/"); +makeSerializable( + ModuleDecoratorDependency, + "webpack/lib/dependencies/ModuleDecoratorDependency" +); - const entrySource = new ConcatSource(); - entrySource.add(source); - entrySource.add(";\n\n// load runtime\n"); - entrySource.add( - `import __webpack_require__ from ${JSON.stringify( - runtimePath - )};\n` - ); - entrySource.add( - `import * as __webpack_self_exports__ from ${JSON.stringify( - "./" + outputFilename - )};\n` - ); - entrySource.add( - `${RuntimeGlobals.externalInstallChunk}(__webpack_self_exports__);\n` - ); - const startupSource = new RawSource( - generateEntryStartup( - chunkGraph, - runtimeTemplate, - entries, - chunk, - false - ) - ); - entrySource.add( - hooks.renderStartup.call( - startupSource, - entries[entries.length - 1][0], - { - ...renderContext, - inlined: false - } - ) - ); - return entrySource; - } - } - return source; - } - ); - hooks.chunkHash.tap( - "ModuleChunkFormatPlugin", - (chunk, hash, { chunkGraph, runtimeTemplate }) => { - if (chunk.hasRuntime()) return; - hash.update("ModuleChunkFormatPlugin"); - hash.update("1"); - const entries = Array.from( - chunkGraph.getChunkEntryModulesWithChunkGroupIterable(chunk) - ); - updateHashForEntryStartup(hash, chunkGraph, entries, chunk); - } - ); - } +ModuleDecoratorDependency.Template = class ModuleDecoratorDependencyTemplate extends ( + NullDependency.Template +) { + /** + * @param {Dependency} dependency the dependency for which the template should be applied + * @param {ReplaceSource} source the current replace source which can be modified + * @param {DependencyTemplateContext} templateContext the context object + * @returns {void} + */ + apply( + dependency, + source, + { module, chunkGraph, initFragments, runtimeRequirements } + ) { + const dep = /** @type {ModuleDecoratorDependency} */ (dependency); + runtimeRequirements.add(RuntimeGlobals.moduleLoaded); + runtimeRequirements.add(RuntimeGlobals.moduleId); + runtimeRequirements.add(RuntimeGlobals.module); + runtimeRequirements.add(dep.decorator); + initFragments.push( + new InitFragment( + `/* module decorator */ ${module.moduleArgument} = ${dep.decorator}(${module.moduleArgument});\n`, + InitFragment.STAGE_PROVIDES, + 0, + `module decorator ${chunkGraph.getModuleId(module)}` + ) ); } -} +}; -module.exports = ModuleChunkFormatPlugin; +module.exports = ModuleDecoratorDependency; /***/ }), -/***/ 94970: +/***/ 80944: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; @@ -87195,315 +85308,217 @@ module.exports = ModuleChunkFormatPlugin; -const RuntimeGlobals = __webpack_require__(49404); -const ExportWebpackRequireRuntimeModule = __webpack_require__(80744); -const ModuleChunkLoadingRuntimeModule = __webpack_require__(53807); +const Dependency = __webpack_require__(50384); +const DependencyTemplate = __webpack_require__(17600); +const memoize = __webpack_require__(84297); -/** @typedef {import("../Compiler")} Compiler */ +/** @typedef {import("../Dependency").TRANSITIVE} TRANSITIVE */ +/** @typedef {import("../Module")} Module */ -class ModuleChunkLoadingPlugin { +const getRawModule = memoize(() => __webpack_require__(82329)); + +class ModuleDependency extends Dependency { /** - * Apply the plugin - * @param {Compiler} compiler the compiler instance - * @returns {void} + * @param {string} request request path which needs resolving */ - apply(compiler) { - compiler.hooks.thisCompilation.tap( - "ModuleChunkLoadingPlugin", - compilation => { - const globalChunkLoading = compilation.outputOptions.chunkLoading; - const isEnabledForChunk = chunk => { - const options = chunk.getEntryOptions(); - const chunkLoading = - (options && options.chunkLoading) || globalChunkLoading; - return chunkLoading === "import"; - }; - const onceForChunkSet = new WeakSet(); - const handler = (chunk, set) => { - if (onceForChunkSet.has(chunk)) return; - onceForChunkSet.add(chunk); - if (!isEnabledForChunk(chunk)) return; - set.add(RuntimeGlobals.moduleFactoriesAddOnly); - set.add(RuntimeGlobals.hasOwnProperty); - compilation.addRuntimeModule( - chunk, - new ModuleChunkLoadingRuntimeModule(set) - ); - }; - compilation.hooks.runtimeRequirementInTree - .for(RuntimeGlobals.ensureChunkHandlers) - .tap("ModuleChunkLoadingPlugin", handler); - compilation.hooks.runtimeRequirementInTree - .for(RuntimeGlobals.baseURI) - .tap("ModuleChunkLoadingPlugin", handler); - compilation.hooks.runtimeRequirementInTree - .for(RuntimeGlobals.externalInstallChunk) - .tap("ModuleChunkLoadingPlugin", handler); - compilation.hooks.runtimeRequirementInTree - .for(RuntimeGlobals.onChunksLoaded) - .tap("ModuleChunkLoadingPlugin", handler); - compilation.hooks.runtimeRequirementInTree - .for(RuntimeGlobals.externalInstallChunk) - .tap("ModuleChunkLoadingPlugin", (chunk, set) => { - if (!isEnabledForChunk(chunk)) return; - compilation.addRuntimeModule( - chunk, - new ExportWebpackRequireRuntimeModule() - ); - }); + constructor(request) { + super(); + this.request = request; + this.userRequest = request; + this.range = undefined; + // assertions must be serialized by subclasses that use it + /** @type {Record | undefined} */ + this.assertions = undefined; + } - compilation.hooks.runtimeRequirementInTree - .for(RuntimeGlobals.ensureChunkHandlers) - .tap("ModuleChunkLoadingPlugin", (chunk, set) => { - if (!isEnabledForChunk(chunk)) return; - set.add(RuntimeGlobals.getChunkScriptFilename); - }); - } + /** + * @returns {string | null} an identifier to merge equal requests + */ + getResourceIdentifier() { + let str = `module${this.request}`; + if (this.assertions !== undefined) { + str += JSON.stringify(this.assertions); + } + return str; + } + + /** + * @returns {boolean | TRANSITIVE} true, when changes to the referenced module could affect the referencing module; TRANSITIVE, when changes to the referenced module could affect referencing modules of the referencing module + */ + couldAffectReferencingModule() { + return true; + } + + /** + * @param {string} context context directory + * @returns {Module} a module + */ + createIgnoredModule(context) { + const RawModule = getRawModule(); + return new RawModule( + "/* (ignored) */", + `ignored|${context}|${this.request}`, + `${this.request} (ignored)` ); } + + serialize(context) { + const { write } = context; + write(this.request); + write(this.userRequest); + write(this.range); + super.serialize(context); + } + + deserialize(context) { + const { read } = context; + this.request = read(); + this.userRequest = read(); + this.range = read(); + super.deserialize(context); + } } -module.exports = ModuleChunkLoadingPlugin; +ModuleDependency.Template = DependencyTemplate; + +module.exports = ModuleDependency; /***/ }), -/***/ 53807: +/***/ 35795: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; /* MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra */ -const { SyncWaterfallHook } = __webpack_require__(34718); -const Compilation = __webpack_require__(59622); -const RuntimeGlobals = __webpack_require__(49404); -const RuntimeModule = __webpack_require__(61439); -const Template = __webpack_require__(92066); -const { - getChunkFilenameTemplate, - chunkHasJs -} = __webpack_require__(76767); -const { getInitialChunkIds } = __webpack_require__(30951); -const compileBooleanMatcher = __webpack_require__(356); -const { getUndoPath } = __webpack_require__(96236); - -/** @typedef {import("../Chunk")} Chunk */ - -/** - * @typedef {Object} JsonpCompilationPluginHooks - * @property {SyncWaterfallHook<[string, Chunk]>} linkPreload - * @property {SyncWaterfallHook<[string, Chunk]>} linkPrefetch - */ +const ModuleDependency = __webpack_require__(80944); -/** @type {WeakMap} */ -const compilationHooksMap = new WeakMap(); +/** @typedef {import("webpack-sources").ReplaceSource} ReplaceSource */ +/** @typedef {import("../Dependency")} Dependency */ +/** @typedef {import("../DependencyTemplate").DependencyTemplateContext} DependencyTemplateContext */ -class ModuleChunkLoadingRuntimeModule extends RuntimeModule { +class ModuleDependencyTemplateAsId extends ModuleDependency.Template { /** - * @param {Compilation} compilation the compilation - * @returns {JsonpCompilationPluginHooks} hooks + * @param {Dependency} dependency the dependency for which the template should be applied + * @param {ReplaceSource} source the current replace source which can be modified + * @param {DependencyTemplateContext} templateContext the context object + * @returns {void} */ - static getCompilationHooks(compilation) { - if (!(compilation instanceof Compilation)) { - throw new TypeError( - "The 'compilation' argument must be an instance of Compilation" - ); - } - let hooks = compilationHooksMap.get(compilation); - if (hooks === undefined) { - hooks = { - linkPreload: new SyncWaterfallHook(["source", "chunk"]), - linkPrefetch: new SyncWaterfallHook(["source", "chunk"]) - }; - compilationHooksMap.set(compilation, hooks); - } - return hooks; + apply(dependency, source, { runtimeTemplate, moduleGraph, chunkGraph }) { + const dep = /** @type {ModuleDependency} */ (dependency); + if (!dep.range) return; + const content = runtimeTemplate.moduleId({ + module: moduleGraph.getModule(dep), + chunkGraph, + request: dep.request, + weak: dep.weak + }); + source.replace(dep.range[0], dep.range[1] - 1, content); } +} - constructor(runtimeRequirements) { - super("import chunk loading", RuntimeModule.STAGE_ATTACH); - this._runtimeRequirements = runtimeRequirements; - } +module.exports = ModuleDependencyTemplateAsId; + + +/***/ }), + +/***/ 77802: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ + + + +const ModuleDependency = __webpack_require__(80944); + +/** @typedef {import("webpack-sources").ReplaceSource} ReplaceSource */ +/** @typedef {import("../Dependency")} Dependency */ +/** @typedef {import("../DependencyTemplate").DependencyTemplateContext} DependencyTemplateContext */ +class ModuleDependencyTemplateAsRequireId extends ModuleDependency.Template { /** - * @returns {string} runtime code + * @param {Dependency} dependency the dependency for which the template should be applied + * @param {ReplaceSource} source the current replace source which can be modified + * @param {DependencyTemplateContext} templateContext the context object + * @returns {void} */ - generate() { - const { compilation, chunk } = this; - const { - runtimeTemplate, + apply( + dependency, + source, + { runtimeTemplate, moduleGraph, chunkGraph, runtimeRequirements } + ) { + const dep = /** @type {ModuleDependency} */ (dependency); + if (!dep.range) return; + const content = runtimeTemplate.moduleExports({ + module: moduleGraph.getModule(dep), chunkGraph, - outputOptions: { importFunctionName, importMetaName } - } = compilation; - const fn = RuntimeGlobals.ensureChunkHandlers; - const withBaseURI = this._runtimeRequirements.has(RuntimeGlobals.baseURI); - const withExternalInstallChunk = this._runtimeRequirements.has( - RuntimeGlobals.externalInstallChunk - ); - const withLoading = this._runtimeRequirements.has( - RuntimeGlobals.ensureChunkHandlers - ); - const withOnChunkLoad = this._runtimeRequirements.has( - RuntimeGlobals.onChunksLoaded - ); - const withHmr = this._runtimeRequirements.has( - RuntimeGlobals.hmrDownloadUpdateHandlers - ); - const conditionMap = chunkGraph.getChunkConditionMap(chunk, chunkHasJs); - const hasJsMatcher = compileBooleanMatcher(conditionMap); - const initialChunkIds = getInitialChunkIds(chunk, chunkGraph); + request: dep.request, + weak: dep.weak, + runtimeRequirements + }); + source.replace(dep.range[0], dep.range[1] - 1, content); + } +} +module.exports = ModuleDependencyTemplateAsRequireId; - const outputName = this.compilation.getPath( - getChunkFilenameTemplate(chunk, this.compilation.outputOptions), - { - chunk, - contentHashType: "javascript" - } - ); - const rootOutputDir = getUndoPath( - outputName, - this.compilation.outputOptions.path, - true - ); - const stateExpression = withHmr - ? `${RuntimeGlobals.hmrRuntimeStatePrefix}_module` - : undefined; +/***/ }), - return Template.asString([ - withBaseURI - ? Template.asString([ - `${RuntimeGlobals.baseURI} = new URL(${JSON.stringify( - rootOutputDir - )}, ${importMetaName}.url);` - ]) - : "// no baseURI", - "", - "// object to store loaded and loading chunks", - "// undefined = chunk not loaded, null = chunk preloaded/prefetched", - "// [resolve, reject, Promise] = chunk loading, 0 = chunk loaded", - `var installedChunks = ${ - stateExpression ? `${stateExpression} = ${stateExpression} || ` : "" - }{`, - Template.indent( - Array.from(initialChunkIds, id => `${JSON.stringify(id)}: 0`).join( - ",\n" - ) - ), - "};", - "", - withLoading || withExternalInstallChunk - ? `var installChunk = ${runtimeTemplate.basicFunction("data", [ - runtimeTemplate.destructureObject( - ["ids", "modules", "runtime"], - "data" - ), - '// add "modules" to the modules object,', - '// then flag all "ids" as loaded and fire callback', - "var moduleId, chunkId, i = 0;", - "for(moduleId in modules) {", - Template.indent([ - `if(${RuntimeGlobals.hasOwnProperty}(modules, moduleId)) {`, - Template.indent( - `${RuntimeGlobals.moduleFactories}[moduleId] = modules[moduleId];` - ), - "}" - ]), - "}", - "if(runtime) runtime(__webpack_require__);", - "for(;i < ids.length; i++) {", - Template.indent([ - "chunkId = ids[i];", - `if(${RuntimeGlobals.hasOwnProperty}(installedChunks, chunkId) && installedChunks[chunkId]) {`, - Template.indent("installedChunks[chunkId][0]();"), - "}", - "installedChunks[ids[i]] = 0;" - ]), - "}", - withOnChunkLoad ? `${RuntimeGlobals.onChunksLoaded}();` : "" - ])}` - : "// no install chunk", - "", - withLoading - ? Template.asString([ - `${fn}.j = ${runtimeTemplate.basicFunction( - "chunkId, promises", - hasJsMatcher !== false - ? Template.indent([ - "// import() chunk loading for javascript", - `var installedChunkData = ${RuntimeGlobals.hasOwnProperty}(installedChunks, chunkId) ? installedChunks[chunkId] : undefined;`, - 'if(installedChunkData !== 0) { // 0 means "already installed".', - Template.indent([ - "", - '// a Promise means "currently loading".', - "if(installedChunkData) {", - Template.indent([ - "promises.push(installedChunkData[1]);" - ]), - "} else {", - Template.indent([ - hasJsMatcher === true - ? "if(true) { // all chunks have JS" - : `if(${hasJsMatcher("chunkId")}) {`, - Template.indent([ - "// setup Promise in chunk cache", - `var promise = ${importFunctionName}(${JSON.stringify( - rootOutputDir - )} + ${ - RuntimeGlobals.getChunkScriptFilename - }(chunkId)).then(installChunk, ${runtimeTemplate.basicFunction( - "e", - [ - "if(installedChunks[chunkId] !== 0) installedChunks[chunkId] = undefined;", - "throw e;" - ] - )});`, - `var promise = Promise.race([promise, new Promise(${runtimeTemplate.expressionFunction( - `installedChunkData = installedChunks[chunkId] = [resolve]`, - "resolve" - )})])`, - `promises.push(installedChunkData[1] = promise);` - ]), - "} else installedChunks[chunkId] = 0;" - ]), - "}" - ]), - "}" - ]) - : Template.indent(["installedChunks[chunkId] = 0;"]) - )};` - ]) - : "// no chunk on demand loading", - "", - withExternalInstallChunk - ? Template.asString([ - `${RuntimeGlobals.externalInstallChunk} = installChunk;` - ]) - : "// no external install chunk", - "", - withOnChunkLoad - ? `${ - RuntimeGlobals.onChunksLoaded - }.j = ${runtimeTemplate.returningFunction( - "installedChunks[chunkId] === 0", - "chunkId" - )};` - : "// no on chunks loaded" - ]); +/***/ 90200: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ + + + +const makeSerializable = __webpack_require__(26522); +const ModuleDependency = __webpack_require__(80944); +const ModuleDependencyTemplateAsId = __webpack_require__(35795); + +class ModuleHotAcceptDependency extends ModuleDependency { + constructor(request, range) { + super(request); + this.range = range; + this.weak = true; + } + + get type() { + return "module.hot.accept"; + } + + get category() { + return "commonjs"; } } -module.exports = ModuleChunkLoadingRuntimeModule; +makeSerializable( + ModuleHotAcceptDependency, + "webpack/lib/dependencies/ModuleHotAcceptDependency" +); + +ModuleHotAcceptDependency.Template = ModuleDependencyTemplateAsId; + +module.exports = ModuleHotAcceptDependency; /***/ }), -/***/ 57261: -/***/ (function(module) { +/***/ 72986: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; /* @@ -87513,72 +85528,40 @@ module.exports = ModuleChunkLoadingRuntimeModule; -/** @typedef {import("./Dependency").DependencyLocation} DependencyLocation */ -/** @typedef {import("./Dependency").SourcePosition} SourcePosition */ +const makeSerializable = __webpack_require__(26522); +const ModuleDependency = __webpack_require__(80944); +const ModuleDependencyTemplateAsId = __webpack_require__(35795); -/** - * @param {SourcePosition} pos position - * @returns {string} formatted position - */ -const formatPosition = pos => { - if (pos && typeof pos === "object") { - if ("line" in pos && "column" in pos) { - return `${pos.line}:${pos.column}`; - } else if ("line" in pos) { - return `${pos.line}:?`; - } +class ModuleHotDeclineDependency extends ModuleDependency { + constructor(request, range) { + super(request); + + this.range = range; + this.weak = true; } - return ""; -}; -/** - * @param {DependencyLocation} loc location - * @returns {string} formatted location - */ -const formatLocation = loc => { - if (loc && typeof loc === "object") { - if ("start" in loc && loc.start && "end" in loc && loc.end) { - if ( - typeof loc.start === "object" && - typeof loc.start.line === "number" && - typeof loc.end === "object" && - typeof loc.end.line === "number" && - typeof loc.end.column === "number" && - loc.start.line === loc.end.line - ) { - return `${formatPosition(loc.start)}-${loc.end.column}`; - } else if ( - typeof loc.start === "object" && - typeof loc.start.line === "number" && - typeof loc.start.column !== "number" && - typeof loc.end === "object" && - typeof loc.end.line === "number" && - typeof loc.end.column !== "number" - ) { - return `${loc.start.line}-${loc.end.line}`; - } else { - return `${formatPosition(loc.start)}-${formatPosition(loc.end)}`; - } - } - if ("start" in loc && loc.start) { - return formatPosition(loc.start); - } - if ("name" in loc && "index" in loc) { - return `${loc.name}[${loc.index}]`; - } - if ("name" in loc) { - return loc.name; - } + get type() { + return "module.hot.decline"; + } + + get category() { + return "commonjs"; } - return ""; -}; +} -module.exports = formatLocation; +makeSerializable( + ModuleHotDeclineDependency, + "webpack/lib/dependencies/ModuleHotDeclineDependency" +); + +ModuleHotDeclineDependency.Template = ModuleDependencyTemplateAsId; + +module.exports = ModuleHotDeclineDependency; /***/ }), -/***/ 21978: +/***/ 65845: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; @@ -87589,46 +85572,44 @@ module.exports = formatLocation; -const RuntimeGlobals = __webpack_require__(49404); -const RuntimeModule = __webpack_require__(61439); -const Template = __webpack_require__(92066); +const Dependency = __webpack_require__(50384); +const DependencyTemplate = __webpack_require__(17600); -class HotModuleReplacementRuntimeModule extends RuntimeModule { - constructor() { - super("hot module replacement", RuntimeModule.STAGE_BASIC); +/** @typedef {import("webpack-sources").ReplaceSource} ReplaceSource */ +/** @typedef {import("../Dependency").TRANSITIVE} TRANSITIVE */ +/** @typedef {import("../DependencyTemplate").DependencyTemplateContext} DependencyTemplateContext */ + +class NullDependency extends Dependency { + get type() { + return "null"; } + /** - * @returns {string} runtime code + * @returns {boolean | TRANSITIVE} true, when changes to the referenced module could affect the referencing module; TRANSITIVE, when changes to the referenced module could affect referencing modules of the referencing module */ - generate() { - return Template.getFunctionContent( - require('./HotModuleReplacement.runtime.js') - ) - .replace(/\$getFullHash\$/g, RuntimeGlobals.getFullHash) - .replace( - /\$interceptModuleExecution\$/g, - RuntimeGlobals.interceptModuleExecution - ) - .replace(/\$moduleCache\$/g, RuntimeGlobals.moduleCache) - .replace(/\$hmrModuleData\$/g, RuntimeGlobals.hmrModuleData) - .replace(/\$hmrDownloadManifest\$/g, RuntimeGlobals.hmrDownloadManifest) - .replace( - /\$hmrInvalidateModuleHandlers\$/g, - RuntimeGlobals.hmrInvalidateModuleHandlers - ) - .replace( - /\$hmrDownloadUpdateHandlers\$/g, - RuntimeGlobals.hmrDownloadUpdateHandlers - ); + couldAffectReferencingModule() { + return false; } } -module.exports = HotModuleReplacementRuntimeModule; +NullDependency.Template = class NullDependencyTemplate extends ( + DependencyTemplate +) { + /** + * @param {Dependency} dependency the dependency for which the template should be applied + * @param {ReplaceSource} source the current replace source which can be modified + * @param {DependencyTemplateContext} templateContext the context object + * @returns {void} + */ + apply(dependency, source, templateContext) {} +}; + +module.exports = NullDependency; /***/ }), -/***/ 70839: +/***/ 39986: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; @@ -87639,398 +85620,294 @@ module.exports = HotModuleReplacementRuntimeModule; -const { RawSource } = __webpack_require__(96192); -const AsyncDependenciesBlock = __webpack_require__(11315); -const Dependency = __webpack_require__(50384); -const Module = __webpack_require__(85887); -const ModuleFactory = __webpack_require__(61574); -const RuntimeGlobals = __webpack_require__(49404); -const Template = __webpack_require__(92066); -const CommonJsRequireDependency = __webpack_require__(38604); -const { registerNotSerializable } = __webpack_require__(99551); - -/** @typedef {import("../../declarations/WebpackOptions")} WebpackOptions */ -/** @typedef {import("../Compilation")} Compilation */ -/** @typedef {import("../Compiler")} Compiler */ -/** @typedef {import("../Dependency").UpdateHashContext} UpdateHashContext */ -/** @typedef {import("../Module").BuildMeta} BuildMeta */ -/** @typedef {import("../Module").CodeGenerationContext} CodeGenerationContext */ -/** @typedef {import("../Module").CodeGenerationResult} CodeGenerationResult */ -/** @typedef {import("../Module").LibIdentOptions} LibIdentOptions */ -/** @typedef {import("../Module").NeedBuildContext} NeedBuildContext */ -/** @typedef {import("../ModuleFactory").ModuleFactoryCreateData} ModuleFactoryCreateData */ -/** @typedef {import("../ModuleFactory").ModuleFactoryResult} ModuleFactoryResult */ -/** @typedef {import("../RequestShortener")} RequestShortener */ -/** @typedef {import("../ResolverFactory").ResolverWithOptions} ResolverWithOptions */ -/** @typedef {import("../WebpackError")} WebpackError */ -/** @typedef {import("../util/Hash")} Hash */ -/** @typedef {import("../util/fs").InputFileSystem} InputFileSystem */ - -/** - * @typedef {Object} BackendApi - * @property {function(Error=): void} dispose - * @property {function(Module): { client: string, data: string, active: boolean }} module - */ - -const IGNORED_DEPENDENCY_TYPES = new Set([ - "import.meta.webpackHot.accept", - "import.meta.webpackHot.decline", - "module.hot.accept", - "module.hot.decline" -]); +const ModuleDependency = __webpack_require__(80944); -/** - * @param {undefined|string|RegExp|Function} test test option - * @param {Module} module the module - * @returns {boolean} true, if the module should be selected - */ -const checkTest = (test, module) => { - if (test === undefined) return true; - if (typeof test === "function") { - return test(module); - } - if (typeof test === "string") { - const name = module.nameForCondition(); - return name && name.startsWith(test); - } - if (test instanceof RegExp) { - const name = module.nameForCondition(); - return name && test.test(name); +class PrefetchDependency extends ModuleDependency { + constructor(request) { + super(request); } - return false; -}; - -const TYPES = new Set(["javascript"]); -class LazyCompilationDependency extends Dependency { - constructor(proxyModule) { - super(); - this.proxyModule = proxyModule; + get type() { + return "prefetch"; } get category() { return "esm"; } +} - get type() { - return "lazy import()"; - } +module.exports = PrefetchDependency; - /** - * @returns {string | null} an identifier to merge equal requests - */ - getResourceIdentifier() { - return this.proxyModule.originalModule.identifier(); - } -} -registerNotSerializable(LazyCompilationDependency); +/***/ }), -class LazyCompilationProxyModule extends Module { - constructor(context, originalModule, request, client, data, active) { - super("lazy-compilation-proxy", context, originalModule.layer); - this.originalModule = originalModule; - this.request = request; - this.client = client; - this.data = data; - this.active = active; +/***/ 88915: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Florent Cailhol @ooflorent +*/ + + + +const InitFragment = __webpack_require__(51739); +const makeSerializable = __webpack_require__(26522); +const ModuleDependency = __webpack_require__(80944); + +/** @typedef {import("webpack-sources").ReplaceSource} ReplaceSource */ +/** @typedef {import("../ChunkGraph")} ChunkGraph */ +/** @typedef {import("../Dependency")} Dependency */ +/** @typedef {import("../Dependency").UpdateHashContext} UpdateHashContext */ +/** @typedef {import("../DependencyTemplate").DependencyTemplateContext} DependencyTemplateContext */ +/** @typedef {import("../DependencyTemplates")} DependencyTemplates */ +/** @typedef {import("../ModuleGraph")} ModuleGraph */ +/** @typedef {import("../RuntimeTemplate")} RuntimeTemplate */ +/** @typedef {import("../util/Hash")} Hash */ + +/** + * @param {string[]|null} path the property path array + * @returns {string} the converted path + */ +const pathToString = path => + path !== null && path.length > 0 + ? path.map(part => `[${JSON.stringify(part)}]`).join("") + : ""; + +class ProvidedDependency extends ModuleDependency { + constructor(request, identifier, path, range) { + super(request); + this.identifier = identifier; + this.path = path; + this.range = range; + this._hashUpdate = undefined; } - /** - * @returns {string} a unique identifier of the module - */ - identifier() { - return `lazy-compilation-proxy|${this.originalModule.identifier()}`; + get type() { + return "provided"; } - /** - * @param {RequestShortener} requestShortener the request shortener - * @returns {string} a user readable identifier of the module - */ - readableIdentifier(requestShortener) { - return `lazy-compilation-proxy ${this.originalModule.readableIdentifier( - requestShortener - )}`; + get category() { + return "esm"; } /** - * Assuming this module is in the cache. Update the (cached) module with - * the fresh module from the factory. Usually updates internal references - * and properties. - * @param {Module} module fresh module + * Update the hash + * @param {Hash} hash hash to be updated + * @param {UpdateHashContext} context context * @returns {void} */ - updateCacheModule(module) { - super.updateCacheModule(module); - const m = /** @type {LazyCompilationProxyModule} */ (module); - this.originalModule = m.originalModule; - this.request = m.request; - this.client = m.client; - this.data = m.data; - this.active = m.active; + updateHash(hash, context) { + if (this._hashUpdate === undefined) { + this._hashUpdate = + this.identifier + (this.path ? this.path.join(",") : "null"); + } + hash.update(this._hashUpdate); } - /** - * @param {LibIdentOptions} options options - * @returns {string | null} an identifier for library inclusion - */ - libIdent(options) { - return `${this.originalModule.libIdent(options)}!lazy-compilation-proxy`; + serialize(context) { + const { write } = context; + write(this.identifier); + write(this.path); + super.serialize(context); } - /** - * @param {NeedBuildContext} context context info - * @param {function(WebpackError=, boolean=): void} callback callback function, returns true, if the module needs a rebuild - * @returns {void} - */ - needBuild(context, callback) { - callback(null, !this.buildInfo || this.buildInfo.active !== this.active); + deserialize(context) { + const { read } = context; + this.identifier = read(); + this.path = read(); + super.deserialize(context); } +} + +makeSerializable( + ProvidedDependency, + "webpack/lib/dependencies/ProvidedDependency" +); +class ProvidedDependencyTemplate extends ModuleDependency.Template { /** - * @param {WebpackOptions} options webpack options - * @param {Compilation} compilation the compilation - * @param {ResolverWithOptions} resolver the resolver - * @param {InputFileSystem} fs the file system - * @param {function(WebpackError=): void} callback callback function + * @param {Dependency} dependency the dependency for which the template should be applied + * @param {ReplaceSource} source the current replace source which can be modified + * @param {DependencyTemplateContext} templateContext the context object * @returns {void} */ - build(options, compilation, resolver, fs, callback) { - this.buildInfo = { - active: this.active - }; - /** @type {BuildMeta} */ - this.buildMeta = {}; - this.clearDependenciesAndBlocks(); - const dep = new CommonJsRequireDependency(this.client); - this.addDependency(dep); - if (this.active) { - const dep = new LazyCompilationDependency(this); - const block = new AsyncDependenciesBlock({}); - block.addDependency(dep); - this.addBlock(block); + apply( + dependency, + source, + { + runtimeTemplate, + moduleGraph, + chunkGraph, + initFragments, + runtimeRequirements } - callback(); + ) { + const dep = /** @type {ProvidedDependency} */ (dependency); + initFragments.push( + new InitFragment( + `/* provided dependency */ var ${ + dep.identifier + } = ${runtimeTemplate.moduleExports({ + module: moduleGraph.getModule(dep), + chunkGraph, + request: dep.request, + runtimeRequirements + })}${pathToString(dep.path)};\n`, + InitFragment.STAGE_PROVIDES, + 1, + `provided ${dep.identifier}` + ) + ); + source.replace(dep.range[0], dep.range[1] - 1, dep.identifier); } +} - /** - * @returns {Set} types available (do not mutate) - */ - getSourceTypes() { - return TYPES; - } +ProvidedDependency.Template = ProvidedDependencyTemplate; - /** - * @param {string=} type the source type for which the size should be estimated - * @returns {number} the estimated size of the module (must be non-zero) - */ - size(type) { - return 200; - } +module.exports = ProvidedDependency; + + +/***/ }), + +/***/ 24746: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ + + +const { UsageState } = __webpack_require__(4295); +const makeSerializable = __webpack_require__(26522); +const { filterRuntime } = __webpack_require__(19655); +const NullDependency = __webpack_require__(65845); + +/** @typedef {import("webpack-sources").ReplaceSource} ReplaceSource */ +/** @typedef {import("../ChunkGraph")} ChunkGraph */ +/** @typedef {import("../Dependency")} Dependency */ +/** @typedef {import("../Dependency").UpdateHashContext} UpdateHashContext */ +/** @typedef {import("../DependencyTemplate").DependencyTemplateContext} DependencyTemplateContext */ +/** @typedef {import("../ModuleGraph")} ModuleGraph */ +/** @typedef {import("../ModuleGraphConnection").ConnectionState} ConnectionState */ +/** @typedef {import("../util/Hash")} Hash */ + +class PureExpressionDependency extends NullDependency { /** - * @param {CodeGenerationContext} context context for code generation - * @returns {CodeGenerationResult} result + * @param {[number, number]} range the source range */ - codeGeneration({ runtimeTemplate, chunkGraph, moduleGraph }) { - const sources = new Map(); - const runtimeRequirements = new Set(); - runtimeRequirements.add(RuntimeGlobals.module); - const clientDep = /** @type {CommonJsRequireDependency} */ ( - this.dependencies[0] - ); - const clientModule = moduleGraph.getModule(clientDep); - const block = this.blocks[0]; - const client = Template.asString([ - `var client = ${runtimeTemplate.moduleExports({ - module: clientModule, - chunkGraph, - request: clientDep.userRequest, - runtimeRequirements - })}`, - `var data = ${JSON.stringify(this.data)};` - ]); - const keepActive = Template.asString([ - `var dispose = client.keepAlive({ data: data, active: ${JSON.stringify( - !!block - )}, module: module, onError: onError });` - ]); - let source; - if (block) { - const dep = block.dependencies[0]; - const module = moduleGraph.getModule(dep); - source = Template.asString([ - client, - `module.exports = ${runtimeTemplate.moduleNamespacePromise({ - chunkGraph, - block, - module, - request: this.request, - strict: false, // TODO this should be inherited from the original module - message: "import()", - runtimeRequirements - })};`, - "if (module.hot) {", - Template.indent([ - "module.hot.accept();", - `module.hot.accept(${JSON.stringify( - chunkGraph.getModuleId(module) - )}, function() { module.hot.invalidate(); });`, - "module.hot.dispose(function(data) { delete data.resolveSelf; dispose(data); });", - "if (module.hot.data && module.hot.data.resolveSelf) module.hot.data.resolveSelf(module.exports);" - ]), - "}", - "function onError() { /* ignore */ }", - keepActive - ]); - } else { - source = Template.asString([ - client, - "var resolveSelf, onError;", - `module.exports = new Promise(function(resolve, reject) { resolveSelf = resolve; onError = reject; });`, - "if (module.hot) {", - Template.indent([ - "module.hot.accept();", - "if (module.hot.data && module.hot.data.resolveSelf) module.hot.data.resolveSelf(module.exports);", - "module.hot.dispose(function(data) { data.resolveSelf = resolveSelf; dispose(data); });" - ]), - "}", - keepActive - ]); - } - sources.set("javascript", new RawSource(source)); - return { - sources, - runtimeRequirements - }; + constructor(range) { + super(); + this.range = range; + /** @type {Set | false} */ + this.usedByExports = false; + this._hashUpdate = undefined; } /** - * @param {Hash} hash the hash used to track dependencies + * Update the hash + * @param {Hash} hash hash to be updated * @param {UpdateHashContext} context context * @returns {void} */ updateHash(hash, context) { - super.updateHash(hash, context); - hash.update(this.active ? "active" : ""); - hash.update(JSON.stringify(this.data)); + if (this._hashUpdate === undefined) { + this._hashUpdate = this.range + ""; + } + hash.update(this._hashUpdate); } -} -registerNotSerializable(LazyCompilationProxyModule); + /** + * @param {ModuleGraph} moduleGraph the module graph + * @returns {ConnectionState} how this dependency connects the module to referencing modules + */ + getModuleEvaluationSideEffectsState(moduleGraph) { + return false; + } -class LazyCompilationDependencyFactory extends ModuleFactory { - constructor(factory) { - super(); - this._factory = factory; + serialize(context) { + const { write } = context; + write(this.range); + write(this.usedByExports); + super.serialize(context); } - /** - * @param {ModuleFactoryCreateData} data data object - * @param {function(Error=, ModuleFactoryResult=): void} callback callback - * @returns {void} - */ - create(data, callback) { - const dependency = /** @type {LazyCompilationDependency} */ ( - data.dependencies[0] - ); - callback(null, { - module: dependency.proxyModule.originalModule - }); + deserialize(context) { + const { read } = context; + this.range = read(); + this.usedByExports = read(); + super.deserialize(context); } } -class LazyCompilationPlugin { - /** - * @param {Object} options options - * @param {(function(Compiler, function(Error?, BackendApi?): void): void) | function(Compiler): Promise} options.backend the backend - * @param {boolean} options.entries true, when entries are lazy compiled - * @param {boolean} options.imports true, when import() modules are lazy compiled - * @param {RegExp | string | (function(Module): boolean)} options.test additional filter for lazy compiled entrypoint modules - */ - constructor({ backend, entries, imports, test }) { - this.backend = backend; - this.entries = entries; - this.imports = imports; - this.test = test; - } +makeSerializable( + PureExpressionDependency, + "webpack/lib/dependencies/PureExpressionDependency" +); + +PureExpressionDependency.Template = class PureExpressionDependencyTemplate extends ( + NullDependency.Template +) { /** - * Apply the plugin - * @param {Compiler} compiler the compiler instance + * @param {Dependency} dependency the dependency for which the template should be applied + * @param {ReplaceSource} source the current replace source which can be modified + * @param {DependencyTemplateContext} templateContext the context object * @returns {void} */ - apply(compiler) { - let backend; - compiler.hooks.beforeCompile.tapAsync( - "LazyCompilationPlugin", - (params, callback) => { - if (backend !== undefined) return callback(); - const promise = this.backend(compiler, (err, result) => { - if (err) return callback(err); - backend = result; - callback(); - }); - if (promise && promise.then) { - promise.then(b => { - backend = b; - callback(); - }, callback); - } - } - ); - compiler.hooks.thisCompilation.tap( - "LazyCompilationPlugin", - (compilation, { normalModuleFactory }) => { - normalModuleFactory.hooks.module.tap( - "LazyCompilationPlugin", - (originalModule, createData, resolveData) => { - if ( - resolveData.dependencies.every( - dep => - IGNORED_DEPENDENCY_TYPES.has(dep.type) || - (this.imports && - (dep.type === "import()" || - dep.type === "import() context element")) || - (this.entries && dep.type === "entry") - ) && - !/webpack[/\\]hot[/\\]|webpack-dev-server[/\\]client/.test( - resolveData.request - ) && - checkTest(this.test, originalModule) - ) { - const moduleInfo = backend.module(originalModule); - if (!moduleInfo) return; - const { client, data, active } = moduleInfo; + apply( + dependency, + source, + { chunkGraph, moduleGraph, runtime, runtimeTemplate, runtimeRequirements } + ) { + const dep = /** @type {PureExpressionDependency} */ (dependency); - return new LazyCompilationProxyModule( - compiler.context, - originalModule, - resolveData.request, - client, - data, - active - ); - } + const usedByExports = dep.usedByExports; + if (usedByExports !== false) { + const selfModule = moduleGraph.getParentModule(dep); + const exportsInfo = moduleGraph.getExportsInfo(selfModule); + const runtimeCondition = filterRuntime(runtime, runtime => { + for (const exportName of usedByExports) { + if (exportsInfo.getUsed(exportName, runtime) !== UsageState.Unused) { + return true; } + } + return false; + }); + if (runtimeCondition === true) return; + if (runtimeCondition !== false) { + const condition = runtimeTemplate.runtimeConditionExpression({ + chunkGraph, + runtime, + runtimeCondition, + runtimeRequirements + }); + source.insert( + dep.range[0], + `(/* runtime-dependent pure expression or super */ ${condition} ? (` ); - compilation.dependencyFactories.set( - LazyCompilationDependency, - new LazyCompilationDependencyFactory() - ); + source.insert(dep.range[1], ") : null)"); + return; } + } + + source.insert( + dep.range[0], + `(/* unused pure expression or super */ null && (` ); - compiler.hooks.shutdown.tapAsync("LazyCompilationPlugin", callback => { - backend.dispose(callback); - }); + source.insert(dep.range[1], "))"); } -} +}; -module.exports = LazyCompilationPlugin; +module.exports = PureExpressionDependency; /***/ }), -/***/ 46574: +/***/ 98854: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; @@ -88041,145 +85918,51 @@ module.exports = LazyCompilationPlugin; -/** @typedef {import("http").ServerOptions} HttpServerOptions */ -/** @typedef {import("https").ServerOptions} HttpsServerOptions */ -/** @typedef {import("../../declarations/WebpackOptions").LazyCompilationDefaultBackendOptions} LazyCompilationDefaultBackendOptions */ -/** @typedef {import("../Compiler")} Compiler */ +const makeSerializable = __webpack_require__(26522); +const ContextDependency = __webpack_require__(67840); +const ModuleDependencyTemplateAsRequireId = __webpack_require__(77802); -/** - * @callback BackendHandler - * @param {Compiler} compiler compiler - * @param {function(Error?, any?): void} callback callback - * @returns {void} - */ +class RequireContextDependency extends ContextDependency { + constructor(options, range) { + super(options); -/** - * @param {Omit & { client: NonNullable}} options additional options for the backend - * @returns {BackendHandler} backend - */ -module.exports = options => (compiler, callback) => { - const logger = compiler.getInfrastructureLogger("LazyCompilationBackend"); - const activeModules = new Map(); - const prefix = "/lazy-compilation-using-"; + this.range = range; + } - const isHttps = - options.protocol === "https" || - (typeof options.server === "object" && - ("key" in options.server || "pfx" in options.server)); + get type() { + return "require.context"; + } - const createServer = - typeof options.server === "function" - ? options.server - : (() => { - const http = isHttps ? __webpack_require__(57211) : __webpack_require__(98605); - return http.createServer.bind(http, options.server); - })(); - const listen = - typeof options.listen === "function" - ? options.listen - : server => { - let listen = options.listen; - if (typeof listen === "object" && !("port" in listen)) - listen = { ...listen, port: undefined }; - server.listen(listen); - }; + serialize(context) { + const { write } = context; - const protocol = options.protocol || (isHttps ? "https" : "http"); + write(this.range); - const requestListener = (req, res) => { - const keys = req.url.slice(prefix.length).split("@"); - req.socket.on("close", () => { - setTimeout(() => { - for (const key of keys) { - const oldValue = activeModules.get(key) || 0; - activeModules.set(key, oldValue - 1); - if (oldValue === 1) { - logger.log( - `${key} is no longer in use. Next compilation will skip this module.` - ); - } - } - }, 120000); - }); - req.socket.setNoDelay(true); - res.writeHead(200, { - "content-type": "text/event-stream", - "Access-Control-Allow-Origin": "*" - }); - res.write("\n"); - let moduleActivated = false; - for (const key of keys) { - const oldValue = activeModules.get(key) || 0; - activeModules.set(key, oldValue + 1); - if (oldValue === 0) { - logger.log(`${key} is now in use and will be compiled.`); - moduleActivated = true; - } - } - if (moduleActivated && compiler.watching) compiler.watching.invalidate(); - }; + super.serialize(context); + } - const server = /** @type {import("net").Server} */ (createServer()); - server.on("request", requestListener); + deserialize(context) { + const { read } = context; - let isClosing = false; - /** @type {Set} */ - const sockets = new Set(); - server.on("connection", socket => { - sockets.add(socket); - socket.on("close", () => { - sockets.delete(socket); - }); - if (isClosing) socket.destroy(); - }); - server.on("clientError", e => { - if (e.message !== "Server is disposing") logger.warn(e); - }); - server.on("listening", err => { - if (err) return callback(err); - const addr = server.address(); - if (typeof addr === "string") throw new Error("addr must not be a string"); - const urlBase = - addr.address === "::" || addr.address === "0.0.0.0" - ? `${protocol}://localhost:${addr.port}` - : addr.family === "IPv6" - ? `${protocol}://[${addr.address}]:${addr.port}` - : `${protocol}://${addr.address}:${addr.port}`; - logger.log( - `Server-Sent-Events server for lazy compilation open at ${urlBase}.` - ); - callback(null, { - dispose(callback) { - isClosing = true; - // Removing the listener is a workaround for a memory leak in node.js - server.off("request", requestListener); - server.close(err => { - callback(err); - }); - for (const socket of sockets) { - socket.destroy(new Error("Server is disposing")); - } - }, - module(originalModule) { - const key = `${encodeURIComponent( - originalModule.identifier().replace(/\\/g, "/").replace(/@/g, "_") - ).replace(/%(2F|3A|24|26|2B|2C|3B|3D|3A)/g, decodeURIComponent)}`; - const active = activeModules.get(key) > 0; - return { - client: `${options.client}?${encodeURIComponent(urlBase + prefix)}`, - data: key, - active - }; - } - }); - }); - listen(server); -}; + this.range = read(); + + super.deserialize(context); + } +} + +makeSerializable( + RequireContextDependency, + "webpack/lib/dependencies/RequireContextDependency" +); + +RequireContextDependency.Template = ModuleDependencyTemplateAsRequireId; + +module.exports = RequireContextDependency; /***/ }), -/***/ 7047: +/***/ 18885: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; @@ -88190,109 +85973,84 @@ module.exports = options => (compiler, callback) => { -const { find } = __webpack_require__(34715); -const { - compareModulesByPreOrderIndexOrIdentifier, - compareModulesByPostOrderIndexOrIdentifier -} = __webpack_require__(26296); - -/** @typedef {import("../Compiler")} Compiler */ - -class ChunkModuleIdRangePlugin { - constructor(options) { - this.options = options; - } - - /** - * Apply the plugin - * @param {Compiler} compiler the compiler instance - * @returns {void} - */ - apply(compiler) { - const options = this.options; - compiler.hooks.compilation.tap("ChunkModuleIdRangePlugin", compilation => { - const moduleGraph = compilation.moduleGraph; - compilation.hooks.moduleIds.tap("ChunkModuleIdRangePlugin", modules => { - const chunkGraph = compilation.chunkGraph; - const chunk = find( - compilation.chunks, - chunk => chunk.name === options.name - ); - if (!chunk) { - throw new Error( - `ChunkModuleIdRangePlugin: Chunk with name '${options.name}"' was not found` - ); - } +const RequireContextDependency = __webpack_require__(98854); - let chunkModules; - if (options.order) { - let cmpFn; - switch (options.order) { - case "index": - case "preOrderIndex": - cmpFn = compareModulesByPreOrderIndexOrIdentifier(moduleGraph); - break; - case "index2": - case "postOrderIndex": - cmpFn = compareModulesByPostOrderIndexOrIdentifier(moduleGraph); - break; - default: - throw new Error( - "ChunkModuleIdRangePlugin: unexpected value of order" - ); +module.exports = class RequireContextDependencyParserPlugin { + apply(parser) { + parser.hooks.call + .for("require.context") + .tap("RequireContextDependencyParserPlugin", expr => { + let regExp = /^\.\/.*$/; + let recursive = true; + let mode = "sync"; + switch (expr.arguments.length) { + case 4: { + const modeExpr = parser.evaluateExpression(expr.arguments[3]); + if (!modeExpr.isString()) return; + mode = modeExpr.string; } - chunkModules = chunkGraph.getOrderedChunkModules(chunk, cmpFn); - } else { - chunkModules = Array.from(modules) - .filter(m => { - return chunkGraph.isModuleInChunk(m, chunk); - }) - .sort(compareModulesByPreOrderIndexOrIdentifier(moduleGraph)); - } - - let currentId = options.start || 0; - for (let i = 0; i < chunkModules.length; i++) { - const m = chunkModules[i]; - if (m.needId && chunkGraph.getModuleId(m) === null) { - chunkGraph.setModuleId(m, currentId++); + // falls through + case 3: { + const regExpExpr = parser.evaluateExpression(expr.arguments[2]); + if (!regExpExpr.isRegExp()) return; + regExp = regExpExpr.regExp; + } + // falls through + case 2: { + const recursiveExpr = parser.evaluateExpression(expr.arguments[1]); + if (!recursiveExpr.isBoolean()) return; + recursive = recursiveExpr.bool; + } + // falls through + case 1: { + const requestExpr = parser.evaluateExpression(expr.arguments[0]); + if (!requestExpr.isString()) return; + const dep = new RequireContextDependency( + { + request: requestExpr.string, + recursive, + regExp, + mode, + category: "commonjs" + }, + expr.range + ); + dep.loc = expr.loc; + dep.optional = !!parser.scope.inTry; + parser.state.current.addDependency(dep); + return true; } - if (options.end && currentId > options.end) break; } }); - }); } -} -module.exports = ChunkModuleIdRangePlugin; +}; /***/ }), -/***/ 64801: +/***/ 30738: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; /* MIT License http://www.opensource.org/licenses/mit-license.php - Author Florent Cailhol @ooflorent + Author Tobias Koppers @sokra */ -const { compareChunksNatural } = __webpack_require__(26296); -const { - getFullChunkName, - getUsedChunkIds, - assignDeterministicIds -} = __webpack_require__(72922); +const { cachedSetProperty } = __webpack_require__(11217); +const ContextElementDependency = __webpack_require__(83853); +const RequireContextDependency = __webpack_require__(98854); +const RequireContextDependencyParserPlugin = __webpack_require__(18885); +/** @typedef {import("../../declarations/WebpackOptions").ResolveOptions} ResolveOptions */ /** @typedef {import("../Compiler")} Compiler */ -/** @typedef {import("../Module")} Module */ -class DeterministicChunkIdsPlugin { - constructor(options) { - this.options = options || {}; - } +/** @type {ResolveOptions} */ +const EMPTY_RESOLVE_OPTIONS = {}; +class RequireContextPlugin { /** * Apply the plugin * @param {Compiler} compiler the compiler instance @@ -88300,137 +86058,138 @@ class DeterministicChunkIdsPlugin { */ apply(compiler) { compiler.hooks.compilation.tap( - "DeterministicChunkIdsPlugin", - compilation => { - compilation.hooks.chunkIds.tap( - "DeterministicChunkIdsPlugin", - chunks => { - const chunkGraph = compilation.chunkGraph; - const context = this.options.context - ? this.options.context - : compiler.context; - const maxLength = this.options.maxLength || 3; - - const compareNatural = compareChunksNatural(chunkGraph); - - const usedIds = getUsedChunkIds(compilation); - assignDeterministicIds( - Array.from(chunks).filter(chunk => { - return chunk.id === null; - }), - chunk => - getFullChunkName(chunk, chunkGraph, context, compiler.root), - compareNatural, - (chunk, id) => { - const size = usedIds.size; - usedIds.add(`${id}`); - if (size === usedIds.size) return false; - chunk.id = id; - chunk.ids = [id]; - return true; - }, - [Math.pow(10, maxLength)], - 10, - usedIds.size - ); - } + "RequireContextPlugin", + (compilation, { contextModuleFactory, normalModuleFactory }) => { + compilation.dependencyFactories.set( + RequireContextDependency, + contextModuleFactory + ); + compilation.dependencyTemplates.set( + RequireContextDependency, + new RequireContextDependency.Template() ); - } - ); - } -} - -module.exports = DeterministicChunkIdsPlugin; - - -/***/ }), -/***/ 84965: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + compilation.dependencyFactories.set( + ContextElementDependency, + normalModuleFactory + ); -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Florent Cailhol @ooflorent -*/ + const handler = (parser, parserOptions) => { + if ( + parserOptions.requireContext !== undefined && + !parserOptions.requireContext + ) + return; + new RequireContextDependencyParserPlugin().apply(parser); + }; + normalModuleFactory.hooks.parser + .for("javascript/auto") + .tap("RequireContextPlugin", handler); + normalModuleFactory.hooks.parser + .for("javascript/dynamic") + .tap("RequireContextPlugin", handler); -const { - compareModulesByPreOrderIndexOrIdentifier -} = __webpack_require__(26296); -const { - getUsedModuleIds, - getFullModuleName, - assignDeterministicIds -} = __webpack_require__(72922); + contextModuleFactory.hooks.alternativeRequests.tap( + "RequireContextPlugin", + (items, options) => { + if (items.length === 0) return items; -/** @typedef {import("../Compiler")} Compiler */ -/** @typedef {import("../Module")} Module */ + const finalResolveOptions = compiler.resolverFactory.get( + "normal", + cachedSetProperty( + options.resolveOptions || EMPTY_RESOLVE_OPTIONS, + "dependencyType", + options.category + ) + ).options; -class DeterministicModuleIdsPlugin { - constructor(options) { - this.options = options || {}; - } + let newItems; + if (!finalResolveOptions.fullySpecified) { + newItems = []; + for (const item of items) { + const { request, context } = item; + for (const ext of finalResolveOptions.extensions) { + if (request.endsWith(ext)) { + newItems.push({ + context, + request: request.slice(0, -ext.length) + }); + } + } + if (!finalResolveOptions.enforceExtension) { + newItems.push(item); + } + } + items = newItems; - /** - * Apply the plugin - * @param {Compiler} compiler the compiler instance - * @returns {void} - */ - apply(compiler) { - compiler.hooks.compilation.tap( - "DeterministicModuleIdsPlugin", - compilation => { - compilation.hooks.moduleIds.tap( - "DeterministicModuleIdsPlugin", - modules => { - const chunkGraph = compilation.chunkGraph; - const context = this.options.context - ? this.options.context - : compiler.context; - const maxLength = this.options.maxLength || 3; + newItems = []; + for (const obj of items) { + const { request, context } = obj; + for (const mainFile of finalResolveOptions.mainFiles) { + if (request.endsWith(`/${mainFile}`)) { + newItems.push({ + context, + request: request.slice(0, -mainFile.length) + }); + newItems.push({ + context, + request: request.slice(0, -mainFile.length - 1) + }); + } + } + newItems.push(obj); + } + items = newItems; + } - const usedIds = getUsedModuleIds(compilation); - assignDeterministicIds( - Array.from(modules).filter(module => { - if (!module.needId) return false; - if (chunkGraph.getNumberOfModuleChunks(module) === 0) - return false; - return chunkGraph.getModuleId(module) === null; - }), - module => getFullModuleName(module, context, compiler.root), - compareModulesByPreOrderIndexOrIdentifier( - compilation.moduleGraph - ), - (module, id) => { - const size = usedIds.size; - usedIds.add(`${id}`); - if (size === usedIds.size) return false; - chunkGraph.setModuleId(module, id); - return true; - }, - [Math.pow(10, maxLength)], - 10, - usedIds.size - ); + newItems = []; + for (const item of items) { + let hideOriginal = false; + for (const modulesItems of finalResolveOptions.modules) { + if (Array.isArray(modulesItems)) { + for (const dir of modulesItems) { + if (item.request.startsWith(`./${dir}/`)) { + newItems.push({ + context: item.context, + request: item.request.slice(dir.length + 3) + }); + hideOriginal = true; + } + } + } else { + const dir = modulesItems.replace(/\\/g, "/"); + const fullPath = + item.context.replace(/\\/g, "/") + item.request.slice(1); + if (fullPath.startsWith(dir)) { + newItems.push({ + context: item.context, + request: fullPath.slice(dir.length + 1) + }); + } + } + } + if (!hideOriginal) { + newItems.push(item); + } + } + return newItems; } ); } ); } } - -module.exports = DeterministicModuleIdsPlugin; +module.exports = RequireContextPlugin; /***/ }), -/***/ 83635: +/***/ 91421: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; -/* module decorator */ module = __webpack_require__.nmd(module); /* MIT License http://www.opensource.org/licenses/mit-license.php Author Tobias Koppers @sokra @@ -88438,85 +86197,27 @@ module.exports = DeterministicModuleIdsPlugin; -const { - compareModulesByPreOrderIndexOrIdentifier -} = __webpack_require__(26296); -const createSchemaValidation = __webpack_require__(77695); -const createHash = __webpack_require__(24123); -const { getUsedModuleIds, getFullModuleName } = __webpack_require__(72922); - -/** @typedef {import("../../declarations/plugins/HashedModuleIdsPlugin").HashedModuleIdsPluginOptions} HashedModuleIdsPluginOptions */ - -const validate = createSchemaValidation( - __webpack_require__(168), - () => __webpack_require__(72864), - { - name: "Hashed Module Ids Plugin", - baseDataPath: "options" - } -); - -class HashedModuleIdsPlugin { - /** - * @param {HashedModuleIdsPluginOptions=} options options object - */ - constructor(options = {}) { - validate(options); - - /** @type {HashedModuleIdsPluginOptions} */ - this.options = { - context: null, - hashFunction: "md4", - hashDigest: "base64", - hashDigestLength: 4, - ...options - }; - } - - apply(compiler) { - const options = this.options; - compiler.hooks.compilation.tap("HashedModuleIdsPlugin", compilation => { - compilation.hooks.moduleIds.tap("HashedModuleIdsPlugin", modules => { - const chunkGraph = compilation.chunkGraph; - const context = this.options.context - ? this.options.context - : compiler.context; +const AsyncDependenciesBlock = __webpack_require__(11315); +const makeSerializable = __webpack_require__(26522); - const usedIds = getUsedModuleIds(compilation); - const modulesInNaturalOrder = Array.from(modules) - .filter(m => { - if (!m.needId) return false; - if (chunkGraph.getNumberOfModuleChunks(m) === 0) return false; - return chunkGraph.getModuleId(module) === null; - }) - .sort( - compareModulesByPreOrderIndexOrIdentifier(compilation.moduleGraph) - ); - for (const module of modulesInNaturalOrder) { - const ident = getFullModuleName(module, context, compiler.root); - const hash = createHash(options.hashFunction); - hash.update(ident || ""); - const hashId = /** @type {string} */ ( - hash.digest(options.hashDigest) - ); - let len = options.hashDigestLength; - while (usedIds.has(hashId.substr(0, len))) len++; - const moduleId = hashId.substr(0, len); - chunkGraph.setModuleId(module, moduleId); - usedIds.add(moduleId); - } - }); - }); +class RequireEnsureDependenciesBlock extends AsyncDependenciesBlock { + constructor(chunkName, loc) { + super(chunkName, loc, null); } } -module.exports = HashedModuleIdsPlugin; +makeSerializable( + RequireEnsureDependenciesBlock, + "webpack/lib/dependencies/RequireEnsureDependenciesBlock" +); + +module.exports = RequireEnsureDependenciesBlock; /***/ }), -/***/ 72922: -/***/ (function(__unused_webpack_module, exports, __webpack_require__) { +/***/ 95195: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; /* @@ -88526,467 +86227,349 @@ module.exports = HashedModuleIdsPlugin; -const createHash = __webpack_require__(24123); -const { makePathsRelative } = __webpack_require__(96236); -const numberHash = __webpack_require__(91679); - -/** @typedef {import("../Chunk")} Chunk */ -/** @typedef {import("../ChunkGraph")} ChunkGraph */ -/** @typedef {import("../Compilation")} Compilation */ -/** @typedef {import("../Module")} Module */ -/** @typedef {typeof import("../util/Hash")} Hash */ - -/** - * @param {string} str string to hash - * @param {number} len max length of the hash - * @param {string | Hash} hashFunction hash function to use - * @returns {string} hash - */ -const getHash = (str, len, hashFunction) => { - const hash = createHash(hashFunction); - hash.update(str); - const digest = /** @type {string} */ (hash.digest("hex")); - return digest.substr(0, len); -}; - -/** - * @param {string} str the string - * @returns {string} string prefixed by an underscore if it is a number - */ -const avoidNumber = str => { - // max length of a number is 21 chars, bigger numbers a written as "...e+xx" - if (str.length > 21) return str; - const firstChar = str.charCodeAt(0); - // skip everything that doesn't look like a number - // charCodes: "-": 45, "1": 49, "9": 57 - if (firstChar < 49) { - if (firstChar !== 45) return str; - } else if (firstChar > 57) { - return str; - } - if (str === +str + "") { - return `_${str}`; - } - return str; -}; - -/** - * @param {string} request the request - * @returns {string} id representation - */ -const requestToId = request => { - return request - .replace(/^(\.\.?\/)+/, "") - .replace(/(^[.-]|[^a-zA-Z0-9_-])+/g, "_"); -}; -exports.requestToId = requestToId; - -/** - * @param {string} string the string - * @param {string} delimiter separator for string and hash - * @param {string | Hash} hashFunction hash function to use - * @returns {string} string with limited max length to 100 chars - */ -const shortenLongString = (string, delimiter, hashFunction) => { - if (string.length < 100) return string; - return ( - string.slice(0, 100 - 6 - delimiter.length) + - delimiter + - getHash(string, 6, hashFunction) - ); -}; - -/** - * @param {Module} module the module - * @param {string} context context directory - * @param {Object=} associatedObjectForCache an object to which the cache will be attached - * @returns {string} short module name - */ -const getShortModuleName = (module, context, associatedObjectForCache) => { - const libIdent = module.libIdent({ context, associatedObjectForCache }); - if (libIdent) return avoidNumber(libIdent); - const nameForCondition = module.nameForCondition(); - if (nameForCondition) - return avoidNumber( - makePathsRelative(context, nameForCondition, associatedObjectForCache) - ); - return ""; -}; -exports.getShortModuleName = getShortModuleName; - -/** - * @param {string} shortName the short name - * @param {Module} module the module - * @param {string} context context directory - * @param {string | Hash} hashFunction hash function to use - * @param {Object=} associatedObjectForCache an object to which the cache will be attached - * @returns {string} long module name - */ -const getLongModuleName = ( - shortName, - module, - context, - hashFunction, - associatedObjectForCache -) => { - const fullName = getFullModuleName(module, context, associatedObjectForCache); - return `${shortName}?${getHash(fullName, 4, hashFunction)}`; -}; -exports.getLongModuleName = getLongModuleName; - -/** - * @param {Module} module the module - * @param {string} context context directory - * @param {Object=} associatedObjectForCache an object to which the cache will be attached - * @returns {string} full module name - */ -const getFullModuleName = (module, context, associatedObjectForCache) => { - return makePathsRelative( - context, - module.identifier(), - associatedObjectForCache - ); -}; -exports.getFullModuleName = getFullModuleName; +const RequireEnsureDependenciesBlock = __webpack_require__(91421); +const RequireEnsureDependency = __webpack_require__(975); +const RequireEnsureItemDependency = __webpack_require__(56867); +const getFunctionExpression = __webpack_require__(70108); -/** - * @param {Chunk} chunk the chunk - * @param {ChunkGraph} chunkGraph the chunk graph - * @param {string} context context directory - * @param {string} delimiter delimiter for names - * @param {string | Hash} hashFunction hash function to use - * @param {Object=} associatedObjectForCache an object to which the cache will be attached - * @returns {string} short chunk name - */ -const getShortChunkName = ( - chunk, - chunkGraph, - context, - delimiter, - hashFunction, - associatedObjectForCache -) => { - const modules = chunkGraph.getChunkRootModules(chunk); - const shortModuleNames = modules.map(m => - requestToId(getShortModuleName(m, context, associatedObjectForCache)) - ); - chunk.idNameHints.sort(); - const chunkName = Array.from(chunk.idNameHints) - .concat(shortModuleNames) - .filter(Boolean) - .join(delimiter); - return shortenLongString(chunkName, delimiter, hashFunction); -}; -exports.getShortChunkName = getShortChunkName; +module.exports = class RequireEnsureDependenciesBlockParserPlugin { + apply(parser) { + parser.hooks.call + .for("require.ensure") + .tap("RequireEnsureDependenciesBlockParserPlugin", expr => { + let chunkName = null; + let errorExpressionArg = null; + let errorExpression = null; + switch (expr.arguments.length) { + case 4: { + const chunkNameExpr = parser.evaluateExpression(expr.arguments[3]); + if (!chunkNameExpr.isString()) return; + chunkName = chunkNameExpr.string; + } + // falls through + case 3: { + errorExpressionArg = expr.arguments[2]; + errorExpression = getFunctionExpression(errorExpressionArg); -/** - * @param {Chunk} chunk the chunk - * @param {ChunkGraph} chunkGraph the chunk graph - * @param {string} context context directory - * @param {string} delimiter delimiter for names - * @param {string | Hash} hashFunction hash function to use - * @param {Object=} associatedObjectForCache an object to which the cache will be attached - * @returns {string} short chunk name - */ -const getLongChunkName = ( - chunk, - chunkGraph, - context, - delimiter, - hashFunction, - associatedObjectForCache -) => { - const modules = chunkGraph.getChunkRootModules(chunk); - const shortModuleNames = modules.map(m => - requestToId(getShortModuleName(m, context, associatedObjectForCache)) - ); - const longModuleNames = modules.map(m => - requestToId( - getLongModuleName("", m, context, hashFunction, associatedObjectForCache) - ) - ); - chunk.idNameHints.sort(); - const chunkName = Array.from(chunk.idNameHints) - .concat(shortModuleNames, longModuleNames) - .filter(Boolean) - .join(delimiter); - return shortenLongString(chunkName, delimiter, hashFunction); -}; -exports.getLongChunkName = getLongChunkName; + if (!errorExpression && !chunkName) { + const chunkNameExpr = parser.evaluateExpression( + expr.arguments[2] + ); + if (!chunkNameExpr.isString()) return; + chunkName = chunkNameExpr.string; + } + } + // falls through + case 2: { + const dependenciesExpr = parser.evaluateExpression( + expr.arguments[0] + ); + const dependenciesItems = dependenciesExpr.isArray() + ? dependenciesExpr.items + : [dependenciesExpr]; + const successExpressionArg = expr.arguments[1]; + const successExpression = + getFunctionExpression(successExpressionArg); -/** - * @param {Chunk} chunk the chunk - * @param {ChunkGraph} chunkGraph the chunk graph - * @param {string} context context directory - * @param {Object=} associatedObjectForCache an object to which the cache will be attached - * @returns {string} full chunk name - */ -const getFullChunkName = ( - chunk, - chunkGraph, - context, - associatedObjectForCache -) => { - if (chunk.name) return chunk.name; - const modules = chunkGraph.getChunkRootModules(chunk); - const fullModuleNames = modules.map(m => - makePathsRelative(context, m.identifier(), associatedObjectForCache) - ); - return fullModuleNames.join(); -}; -exports.getFullChunkName = getFullChunkName; + if (successExpression) { + parser.walkExpressions(successExpression.expressions); + } + if (errorExpression) { + parser.walkExpressions(errorExpression.expressions); + } -/** - * @template K - * @template V - * @param {Map} map a map from key to values - * @param {K} key key - * @param {V} value value - * @returns {void} - */ -const addToMapOfItems = (map, key, value) => { - let array = map.get(key); - if (array === undefined) { - array = []; - map.set(key, array); + const depBlock = new RequireEnsureDependenciesBlock( + chunkName, + expr.loc + ); + const errorCallbackExists = + expr.arguments.length === 4 || + (!chunkName && expr.arguments.length === 3); + const dep = new RequireEnsureDependency( + expr.range, + expr.arguments[1].range, + errorCallbackExists && expr.arguments[2].range + ); + dep.loc = expr.loc; + depBlock.addDependency(dep); + const old = parser.state.current; + parser.state.current = depBlock; + try { + let failed = false; + parser.inScope([], () => { + for (const ee of dependenciesItems) { + if (ee.isString()) { + const ensureDependency = new RequireEnsureItemDependency( + ee.string + ); + ensureDependency.loc = ee.loc || expr.loc; + depBlock.addDependency(ensureDependency); + } else { + failed = true; + } + } + }); + if (failed) { + return; + } + if (successExpression) { + if (successExpression.fn.body.type === "BlockStatement") { + parser.walkStatement(successExpression.fn.body); + } else { + parser.walkExpression(successExpression.fn.body); + } + } + old.addBlock(depBlock); + } finally { + parser.state.current = old; + } + if (!successExpression) { + parser.walkExpression(successExpressionArg); + } + if (errorExpression) { + if (errorExpression.fn.body.type === "BlockStatement") { + parser.walkStatement(errorExpression.fn.body); + } else { + parser.walkExpression(errorExpression.fn.body); + } + } else if (errorExpressionArg) { + parser.walkExpression(errorExpressionArg); + } + return true; + } + } + }); } - array.push(value); }; -/** - * @param {Compilation} compilation the compilation - * @returns {Set} used module ids as strings - */ -const getUsedModuleIds = compilation => { - const chunkGraph = compilation.chunkGraph; - /** @type {Set} */ - const usedIds = new Set(); - if (compilation.usedModuleIds) { - for (const id of compilation.usedModuleIds) { - usedIds.add(id + ""); - } - } +/***/ }), - for (const module of compilation.modules) { - const moduleId = chunkGraph.getModuleId(module); - if (moduleId !== null) { - usedIds.add(moduleId + ""); - } - } +/***/ 975: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - return usedIds; -}; -exports.getUsedModuleIds = getUsedModuleIds; +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ -/** - * @param {Compilation} compilation the compilation - * @returns {Set} used chunk ids as strings - */ -const getUsedChunkIds = compilation => { - /** @type {Set} */ - const usedIds = new Set(); - if (compilation.usedChunkIds) { - for (const id of compilation.usedChunkIds) { - usedIds.add(id + ""); - } + + +const RuntimeGlobals = __webpack_require__(49404); +const makeSerializable = __webpack_require__(26522); +const NullDependency = __webpack_require__(65845); + +/** @typedef {import("webpack-sources").ReplaceSource} ReplaceSource */ +/** @typedef {import("../AsyncDependenciesBlock")} AsyncDependenciesBlock */ +/** @typedef {import("../Dependency")} Dependency */ +/** @typedef {import("../DependencyTemplate").DependencyTemplateContext} DependencyTemplateContext */ + +class RequireEnsureDependency extends NullDependency { + constructor(range, contentRange, errorHandlerRange) { + super(); + + this.range = range; + this.contentRange = contentRange; + this.errorHandlerRange = errorHandlerRange; } - for (const chunk of compilation.chunks) { - const chunkId = chunk.id; - if (chunkId !== null) { - usedIds.add(chunkId + ""); - } + get type() { + return "require.ensure"; } - return usedIds; -}; -exports.getUsedChunkIds = getUsedChunkIds; + serialize(context) { + const { write } = context; -/** - * @template T - * @param {Iterable} items list of items to be named - * @param {function(T): string} getShortName get a short name for an item - * @param {function(T, string): string} getLongName get a long name for an item - * @param {function(T, T): -1|0|1} comparator order of items - * @param {Set} usedIds already used ids, will not be assigned - * @param {function(T, string): void} assignName assign a name to an item - * @returns {T[]} list of items without a name - */ -const assignNames = ( - items, - getShortName, - getLongName, - comparator, - usedIds, - assignName -) => { - /** @type {Map} */ - const nameToItems = new Map(); + write(this.range); + write(this.contentRange); + write(this.errorHandlerRange); - for (const item of items) { - const name = getShortName(item); - addToMapOfItems(nameToItems, name, item); + super.serialize(context); } - /** @type {Map} */ - const nameToItems2 = new Map(); + deserialize(context) { + const { read } = context; - for (const [name, items] of nameToItems) { - if (items.length > 1 || !name) { - for (const item of items) { - const longName = getLongName(item, name); - addToMapOfItems(nameToItems2, longName, item); - } - } else { - addToMapOfItems(nameToItems2, name, items[0]); - } + this.range = read(); + this.contentRange = read(); + this.errorHandlerRange = read(); + + super.deserialize(context); } +} - /** @type {T[]} */ - const unnamedItems = []; +makeSerializable( + RequireEnsureDependency, + "webpack/lib/dependencies/RequireEnsureDependency" +); - for (const [name, items] of nameToItems2) { - if (!name) { - for (const item of items) { - unnamedItems.push(item); - } - } else if (items.length === 1 && !usedIds.has(name)) { - assignName(items[0], name); - usedIds.add(name); +RequireEnsureDependency.Template = class RequireEnsureDependencyTemplate extends ( + NullDependency.Template +) { + /** + * @param {Dependency} dependency the dependency for which the template should be applied + * @param {ReplaceSource} source the current replace source which can be modified + * @param {DependencyTemplateContext} templateContext the context object + * @returns {void} + */ + apply( + dependency, + source, + { runtimeTemplate, moduleGraph, chunkGraph, runtimeRequirements } + ) { + const dep = /** @type {RequireEnsureDependency} */ (dependency); + const depBlock = /** @type {AsyncDependenciesBlock} */ ( + moduleGraph.getParentBlock(dep) + ); + const promise = runtimeTemplate.blockPromise({ + chunkGraph, + block: depBlock, + message: "require.ensure", + runtimeRequirements + }); + const range = dep.range; + const contentRange = dep.contentRange; + const errorHandlerRange = dep.errorHandlerRange; + source.replace(range[0], contentRange[0] - 1, `${promise}.then((`); + if (errorHandlerRange) { + source.replace( + contentRange[1], + errorHandlerRange[0] - 1, + ").bind(null, __webpack_require__))['catch'](" + ); + source.replace(errorHandlerRange[1], range[1] - 1, ")"); } else { - items.sort(comparator); - let i = 0; - for (const item of items) { - while (nameToItems2.has(name + i) && usedIds.has(name + i)) i++; - assignName(item, name + i); - usedIds.add(name + i); - i++; - } + source.replace( + contentRange[1], + range[1] - 1, + `).bind(null, __webpack_require__))['catch'](${RuntimeGlobals.uncaughtErrorHandler})` + ); } } - - unnamedItems.sort(comparator); - return unnamedItems; }; -exports.assignNames = assignNames; -/** - * @template T - * @param {T[]} items list of items to be named - * @param {function(T): string} getName get a name for an item - * @param {function(T, T): -1|0|1} comparator order of items - * @param {function(T, number): boolean} assignId assign an id to an item - * @param {number[]} ranges usable ranges for ids - * @param {number} expandFactor factor to create more ranges - * @param {number} extraSpace extra space to allocate, i. e. when some ids are already used - * @returns {void} - */ -const assignDeterministicIds = ( - items, - getName, - comparator, - assignId, - ranges = [10], - expandFactor = 10, - extraSpace = 0 -) => { - items.sort(comparator); +module.exports = RequireEnsureDependency; - // max 5% fill rate - const optimalRange = Math.min( - Math.ceil(items.length * 20) + extraSpace, - Number.MAX_SAFE_INTEGER - ); - let i = 0; - let range = ranges[i]; - while (range < optimalRange) { - i++; - if (i < ranges.length) { - range = Math.min(ranges[i], Number.MAX_SAFE_INTEGER); - } else { - range = Math.min(range * expandFactor, Number.MAX_SAFE_INTEGER); - } - } +/***/ }), - for (const item of items) { - const ident = getName(item); - let id; - let i = 0; - do { - id = numberHash(ident + i++, range); - } while (!assignId(item, id)); - } -}; -exports.assignDeterministicIds = assignDeterministicIds; +/***/ 56867: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { -/** - * @param {Iterable} modules the modules - * @param {Compilation} compilation the compilation - * @returns {void} - */ -const assignAscendingModuleIds = (modules, compilation) => { - const chunkGraph = compilation.chunkGraph; +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ - const usedIds = getUsedModuleIds(compilation); - let nextId = 0; - let assignId; - if (usedIds.size > 0) { - assignId = module => { - if (chunkGraph.getModuleId(module) === null) { - while (usedIds.has(nextId + "")) nextId++; - chunkGraph.setModuleId(module, nextId++); - } - }; - } else { - assignId = module => { - if (chunkGraph.getModuleId(module) === null) { - chunkGraph.setModuleId(module, nextId++); - } - }; + +const makeSerializable = __webpack_require__(26522); +const ModuleDependency = __webpack_require__(80944); +const NullDependency = __webpack_require__(65845); + +class RequireEnsureItemDependency extends ModuleDependency { + constructor(request) { + super(request); } - for (const module of modules) { - assignId(module); + + get type() { + return "require.ensure item"; } -}; -exports.assignAscendingModuleIds = assignAscendingModuleIds; -/** - * @param {Iterable} chunks the chunks - * @param {Compilation} compilation the compilation - * @returns {void} - */ -const assignAscendingChunkIds = (chunks, compilation) => { - const usedIds = getUsedChunkIds(compilation); + get category() { + return "commonjs"; + } +} - let nextId = 0; - if (usedIds.size > 0) { - for (const chunk of chunks) { - if (chunk.id === null) { - while (usedIds.has(nextId + "")) nextId++; - chunk.id = nextId; - chunk.ids = [nextId]; - nextId++; - } - } - } else { - for (const chunk of chunks) { - if (chunk.id === null) { - chunk.id = nextId; - chunk.ids = [nextId]; - nextId++; +makeSerializable( + RequireEnsureItemDependency, + "webpack/lib/dependencies/RequireEnsureItemDependency" +); + +RequireEnsureItemDependency.Template = NullDependency.Template; + +module.exports = RequireEnsureItemDependency; + + +/***/ }), + +/***/ 66697: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ + + + +const RequireEnsureDependency = __webpack_require__(975); +const RequireEnsureItemDependency = __webpack_require__(56867); + +const RequireEnsureDependenciesBlockParserPlugin = __webpack_require__(95195); + +const { + evaluateToString, + toConstantDependency +} = __webpack_require__(28723); + +class RequireEnsurePlugin { + apply(compiler) { + compiler.hooks.compilation.tap( + "RequireEnsurePlugin", + (compilation, { normalModuleFactory }) => { + compilation.dependencyFactories.set( + RequireEnsureItemDependency, + normalModuleFactory + ); + compilation.dependencyTemplates.set( + RequireEnsureItemDependency, + new RequireEnsureItemDependency.Template() + ); + + compilation.dependencyTemplates.set( + RequireEnsureDependency, + new RequireEnsureDependency.Template() + ); + + const handler = (parser, parserOptions) => { + if ( + parserOptions.requireEnsure !== undefined && + !parserOptions.requireEnsure + ) + return; + + new RequireEnsureDependenciesBlockParserPlugin().apply(parser); + parser.hooks.evaluateTypeof + .for("require.ensure") + .tap("RequireEnsurePlugin", evaluateToString("function")); + parser.hooks.typeof + .for("require.ensure") + .tap( + "RequireEnsurePlugin", + toConstantDependency(parser, JSON.stringify("function")) + ); + }; + + normalModuleFactory.hooks.parser + .for("javascript/auto") + .tap("RequireEnsurePlugin", handler); + normalModuleFactory.hooks.parser + .for("javascript/dynamic") + .tap("RequireEnsurePlugin", handler); } - } + ); } -}; -exports.assignAscendingChunkIds = assignAscendingChunkIds; +} +module.exports = RequireEnsurePlugin; /***/ }), -/***/ 30483: +/***/ 57010: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; @@ -88997,85 +86580,61 @@ exports.assignAscendingChunkIds = assignAscendingChunkIds; -const { compareChunksNatural } = __webpack_require__(26296); -const { - getShortChunkName, - getLongChunkName, - assignNames, - getUsedChunkIds, - assignAscendingChunkIds -} = __webpack_require__(72922); +const RuntimeGlobals = __webpack_require__(49404); +const makeSerializable = __webpack_require__(26522); +const NullDependency = __webpack_require__(65845); -/** @typedef {import("../Chunk")} Chunk */ -/** @typedef {import("../Compiler")} Compiler */ -/** @typedef {import("../Module")} Module */ +/** @typedef {import("webpack-sources").ReplaceSource} ReplaceSource */ +/** @typedef {import("../Dependency")} Dependency */ +/** @typedef {import("../DependencyTemplate").DependencyTemplateContext} DependencyTemplateContext */ -class NamedChunkIdsPlugin { - constructor(options) { - this.delimiter = (options && options.delimiter) || "-"; - this.context = options && options.context; +class RequireHeaderDependency extends NullDependency { + constructor(range) { + super(); + if (!Array.isArray(range)) throw new Error("range must be valid"); + this.range = range; + } + + serialize(context) { + const { write } = context; + write(this.range); + super.serialize(context); + } + + static deserialize(context) { + const obj = new RequireHeaderDependency(context.read()); + obj.deserialize(context); + return obj; } +} + +makeSerializable( + RequireHeaderDependency, + "webpack/lib/dependencies/RequireHeaderDependency" +); +RequireHeaderDependency.Template = class RequireHeaderDependencyTemplate extends ( + NullDependency.Template +) { /** - * Apply the plugin - * @param {Compiler} compiler the compiler instance + * @param {Dependency} dependency the dependency for which the template should be applied + * @param {ReplaceSource} source the current replace source which can be modified + * @param {DependencyTemplateContext} templateContext the context object * @returns {void} */ - apply(compiler) { - compiler.hooks.compilation.tap("NamedChunkIdsPlugin", compilation => { - const { hashFunction } = compilation.outputOptions; - compilation.hooks.chunkIds.tap("NamedChunkIdsPlugin", chunks => { - const chunkGraph = compilation.chunkGraph; - const context = this.context ? this.context : compiler.context; - const delimiter = this.delimiter; - - const unnamedChunks = assignNames( - Array.from(chunks).filter(chunk => { - if (chunk.name) { - chunk.id = chunk.name; - chunk.ids = [chunk.name]; - } - return chunk.id === null; - }), - chunk => - getShortChunkName( - chunk, - chunkGraph, - context, - delimiter, - hashFunction, - compiler.root - ), - chunk => - getLongChunkName( - chunk, - chunkGraph, - context, - delimiter, - hashFunction, - compiler.root - ), - compareChunksNatural(chunkGraph), - getUsedChunkIds(compilation), - (chunk, name) => { - chunk.id = name; - chunk.ids = [name]; - } - ); - if (unnamedChunks.length > 0) { - assignAscendingChunkIds(unnamedChunks, compilation); - } - }); - }); + apply(dependency, source, { runtimeRequirements }) { + const dep = /** @type {RequireHeaderDependency} */ (dependency); + runtimeRequirements.add(RuntimeGlobals.require); + source.replace(dep.range[0], dep.range[1] - 1, "__webpack_require__"); } -} +}; -module.exports = NamedChunkIdsPlugin; +module.exports = RequireHeaderDependency; /***/ }), -/***/ 88514: +/***/ 17046: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; @@ -89086,65 +86645,78 @@ module.exports = NamedChunkIdsPlugin; -const { compareModulesByIdentifier } = __webpack_require__(26296); -const { - getShortModuleName, - getLongModuleName, - assignNames, - getUsedModuleIds, - assignAscendingModuleIds -} = __webpack_require__(72922); +const Dependency = __webpack_require__(50384); +const Template = __webpack_require__(92066); +const makeSerializable = __webpack_require__(26522); +const ModuleDependency = __webpack_require__(80944); + +/** @typedef {import("webpack-sources").ReplaceSource} ReplaceSource */ +/** @typedef {import("../Dependency").ReferencedExport} ReferencedExport */ +/** @typedef {import("../DependencyTemplate").DependencyTemplateContext} DependencyTemplateContext */ +/** @typedef {import("../ModuleGraph")} ModuleGraph */ +/** @typedef {import("../util/runtime").RuntimeSpec} RuntimeSpec */ + +class RequireIncludeDependency extends ModuleDependency { + constructor(request, range) { + super(request); + + this.range = range; + } -/** @typedef {import("../Compiler")} Compiler */ -/** @typedef {import("../Module")} Module */ + /** + * Returns list of exports referenced by this dependency + * @param {ModuleGraph} moduleGraph module graph + * @param {RuntimeSpec} runtime the runtime for which the module is analysed + * @returns {(string[] | ReferencedExport)[]} referenced exports + */ + getReferencedExports(moduleGraph, runtime) { + // This doesn't use any export + return Dependency.NO_EXPORTS_REFERENCED; + } -class NamedModuleIdsPlugin { - constructor(options) { - this.options = options || {}; + get type() { + return "require.include"; + } + + get category() { + return "commonjs"; } +} +makeSerializable( + RequireIncludeDependency, + "webpack/lib/dependencies/RequireIncludeDependency" +); + +RequireIncludeDependency.Template = class RequireIncludeDependencyTemplate extends ( + ModuleDependency.Template +) { /** - * Apply the plugin - * @param {Compiler} compiler the compiler instance + * @param {Dependency} dependency the dependency for which the template should be applied + * @param {ReplaceSource} source the current replace source which can be modified + * @param {DependencyTemplateContext} templateContext the context object * @returns {void} */ - apply(compiler) { - const { root } = compiler; - compiler.hooks.compilation.tap("NamedModuleIdsPlugin", compilation => { - const { hashFunction } = compilation.outputOptions; - compilation.hooks.moduleIds.tap("NamedModuleIdsPlugin", modules => { - const chunkGraph = compilation.chunkGraph; - const context = this.options.context - ? this.options.context - : compiler.context; + apply(dependency, source, { runtimeTemplate }) { + const dep = /** @type {RequireIncludeDependency} */ (dependency); + const comment = runtimeTemplate.outputOptions.pathinfo + ? Template.toComment( + `require.include ${runtimeTemplate.requestShortener.shorten( + dep.request + )}` + ) + : ""; - const unnamedModules = assignNames( - Array.from(modules).filter(module => { - if (!module.needId) return false; - if (chunkGraph.getNumberOfModuleChunks(module) === 0) return false; - return chunkGraph.getModuleId(module) === null; - }), - m => getShortModuleName(m, context, root), - (m, shortName) => - getLongModuleName(shortName, m, context, hashFunction, root), - compareModulesByIdentifier, - getUsedModuleIds(compilation), - (m, name) => chunkGraph.setModuleId(m, name) - ); - if (unnamedModules.length > 0) { - assignAscendingModuleIds(unnamedModules, compilation); - } - }); - }); + source.replace(dep.range[0], dep.range[1] - 1, `undefined${comment}`); } -} +}; -module.exports = NamedModuleIdsPlugin; +module.exports = RequireIncludeDependency; /***/ }), -/***/ 18326: +/***/ 29984: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; @@ -89155,87 +86727,131 @@ module.exports = NamedModuleIdsPlugin; -const { compareChunksNatural } = __webpack_require__(26296); -const { assignAscendingChunkIds } = __webpack_require__(72922); +const WebpackError = __webpack_require__(68422); +const { + evaluateToString, + toConstantDependency +} = __webpack_require__(28723); +const makeSerializable = __webpack_require__(26522); +const RequireIncludeDependency = __webpack_require__(17046); -/** @typedef {import("../Chunk")} Chunk */ -/** @typedef {import("../Compiler")} Compiler */ -/** @typedef {import("../Module")} Module */ +module.exports = class RequireIncludeDependencyParserPlugin { + constructor(warn) { + this.warn = warn; + } + apply(parser) { + const { warn } = this; + parser.hooks.call + .for("require.include") + .tap("RequireIncludeDependencyParserPlugin", expr => { + if (expr.arguments.length !== 1) return; + const param = parser.evaluateExpression(expr.arguments[0]); + if (!param.isString()) return; -class NaturalChunkIdsPlugin { - /** - * Apply the plugin - * @param {Compiler} compiler the compiler instance - * @returns {void} - */ - apply(compiler) { - compiler.hooks.compilation.tap("NaturalChunkIdsPlugin", compilation => { - compilation.hooks.chunkIds.tap("NaturalChunkIdsPlugin", chunks => { - const chunkGraph = compilation.chunkGraph; - const compareNatural = compareChunksNatural(chunkGraph); - const chunksInNaturalOrder = Array.from(chunks).sort(compareNatural); - assignAscendingChunkIds(chunksInNaturalOrder, compilation); + if (warn) { + parser.state.module.addWarning( + new RequireIncludeDeprecationWarning(expr.loc) + ); + } + + const dep = new RequireIncludeDependency(param.string, expr.range); + dep.loc = expr.loc; + parser.state.current.addDependency(dep); + return true; }); - }); + parser.hooks.evaluateTypeof + .for("require.include") + .tap("RequireIncludePlugin", expr => { + if (warn) { + parser.state.module.addWarning( + new RequireIncludeDeprecationWarning(expr.loc) + ); + } + return evaluateToString("function")(expr); + }); + parser.hooks.typeof + .for("require.include") + .tap("RequireIncludePlugin", expr => { + if (warn) { + parser.state.module.addWarning( + new RequireIncludeDeprecationWarning(expr.loc) + ); + } + return toConstantDependency(parser, JSON.stringify("function"))(expr); + }); + } +}; + +class RequireIncludeDeprecationWarning extends WebpackError { + constructor(loc) { + super("require.include() is deprecated and will be removed soon."); + + this.name = "RequireIncludeDeprecationWarning"; + + this.loc = loc; } } -module.exports = NaturalChunkIdsPlugin; +makeSerializable( + RequireIncludeDeprecationWarning, + "webpack/lib/dependencies/RequireIncludeDependencyParserPlugin", + "RequireIncludeDeprecationWarning" +); /***/ }), -/***/ 96338: +/***/ 83683: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; /* MIT License http://www.opensource.org/licenses/mit-license.php - Author Florent Cailhol @ooflorent + Author Tobias Koppers @sokra */ -const { - compareModulesByPreOrderIndexOrIdentifier -} = __webpack_require__(26296); -const { assignAscendingModuleIds } = __webpack_require__(72922); - -/** @typedef {import("../Compiler")} Compiler */ -/** @typedef {import("../Module")} Module */ +const RequireIncludeDependency = __webpack_require__(17046); +const RequireIncludeDependencyParserPlugin = __webpack_require__(29984); -class NaturalModuleIdsPlugin { - /** - * Apply the plugin - * @param {Compiler} compiler the compiler instance - * @returns {void} - */ +class RequireIncludePlugin { apply(compiler) { - compiler.hooks.compilation.tap("NaturalModuleIdsPlugin", compilation => { - compilation.hooks.moduleIds.tap("NaturalModuleIdsPlugin", modules => { - const chunkGraph = compilation.chunkGraph; - const modulesInNaturalOrder = Array.from(modules) - .filter( - m => - m.needId && - chunkGraph.getNumberOfModuleChunks(m) > 0 && - chunkGraph.getModuleId(m) === null - ) - .sort( - compareModulesByPreOrderIndexOrIdentifier(compilation.moduleGraph) - ); - assignAscendingModuleIds(modulesInNaturalOrder, compilation); - }); - }); + compiler.hooks.compilation.tap( + "RequireIncludePlugin", + (compilation, { normalModuleFactory }) => { + compilation.dependencyFactories.set( + RequireIncludeDependency, + normalModuleFactory + ); + compilation.dependencyTemplates.set( + RequireIncludeDependency, + new RequireIncludeDependency.Template() + ); + + const handler = (parser, parserOptions) => { + if (parserOptions.requireInclude === false) return; + const warn = parserOptions.requireInclude === undefined; + + new RequireIncludeDependencyParserPlugin(warn).apply(parser); + }; + + normalModuleFactory.hooks.parser + .for("javascript/auto") + .tap("RequireIncludePlugin", handler); + normalModuleFactory.hooks.parser + .for("javascript/dynamic") + .tap("RequireIncludePlugin", handler); + } + ); } } - -module.exports = NaturalModuleIdsPlugin; +module.exports = RequireIncludePlugin; /***/ }), -/***/ 98702: +/***/ 48789: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; @@ -89246,84 +86862,54 @@ module.exports = NaturalModuleIdsPlugin; -const { compareChunksNatural } = __webpack_require__(26296); -const createSchemaValidation = __webpack_require__(77695); -const { assignAscendingChunkIds } = __webpack_require__(72922); +const makeSerializable = __webpack_require__(26522); +const ContextDependency = __webpack_require__(67840); +const ContextDependencyTemplateAsId = __webpack_require__(95080); -/** @typedef {import("../../declarations/plugins/ids/OccurrenceChunkIdsPlugin").OccurrenceChunkIdsPluginOptions} OccurrenceChunkIdsPluginOptions */ -/** @typedef {import("../Chunk")} Chunk */ -/** @typedef {import("../Compiler")} Compiler */ -/** @typedef {import("../Module")} Module */ +class RequireResolveContextDependency extends ContextDependency { + constructor(options, range, valueRange) { + super(options); -const validate = createSchemaValidation( - __webpack_require__(19311), - () => __webpack_require__(7435), - { - name: "Occurrence Order Chunk Ids Plugin", - baseDataPath: "options" + this.range = range; + this.valueRange = valueRange; } -); -class OccurrenceChunkIdsPlugin { - /** - * @param {OccurrenceChunkIdsPluginOptions=} options options object - */ - constructor(options = {}) { - validate(options); - this.options = options; + get type() { + return "amd require context"; } - /** - * Apply the plugin - * @param {Compiler} compiler the compiler instance - * @returns {void} - */ - apply(compiler) { - const prioritiseInitial = this.options.prioritiseInitial; - compiler.hooks.compilation.tap("OccurrenceChunkIdsPlugin", compilation => { - compilation.hooks.chunkIds.tap("OccurrenceChunkIdsPlugin", chunks => { - const chunkGraph = compilation.chunkGraph; + serialize(context) { + const { write } = context; - /** @type {Map} */ - const occursInInitialChunksMap = new Map(); + write(this.range); + write(this.valueRange); - const compareNatural = compareChunksNatural(chunkGraph); + super.serialize(context); + } - for (const c of chunks) { - let occurs = 0; - for (const chunkGroup of c.groupsIterable) { - for (const parent of chunkGroup.parentsIterable) { - if (parent.isInitial()) occurs++; - } - } - occursInInitialChunksMap.set(c, occurs); - } + deserialize(context) { + const { read } = context; - const chunksInOccurrenceOrder = Array.from(chunks).sort((a, b) => { - if (prioritiseInitial) { - const aEntryOccurs = occursInInitialChunksMap.get(a); - const bEntryOccurs = occursInInitialChunksMap.get(b); - if (aEntryOccurs > bEntryOccurs) return -1; - if (aEntryOccurs < bEntryOccurs) return 1; - } - const aOccurs = a.getNumberOfGroups(); - const bOccurs = b.getNumberOfGroups(); - if (aOccurs > bOccurs) return -1; - if (aOccurs < bOccurs) return 1; - return compareNatural(a, b); - }); - assignAscendingChunkIds(chunksInOccurrenceOrder, compilation); - }); - }); + this.range = read(); + this.valueRange = read(); + + super.deserialize(context); } } -module.exports = OccurrenceChunkIdsPlugin; +makeSerializable( + RequireResolveContextDependency, + "webpack/lib/dependencies/RequireResolveContextDependency" +); + +RequireResolveContextDependency.Template = ContextDependencyTemplateAsId; + +module.exports = RequireResolveContextDependency; /***/ }), -/***/ 128: +/***/ 93172: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; @@ -89334,160 +86920,126 @@ module.exports = OccurrenceChunkIdsPlugin; -const { - compareModulesByPreOrderIndexOrIdentifier -} = __webpack_require__(26296); -const createSchemaValidation = __webpack_require__(77695); -const { assignAscendingModuleIds } = __webpack_require__(72922); +const Dependency = __webpack_require__(50384); +const makeSerializable = __webpack_require__(26522); +const ModuleDependency = __webpack_require__(80944); +const ModuleDependencyAsId = __webpack_require__(35795); -/** @typedef {import("../../declarations/plugins/ids/OccurrenceModuleIdsPlugin").OccurrenceModuleIdsPluginOptions} OccurrenceModuleIdsPluginOptions */ -/** @typedef {import("../Compiler")} Compiler */ -/** @typedef {import("../Module")} Module */ -/** @typedef {import("../ModuleGraphConnection")} ModuleGraphConnection */ +/** @typedef {import("../Dependency").ReferencedExport} ReferencedExport */ +/** @typedef {import("../ModuleGraph")} ModuleGraph */ +/** @typedef {import("../util/runtime").RuntimeSpec} RuntimeSpec */ -const validate = createSchemaValidation( - __webpack_require__(4650), - () => __webpack_require__(88570), - { - name: "Occurrence Order Module Ids Plugin", - baseDataPath: "options" +class RequireResolveDependency extends ModuleDependency { + constructor(request, range) { + super(request); + + this.range = range; } -); -class OccurrenceModuleIdsPlugin { - /** - * @param {OccurrenceModuleIdsPluginOptions=} options options object - */ - constructor(options = {}) { - validate(options); - this.options = options; + get type() { + return "require.resolve"; + } + + get category() { + return "commonjs"; } /** - * Apply the plugin - * @param {Compiler} compiler the compiler instance - * @returns {void} + * Returns list of exports referenced by this dependency + * @param {ModuleGraph} moduleGraph module graph + * @param {RuntimeSpec} runtime the runtime for which the module is analysed + * @returns {(string[] | ReferencedExport)[]} referenced exports */ - apply(compiler) { - const prioritiseInitial = this.options.prioritiseInitial; - compiler.hooks.compilation.tap("OccurrenceModuleIdsPlugin", compilation => { - const moduleGraph = compilation.moduleGraph; + getReferencedExports(moduleGraph, runtime) { + // This doesn't use any export + return Dependency.NO_EXPORTS_REFERENCED; + } +} - compilation.hooks.moduleIds.tap("OccurrenceModuleIdsPlugin", modules => { - const chunkGraph = compilation.chunkGraph; +makeSerializable( + RequireResolveDependency, + "webpack/lib/dependencies/RequireResolveDependency" +); - const modulesInOccurrenceOrder = Array.from(modules).filter( - m => - m.needId && - chunkGraph.getNumberOfModuleChunks(m) > 0 && - chunkGraph.getModuleId(m) === null - ); +RequireResolveDependency.Template = ModuleDependencyAsId; - const occursInInitialChunksMap = new Map(); - const occursInAllChunksMap = new Map(); +module.exports = RequireResolveDependency; - const initialChunkChunkMap = new Map(); - const entryCountMap = new Map(); - for (const m of modulesInOccurrenceOrder) { - let initial = 0; - let entry = 0; - for (const c of chunkGraph.getModuleChunksIterable(m)) { - if (c.canBeInitial()) initial++; - if (chunkGraph.isEntryModuleInChunk(m, c)) entry++; - } - initialChunkChunkMap.set(m, initial); - entryCountMap.set(m, entry); - } - /** - * @param {Module} module module - * @returns {number} count of occurs - */ - const countOccursInEntry = module => { - let sum = 0; - for (const [ - originModule, - connections - ] of moduleGraph.getIncomingConnectionsByOriginModule(module)) { - if (!originModule) continue; - if (!connections.some(c => c.isTargetActive(undefined))) continue; - sum += initialChunkChunkMap.get(originModule); - } - return sum; - }; +/***/ }), - /** - * @param {Module} module module - * @returns {number} count of occurs - */ - const countOccurs = module => { - let sum = 0; - for (const [ - originModule, - connections - ] of moduleGraph.getIncomingConnectionsByOriginModule(module)) { - if (!originModule) continue; - const chunkModules = - chunkGraph.getNumberOfModuleChunks(originModule); - for (const c of connections) { - if (!c.isTargetActive(undefined)) continue; - if (!c.dependency) continue; - const factor = c.dependency.getNumberOfIdOccurrences(); - if (factor === 0) continue; - sum += factor * chunkModules; - } - } - return sum; - }; +/***/ 24128: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - if (prioritiseInitial) { - for (const m of modulesInOccurrenceOrder) { - const result = - countOccursInEntry(m) + - initialChunkChunkMap.get(m) + - entryCountMap.get(m); - occursInInitialChunksMap.set(m, result); - } - } +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ - for (const m of modules) { - const result = - countOccurs(m) + - chunkGraph.getNumberOfModuleChunks(m) + - entryCountMap.get(m); - occursInAllChunksMap.set(m, result); - } - const naturalCompare = compareModulesByPreOrderIndexOrIdentifier( - compilation.moduleGraph - ); - modulesInOccurrenceOrder.sort((a, b) => { - if (prioritiseInitial) { - const aEntryOccurs = occursInInitialChunksMap.get(a); - const bEntryOccurs = occursInInitialChunksMap.get(b); - if (aEntryOccurs > bEntryOccurs) return -1; - if (aEntryOccurs < bEntryOccurs) return 1; - } - const aOccurs = occursInAllChunksMap.get(a); - const bOccurs = occursInAllChunksMap.get(b); - if (aOccurs > bOccurs) return -1; - if (aOccurs < bOccurs) return 1; - return naturalCompare(a, b); - }); +const makeSerializable = __webpack_require__(26522); +const NullDependency = __webpack_require__(65845); + +/** @typedef {import("webpack-sources").ReplaceSource} ReplaceSource */ +/** @typedef {import("../Dependency")} Dependency */ +/** @typedef {import("../DependencyTemplate").DependencyTemplateContext} DependencyTemplateContext */ + +class RequireResolveHeaderDependency extends NullDependency { + constructor(range) { + super(); + + if (!Array.isArray(range)) throw new Error("range must be valid"); + + this.range = range; + } + + serialize(context) { + const { write } = context; + + write(this.range); + + super.serialize(context); + } - assignAscendingModuleIds(modulesInOccurrenceOrder, compilation); - }); - }); + static deserialize(context) { + const obj = new RequireResolveHeaderDependency(context.read()); + obj.deserialize(context); + return obj; } } -module.exports = OccurrenceModuleIdsPlugin; +makeSerializable( + RequireResolveHeaderDependency, + "webpack/lib/dependencies/RequireResolveHeaderDependency" +); + +RequireResolveHeaderDependency.Template = class RequireResolveHeaderDependencyTemplate extends ( + NullDependency.Template +) { + /** + * @param {Dependency} dependency the dependency for which the template should be applied + * @param {ReplaceSource} source the current replace source which can be modified + * @param {DependencyTemplateContext} templateContext the context object + * @returns {void} + */ + apply(dependency, source, templateContext) { + const dep = /** @type {RequireResolveHeaderDependency} */ (dependency); + source.replace(dep.range[0], dep.range[1] - 1, "/*require.resolve*/"); + } + + applyAsTemplateArgument(name, dep, source) { + source.replace(dep.range[0], dep.range[1] - 1, "/*require.resolve*/"); + } +}; + +module.exports = RequireResolveHeaderDependency; /***/ }), -/***/ 48169: +/***/ 75941: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; @@ -89498,570 +87050,155 @@ module.exports = OccurrenceModuleIdsPlugin; -const util = __webpack_require__(31669); -const memoize = __webpack_require__(84297); - -/** @typedef {import("../declarations/WebpackOptions").Entry} Entry */ -/** @typedef {import("../declarations/WebpackOptions").EntryNormalized} EntryNormalized */ -/** @typedef {import("../declarations/WebpackOptions").EntryObject} EntryObject */ -/** @typedef {import("../declarations/WebpackOptions").LibraryOptions} LibraryOptions */ -/** @typedef {import("../declarations/WebpackOptions").ModuleOptions} ModuleOptions */ -/** @typedef {import("../declarations/WebpackOptions").ResolveOptions} ResolveOptions */ -/** @typedef {import("../declarations/WebpackOptions").RuleSetCondition} RuleSetCondition */ -/** @typedef {import("../declarations/WebpackOptions").RuleSetConditionAbsolute} RuleSetConditionAbsolute */ -/** @typedef {import("../declarations/WebpackOptions").RuleSetRule} RuleSetRule */ -/** @typedef {import("../declarations/WebpackOptions").RuleSetUse} RuleSetUse */ -/** @typedef {import("../declarations/WebpackOptions").RuleSetUseItem} RuleSetUseItem */ -/** @typedef {import("../declarations/WebpackOptions").WebpackOptions} Configuration */ -/** @typedef {import("../declarations/WebpackOptions").WebpackOptionsNormalized} WebpackOptionsNormalized */ -/** @typedef {import("../declarations/WebpackOptions").WebpackPluginFunction} WebpackPluginFunction */ -/** @typedef {import("../declarations/WebpackOptions").WebpackPluginInstance} WebpackPluginInstance */ -/** @typedef {import("./Compilation").Asset} Asset */ -/** @typedef {import("./Compilation").AssetInfo} AssetInfo */ -/** @typedef {import("./MultiStats")} MultiStats */ -/** @typedef {import("./Parser").ParserState} ParserState */ -/** @typedef {import("./Watching")} Watching */ -/** @typedef {import("./stats/DefaultStatsFactoryPlugin").StatsAsset} StatsAsset */ -/** @typedef {import("./stats/DefaultStatsFactoryPlugin").StatsChunk} StatsChunk */ -/** @typedef {import("./stats/DefaultStatsFactoryPlugin").StatsChunkGroup} StatsChunkGroup */ -/** @typedef {import("./stats/DefaultStatsFactoryPlugin").StatsChunkOrigin} StatsChunkOrigin */ -/** @typedef {import("./stats/DefaultStatsFactoryPlugin").StatsCompilation} StatsCompilation */ -/** @typedef {import("./stats/DefaultStatsFactoryPlugin").StatsError} StatsError */ -/** @typedef {import("./stats/DefaultStatsFactoryPlugin").StatsLogging} StatsLogging */ -/** @typedef {import("./stats/DefaultStatsFactoryPlugin").StatsLoggingEntry} StatsLoggingEntry */ -/** @typedef {import("./stats/DefaultStatsFactoryPlugin").StatsModule} StatsModule */ -/** @typedef {import("./stats/DefaultStatsFactoryPlugin").StatsModuleIssuer} StatsModuleIssuer */ -/** @typedef {import("./stats/DefaultStatsFactoryPlugin").StatsModuleReason} StatsModuleReason */ -/** @typedef {import("./stats/DefaultStatsFactoryPlugin").StatsModuleTraceDependency} StatsModuleTraceDependency */ -/** @typedef {import("./stats/DefaultStatsFactoryPlugin").StatsModuleTraceItem} StatsModuleTraceItem */ -/** @typedef {import("./stats/DefaultStatsFactoryPlugin").StatsProfile} StatsProfile */ +const makeSerializable = __webpack_require__(26522); +const NullDependency = __webpack_require__(65845); -/** - * @template {Function} T - * @param {function(): T} factory factory function - * @returns {T} function - */ -const lazyFunction = factory => { - const fac = memoize(factory); - const f = /** @type {any} */ ( - (...args) => { - return fac()(...args); - } - ); - return /** @type {T} */ (f); -}; +/** @typedef {import("webpack-sources").ReplaceSource} ReplaceSource */ +/** @typedef {import("../ChunkGraph")} ChunkGraph */ +/** @typedef {import("../Dependency")} Dependency */ +/** @typedef {import("../Dependency").UpdateHashContext} UpdateHashContext */ +/** @typedef {import("../DependencyTemplate").DependencyTemplateContext} DependencyTemplateContext */ +/** @typedef {import("../ModuleGraph")} ModuleGraph */ +/** @typedef {import("../util/Hash")} Hash */ -/** - * @template A - * @template B - * @param {A} obj input a - * @param {B} exports input b - * @returns {A & B} merged - */ -const mergeExports = (obj, exports) => { - const descriptors = Object.getOwnPropertyDescriptors(exports); - for (const name of Object.keys(descriptors)) { - const descriptor = descriptors[name]; - if (descriptor.get) { - const fn = descriptor.get; - Object.defineProperty(obj, name, { - configurable: false, - enumerable: true, - get: memoize(fn) - }); - } else if (typeof descriptor.value === "object") { - Object.defineProperty(obj, name, { - configurable: false, - enumerable: true, - writable: false, - value: mergeExports({}, descriptor.value) - }); - } else { - throw new Error( - "Exposed values must be either a getter or an nested object" - ); - } +class RuntimeRequirementsDependency extends NullDependency { + /** + * @param {string[]} runtimeRequirements runtime requirements + */ + constructor(runtimeRequirements) { + super(); + this.runtimeRequirements = new Set(runtimeRequirements); + this._hashUpdate = undefined; } - return /** @type {A & B} */ (Object.freeze(obj)); -}; - -const fn = lazyFunction(() => __webpack_require__(86128)); -module.exports = mergeExports(fn, { - get webpack() { - return __webpack_require__(86128); - }, - get validate() { - const webpackOptionsSchemaCheck = __webpack_require__(97220); - const getRealValidate = memoize(() => { - const validateSchema = __webpack_require__(55959); - const webpackOptionsSchema = __webpack_require__(1863); - return options => validateSchema(webpackOptionsSchema, options); - }); - return options => { - if (!webpackOptionsSchemaCheck(options)) getRealValidate()(options); - }; - }, - get validateSchema() { - const validateSchema = __webpack_require__(55959); - return validateSchema; - }, - get version() { - return /** @type {string} */ (__webpack_require__(87168)/* .version */ .i8); - }, - - get cli() { - return __webpack_require__(26040); - }, - get AutomaticPrefetchPlugin() { - return __webpack_require__(51714); - }, - get AsyncDependenciesBlock() { - return __webpack_require__(11315); - }, - get BannerPlugin() { - return __webpack_require__(45480); - }, - get Cache() { - return __webpack_require__(99453); - }, - get Chunk() { - return __webpack_require__(65574); - }, - get ChunkGraph() { - return __webpack_require__(97860); - }, - get CleanPlugin() { - return __webpack_require__(49129); - }, - get Compilation() { - return __webpack_require__(59622); - }, - get Compiler() { - return __webpack_require__(11777); - }, - get ConcatenationScope() { - return __webpack_require__(14067); - }, - get ContextExclusionPlugin() { - return __webpack_require__(30480); - }, - get ContextReplacementPlugin() { - return __webpack_require__(21542); - }, - get DefinePlugin() { - return __webpack_require__(46754); - }, - get DelegatedPlugin() { - return __webpack_require__(48248); - }, - get Dependency() { - return __webpack_require__(50384); - }, - get DllPlugin() { - return __webpack_require__(15232); - }, - get DllReferencePlugin() { - return __webpack_require__(8904); - }, - get DynamicEntryPlugin() { - return __webpack_require__(60670); - }, - get EntryOptionPlugin() { - return __webpack_require__(59526); - }, - get EntryPlugin() { - return __webpack_require__(82430); - }, - get EnvironmentPlugin() { - return __webpack_require__(43755); - }, - get EvalDevToolModulePlugin() { - return __webpack_require__(4125); - }, - get EvalSourceMapDevToolPlugin() { - return __webpack_require__(42053); - }, - get ExternalModule() { - return __webpack_require__(89805); - }, - get ExternalsPlugin() { - return __webpack_require__(361); - }, - get Generator() { - return __webpack_require__(1826); - }, - get HotUpdateChunk() { - return __webpack_require__(39222); - }, - get HotModuleReplacementPlugin() { - return __webpack_require__(616); - }, - get IgnorePlugin() { - return __webpack_require__(8098); - }, - get JavascriptModulesPlugin() { - return util.deprecate( - () => __webpack_require__(76767), - "webpack.JavascriptModulesPlugin has moved to webpack.javascript.JavascriptModulesPlugin", - "DEP_WEBPACK_JAVASCRIPT_MODULES_PLUGIN" - )(); - }, - get LibManifestPlugin() { - return __webpack_require__(30711); - }, - get LibraryTemplatePlugin() { - return util.deprecate( - () => __webpack_require__(81735), - "webpack.LibraryTemplatePlugin is deprecated and has been replaced by compilation.outputOptions.library or compilation.addEntry + passing a library option", - "DEP_WEBPACK_LIBRARY_TEMPLATE_PLUGIN" - )(); - }, - get LoaderOptionsPlugin() { - return __webpack_require__(73047); - }, - get LoaderTargetPlugin() { - return __webpack_require__(94834); - }, - get Module() { - return __webpack_require__(85887); - }, - get ModuleFilenameHelpers() { - return __webpack_require__(80295); - }, - get ModuleGraph() { - return __webpack_require__(20258); - }, - get ModuleGraphConnection() { - return __webpack_require__(94144); - }, - get NoEmitOnErrorsPlugin() { - return __webpack_require__(70760); - }, - get NormalModule() { - return __webpack_require__(11026); - }, - get NormalModuleReplacementPlugin() { - return __webpack_require__(12747); - }, - get MultiCompiler() { - return __webpack_require__(73663); - }, - get Parser() { - return __webpack_require__(68214); - }, - get PrefetchPlugin() { - return __webpack_require__(34652); - }, - get ProgressPlugin() { - return __webpack_require__(41306); - }, - get ProvidePlugin() { - return __webpack_require__(18067); - }, - get RuntimeGlobals() { - return __webpack_require__(49404); - }, - get RuntimeModule() { - return __webpack_require__(61439); - }, - get SingleEntryPlugin() { - return util.deprecate( - () => __webpack_require__(82430), - "SingleEntryPlugin was renamed to EntryPlugin", - "DEP_WEBPACK_SINGLE_ENTRY_PLUGIN" - )(); - }, - get SourceMapDevToolPlugin() { - return __webpack_require__(79917); - }, - get Stats() { - return __webpack_require__(87797); - }, - get Template() { - return __webpack_require__(92066); - }, - get UsageState() { - return __webpack_require__(4295).UsageState; - }, - get WatchIgnorePlugin() { - return __webpack_require__(90187); - }, - get WebpackError() { - return __webpack_require__(68422); - }, - get WebpackOptionsApply() { - return __webpack_require__(44137); - }, - get WebpackOptionsDefaulter() { - return util.deprecate( - () => __webpack_require__(547), - "webpack.WebpackOptionsDefaulter is deprecated and has been replaced by webpack.config.getNormalizedWebpackOptions and webpack.config.applyWebpackOptionsDefaults", - "DEP_WEBPACK_OPTIONS_DEFAULTER" - )(); - }, - // TODO webpack 6 deprecate - get WebpackOptionsValidationError() { - return __webpack_require__(79286).ValidationError; - }, - get ValidationError() { - return __webpack_require__(79286).ValidationError; - }, - - cache: { - get MemoryCachePlugin() { - return __webpack_require__(4045); - } - }, - - config: { - get getNormalizedWebpackOptions() { - return __webpack_require__(52975).getNormalizedWebpackOptions; - }, - get applyWebpackOptionsDefaults() { - return __webpack_require__(27057).applyWebpackOptionsDefaults; - } - }, - dependencies: { - get ModuleDependency() { - return __webpack_require__(80944); - }, - get ConstDependency() { - return __webpack_require__(60864); - }, - get NullDependency() { - return __webpack_require__(65845); + /** + * Update the hash + * @param {Hash} hash hash to be updated + * @param {UpdateHashContext} context context + * @returns {void} + */ + updateHash(hash, context) { + if (this._hashUpdate === undefined) { + this._hashUpdate = Array.from(this.runtimeRequirements).join() + ""; } - }, + hash.update(this._hashUpdate); + } - ids: { - get ChunkModuleIdRangePlugin() { - return __webpack_require__(7047); - }, - get NaturalModuleIdsPlugin() { - return __webpack_require__(96338); - }, - get OccurrenceModuleIdsPlugin() { - return __webpack_require__(128); - }, - get NamedModuleIdsPlugin() { - return __webpack_require__(88514); - }, - get DeterministicChunkIdsPlugin() { - return __webpack_require__(64801); - }, - get DeterministicModuleIdsPlugin() { - return __webpack_require__(84965); - }, - get NamedChunkIdsPlugin() { - return __webpack_require__(30483); - }, - get OccurrenceChunkIdsPlugin() { - return __webpack_require__(98702); - }, - get HashedModuleIdsPlugin() { - return __webpack_require__(83635); - } - }, + serialize(context) { + const { write } = context; + write(this.runtimeRequirements); + super.serialize(context); + } - javascript: { - get EnableChunkLoadingPlugin() { - return __webpack_require__(34726); - }, - get JavascriptModulesPlugin() { - return __webpack_require__(76767); - }, - get JavascriptParser() { - return __webpack_require__(42060); - } - }, + deserialize(context) { + const { read } = context; + this.runtimeRequirements = read(); + super.deserialize(context); + } +} - optimize: { - get AggressiveMergingPlugin() { - return __webpack_require__(8239); - }, - get AggressiveSplittingPlugin() { - return util.deprecate( - () => __webpack_require__(10055), - "AggressiveSplittingPlugin is deprecated in favor of SplitChunksPlugin", - "DEP_WEBPACK_AGGRESSIVE_SPLITTING_PLUGIN" - )(); - }, - get InnerGraph() { - return __webpack_require__(92886); - }, - get LimitChunkCountPlugin() { - return __webpack_require__(22119); - }, - get MinChunkSizePlugin() { - return __webpack_require__(85813); - }, - get ModuleConcatenationPlugin() { - return __webpack_require__(29585); - }, - get RealContentHashPlugin() { - return __webpack_require__(6669); - }, - get RuntimeChunkPlugin() { - return __webpack_require__(23821); - }, - get SideEffectsFlagPlugin() { - return __webpack_require__(47844); - }, - get SplitChunksPlugin() { - return __webpack_require__(57073); - } - }, +makeSerializable( + RuntimeRequirementsDependency, + "webpack/lib/dependencies/RuntimeRequirementsDependency" +); - runtime: { - get GetChunkFilenameRuntimeModule() { - return __webpack_require__(53288); - }, - get LoadScriptRuntimeModule() { - return __webpack_require__(80647); +RuntimeRequirementsDependency.Template = class RuntimeRequirementsDependencyTemplate extends ( + NullDependency.Template +) { + /** + * @param {Dependency} dependency the dependency for which the template should be applied + * @param {ReplaceSource} source the current replace source which can be modified + * @param {DependencyTemplateContext} templateContext the context object + * @returns {void} + */ + apply(dependency, source, { runtimeRequirements }) { + const dep = /** @type {RuntimeRequirementsDependency} */ (dependency); + for (const req of dep.runtimeRequirements) { + runtimeRequirements.add(req); } - }, + } +}; - prefetch: { - get ChunkPrefetchPreloadPlugin() { - return __webpack_require__(17839); - } - }, +module.exports = RuntimeRequirementsDependency; - web: { - get FetchCompileAsyncWasmPlugin() { - return __webpack_require__(37118); - }, - get FetchCompileWasmPlugin() { - return __webpack_require__(89728); - }, - get JsonpChunkLoadingRuntimeModule() { - return __webpack_require__(66032); - }, - get JsonpTemplatePlugin() { - return __webpack_require__(45968); - } - }, - webworker: { - get WebWorkerTemplatePlugin() { - return __webpack_require__(9460); - } - }, +/***/ }), - node: { - get NodeEnvironmentPlugin() { - return __webpack_require__(38857); - }, - get NodeSourcePlugin() { - return __webpack_require__(13313); - }, - get NodeTargetPlugin() { - return __webpack_require__(28037); - }, - get NodeTemplatePlugin() { - return __webpack_require__(47087); - }, - get ReadFileCompileWasmPlugin() { - return __webpack_require__(98724); - } - }, +/***/ 67967: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - electron: { - get ElectronTargetPlugin() { - return __webpack_require__(88362); - } - }, +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ - wasm: { - get AsyncWebAssemblyModulesPlugin() { - return __webpack_require__(13804); - } - }, - library: { - get AbstractLibraryPlugin() { - return __webpack_require__(94051); - }, - get EnableLibraryPlugin() { - return __webpack_require__(35613); - } - }, - container: { - get ContainerPlugin() { - return __webpack_require__(20962); - }, - get ContainerReferencePlugin() { - return __webpack_require__(17813); - }, - get ModuleFederationPlugin() { - return __webpack_require__(22814); - }, - get scope() { - return __webpack_require__(56084).scope; - } - }, +const makeSerializable = __webpack_require__(26522); +const NullDependency = __webpack_require__(65845); - sharing: { - get ConsumeSharedPlugin() { - return __webpack_require__(19984); - }, - get ProvideSharedPlugin() { - return __webpack_require__(42672); - }, - get SharePlugin() { - return __webpack_require__(25790); - }, - get scope() { - return __webpack_require__(56084).scope; - } - }, +/** @typedef {import("../ChunkGraph")} ChunkGraph */ +/** @typedef {import("../Dependency").ExportSpec} ExportSpec */ +/** @typedef {import("../Dependency").ExportsSpec} ExportsSpec */ +/** @typedef {import("../Dependency").UpdateHashContext} UpdateHashContext */ +/** @typedef {import("../ModuleGraph")} ModuleGraph */ +/** @typedef {import("../util/Hash")} Hash */ - debug: { - get ProfilingPlugin() { - return __webpack_require__(52034); - } - }, +class StaticExportsDependency extends NullDependency { + /** + * @param {string[] | true} exports export names + * @param {boolean} canMangle true, if mangling exports names is allowed + */ + constructor(exports, canMangle) { + super(); + this.exports = exports; + this.canMangle = canMangle; + } - util: { - get createHash() { - return __webpack_require__(24123); - }, - get comparators() { - return __webpack_require__(26296); - }, - get runtime() { - return __webpack_require__(19655); - }, - get serialization() { - return __webpack_require__(99551); - }, - get cleverMerge() { - return __webpack_require__(11217).cachedCleverMerge; - }, - get LazySet() { - return __webpack_require__(59534); - } - }, + get type() { + return "static exports"; + } - get sources() { - return __webpack_require__(96192); - }, + /** + * Returns the exported names + * @param {ModuleGraph} moduleGraph module graph + * @returns {ExportsSpec | undefined} export names + */ + getExports(moduleGraph) { + return { + exports: this.exports, + canMangle: this.canMangle, + dependencies: undefined + }; + } - experiments: { - schemes: { - get HttpUriPlugin() { - return __webpack_require__(34747); - } - } + serialize(context) { + const { write } = context; + write(this.exports); + write(this.canMangle); + super.serialize(context); } -}); + + deserialize(context) { + const { read } = context; + this.exports = read(); + this.canMangle = read(); + super.deserialize(context); + } +} + +makeSerializable( + StaticExportsDependency, + "webpack/lib/dependencies/StaticExportsDependency" +); + +module.exports = StaticExportsDependency; /***/ }), -/***/ 86189: +/***/ 88768: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; @@ -90072,646 +87209,557 @@ module.exports = mergeExports(fn, { -const { ConcatSource, PrefixSource, RawSource } = __webpack_require__(96192); -const { RuntimeGlobals } = __webpack_require__(48169); -const HotUpdateChunk = __webpack_require__(39222); -const Template = __webpack_require__(92066); -const { getCompilationHooks } = __webpack_require__(76767); +const RuntimeGlobals = __webpack_require__(49404); +const WebpackError = __webpack_require__(68422); const { - generateEntryStartup, - updateHashForEntryStartup -} = __webpack_require__(30951); + evaluateToString, + expressionIsUnsupported, + toConstantDependency +} = __webpack_require__(28723); +const makeSerializable = __webpack_require__(26522); +const ConstDependency = __webpack_require__(60864); +const SystemRuntimeModule = __webpack_require__(45964); /** @typedef {import("../Compiler")} Compiler */ -class ArrayPushCallbackChunkFormatPlugin { +class SystemPlugin { /** * Apply the plugin * @param {Compiler} compiler the compiler instance * @returns {void} */ apply(compiler) { - compiler.hooks.thisCompilation.tap( - "ArrayPushCallbackChunkFormatPlugin", - compilation => { - compilation.hooks.additionalChunkRuntimeRequirements.tap( - "ArrayPushCallbackChunkFormatPlugin", - (chunk, set, { chunkGraph }) => { - if (chunk.hasRuntime()) return; - if (chunkGraph.getNumberOfEntryModules(chunk) > 0) { - set.add(RuntimeGlobals.onChunksLoaded); - set.add(RuntimeGlobals.require); - } - set.add(RuntimeGlobals.chunkCallback); + compiler.hooks.compilation.tap( + "SystemPlugin", + (compilation, { normalModuleFactory }) => { + compilation.hooks.runtimeRequirementInModule + .for(RuntimeGlobals.system) + .tap("SystemPlugin", (module, set) => { + set.add(RuntimeGlobals.requireScope); + }); + + compilation.hooks.runtimeRequirementInTree + .for(RuntimeGlobals.system) + .tap("SystemPlugin", (chunk, set) => { + compilation.addRuntimeModule(chunk, new SystemRuntimeModule()); + }); + + const handler = (parser, parserOptions) => { + if (parserOptions.system === undefined || !parserOptions.system) { + return; } - ); - const hooks = getCompilationHooks(compilation); - hooks.renderChunk.tap( - "ArrayPushCallbackChunkFormatPlugin", - (modules, renderContext) => { - const { chunk, chunkGraph, runtimeTemplate } = renderContext; - const hotUpdateChunk = - chunk instanceof HotUpdateChunk ? chunk : null; - const globalObject = runtimeTemplate.outputOptions.globalObject; - const source = new ConcatSource(); - const runtimeModules = - chunkGraph.getChunkRuntimeModulesInOrder(chunk); - if (hotUpdateChunk) { - const hotUpdateGlobal = - runtimeTemplate.outputOptions.hotUpdateGlobal; - source.add( - `${globalObject}[${JSON.stringify(hotUpdateGlobal)}](` - ); - source.add(`${JSON.stringify(chunk.id)},`); - source.add(modules); - if (runtimeModules.length > 0) { - source.add(",\n"); - const runtimePart = Template.renderChunkRuntimeModules( - runtimeModules, - renderContext - ); - source.add(runtimePart); - } - source.add(")"); - } else { - const chunkLoadingGlobal = - runtimeTemplate.outputOptions.chunkLoadingGlobal; - source.add( - `(${globalObject}[${JSON.stringify( - chunkLoadingGlobal - )}] = ${globalObject}[${JSON.stringify( - chunkLoadingGlobal - )}] || []).push([` - ); - source.add(`${JSON.stringify(chunk.ids)},`); - source.add(modules); - const entries = Array.from( - chunkGraph.getChunkEntryModulesWithChunkGroupIterable(chunk) + + const setNotSupported = name => { + parser.hooks.evaluateTypeof + .for(name) + .tap("SystemPlugin", evaluateToString("undefined")); + parser.hooks.expression + .for(name) + .tap( + "SystemPlugin", + expressionIsUnsupported( + parser, + name + " is not supported by webpack." + ) ); - if (runtimeModules.length > 0 || entries.length > 0) { - const runtime = new ConcatSource( - (runtimeTemplate.supportsArrowFunction() - ? "__webpack_require__ =>" - : "function(__webpack_require__)") + - " { // webpackRuntimeModules\n" - ); - if (runtimeModules.length > 0) { - runtime.add( - Template.renderRuntimeModules(runtimeModules, { - ...renderContext, - codeGenerationResults: compilation.codeGenerationResults - }) - ); - } - if (entries.length > 0) { - const startupSource = new RawSource( - generateEntryStartup( - chunkGraph, - runtimeTemplate, - entries, - chunk, - true - ) - ); - runtime.add( - hooks.renderStartup.call( - startupSource, - entries[entries.length - 1][0], - { - ...renderContext, - inlined: false - } - ) - ); - if ( - chunkGraph - .getChunkRuntimeRequirements(chunk) - .has(RuntimeGlobals.returnExportsFromRuntime) - ) { - runtime.add("return __webpack_exports__;\n"); - } - } - runtime.add("}\n"); - source.add(",\n"); - source.add(new PrefixSource("/******/ ", runtime)); - } - source.add("])"); - } - return source; - } - ); - hooks.chunkHash.tap( - "ArrayPushCallbackChunkFormatPlugin", - (chunk, hash, { chunkGraph, runtimeTemplate }) => { - if (chunk.hasRuntime()) return; - hash.update( - `ArrayPushCallbackChunkFormatPlugin1${runtimeTemplate.outputOptions.chunkLoadingGlobal}${runtimeTemplate.outputOptions.hotUpdateGlobal}${runtimeTemplate.outputOptions.globalObject}` + }; + + parser.hooks.typeof + .for("System.import") + .tap( + "SystemPlugin", + toConstantDependency(parser, JSON.stringify("function")) ); - const entries = Array.from( - chunkGraph.getChunkEntryModulesWithChunkGroupIterable(chunk) + parser.hooks.evaluateTypeof + .for("System.import") + .tap("SystemPlugin", evaluateToString("function")); + parser.hooks.typeof + .for("System") + .tap( + "SystemPlugin", + toConstantDependency(parser, JSON.stringify("object")) ); - updateHashForEntryStartup(hash, chunkGraph, entries, chunk); - } - ); + parser.hooks.evaluateTypeof + .for("System") + .tap("SystemPlugin", evaluateToString("object")); + + setNotSupported("System.set"); + setNotSupported("System.get"); + setNotSupported("System.register"); + + parser.hooks.expression.for("System").tap("SystemPlugin", expr => { + const dep = new ConstDependency(RuntimeGlobals.system, expr.range, [ + RuntimeGlobals.system + ]); + dep.loc = expr.loc; + parser.state.module.addPresentationalDependency(dep); + return true; + }); + + parser.hooks.call.for("System.import").tap("SystemPlugin", expr => { + parser.state.module.addWarning( + new SystemImportDeprecationWarning(expr.loc) + ); + + return parser.hooks.importCall.call({ + type: "ImportExpression", + source: expr.arguments[0], + loc: expr.loc, + range: expr.range + }); + }); + }; + + normalModuleFactory.hooks.parser + .for("javascript/auto") + .tap("SystemPlugin", handler); + normalModuleFactory.hooks.parser + .for("javascript/dynamic") + .tap("SystemPlugin", handler); } ); } } -module.exports = ArrayPushCallbackChunkFormatPlugin; - +class SystemImportDeprecationWarning extends WebpackError { + constructor(loc) { + super( + "System.import() is deprecated and will be removed soon. Use import() instead.\n" + + "For more info visit https://webpack.js.org/guides/code-splitting/" + ); -/***/ }), + this.name = "SystemImportDeprecationWarning"; -/***/ 2412: -/***/ (function(module) { + this.loc = loc; + } +} -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ +makeSerializable( + SystemImportDeprecationWarning, + "webpack/lib/dependencies/SystemPlugin", + "SystemImportDeprecationWarning" +); +module.exports = SystemPlugin; +module.exports.SystemImportDeprecationWarning = SystemImportDeprecationWarning; -/** @typedef {import("estree").Node} EsTreeNode */ -/** @typedef {import("./JavascriptParser").VariableInfoInterface} VariableInfoInterface */ +/***/ }), -const TypeUnknown = 0; -const TypeUndefined = 1; -const TypeNull = 2; -const TypeString = 3; -const TypeNumber = 4; -const TypeBoolean = 5; -const TypeRegExp = 6; -const TypeConditional = 7; -const TypeArray = 8; -const TypeConstArray = 9; -const TypeIdentifier = 10; -const TypeWrapped = 11; -const TypeTemplateString = 12; -const TypeBigInt = 13; +/***/ 45964: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { -class BasicEvaluatedExpression { - constructor() { - this.type = TypeUnknown; - /** @type {[number, number]} */ - this.range = undefined; - /** @type {boolean} */ - this.falsy = false; - /** @type {boolean} */ - this.truthy = false; - /** @type {boolean | undefined} */ - this.nullish = undefined; - /** @type {boolean} */ - this.sideEffects = true; - /** @type {boolean | undefined} */ - this.bool = undefined; - /** @type {number | undefined} */ - this.number = undefined; - /** @type {bigint | undefined} */ - this.bigint = undefined; - /** @type {RegExp | undefined} */ - this.regExp = undefined; - /** @type {string | undefined} */ - this.string = undefined; - /** @type {BasicEvaluatedExpression[] | undefined} */ - this.quasis = undefined; - /** @type {BasicEvaluatedExpression[] | undefined} */ - this.parts = undefined; - /** @type {any[] | undefined} */ - this.array = undefined; - /** @type {BasicEvaluatedExpression[] | undefined} */ - this.items = undefined; - /** @type {BasicEvaluatedExpression[] | undefined} */ - this.options = undefined; - /** @type {BasicEvaluatedExpression | undefined} */ - this.prefix = undefined; - /** @type {BasicEvaluatedExpression | undefined} */ - this.postfix = undefined; - this.wrappedInnerExpressions = undefined; - /** @type {string | undefined} */ - this.identifier = undefined; - /** @type {VariableInfoInterface} */ - this.rootInfo = undefined; - /** @type {() => string[]} */ - this.getMembers = undefined; - /** @type {EsTreeNode} */ - this.expression = undefined; - } +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Florent Cailhol @ooflorent +*/ - isUnknown() { - return this.type === TypeUnknown; - } - isNull() { - return this.type === TypeNull; - } - isUndefined() { - return this.type === TypeUndefined; - } +const RuntimeGlobals = __webpack_require__(49404); +const RuntimeModule = __webpack_require__(61439); +const Template = __webpack_require__(92066); - isString() { - return this.type === TypeString; +class SystemRuntimeModule extends RuntimeModule { + constructor() { + super("system"); } - isNumber() { - return this.type === TypeNumber; + /** + * @returns {string} runtime code + */ + generate() { + return Template.asString([ + `${RuntimeGlobals.system} = {`, + Template.indent([ + "import: function () {", + Template.indent( + "throw new Error('System.import cannot be used indirectly');" + ), + "}" + ]), + "};" + ]); } +} - isBigInt() { - return this.type === TypeBigInt; - } +module.exports = SystemRuntimeModule; - isBoolean() { - return this.type === TypeBoolean; - } - isRegExp() { - return this.type === TypeRegExp; - } +/***/ }), - isConditional() { - return this.type === TypeConditional; - } +/***/ 30990: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - isArray() { - return this.type === TypeArray; - } +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Ivan Kopeykin @vankop +*/ - isConstArray() { - return this.type === TypeConstArray; - } - isIdentifier() { - return this.type === TypeIdentifier; - } - isWrapped() { - return this.type === TypeWrapped; - } +const RuntimeGlobals = __webpack_require__(49404); +const { + getDependencyUsedByExportsCondition +} = __webpack_require__(92886); +const makeSerializable = __webpack_require__(26522); +const memoize = __webpack_require__(84297); +const ModuleDependency = __webpack_require__(80944); - isTemplateString() { - return this.type === TypeTemplateString; - } +/** @typedef {import("webpack-sources").ReplaceSource} ReplaceSource */ +/** @typedef {import("../ChunkGraph")} ChunkGraph */ +/** @typedef {import("../Dependency")} Dependency */ +/** @typedef {import("../Dependency").UpdateHashContext} UpdateHashContext */ +/** @typedef {import("../DependencyTemplate").DependencyTemplateContext} DependencyTemplateContext */ +/** @typedef {import("../Module")} Module */ +/** @typedef {import("../ModuleGraph")} ModuleGraph */ +/** @typedef {import("../ModuleGraphConnection")} ModuleGraphConnection */ +/** @typedef {import("../ModuleGraphConnection").ConnectionState} ConnectionState */ +/** @typedef {import("../util/Hash")} Hash */ +/** @typedef {import("../util/runtime").RuntimeSpec} RuntimeSpec */ + +const getRawModule = memoize(() => __webpack_require__(82329)); +class URLDependency extends ModuleDependency { /** - * Is expression a primitive or an object type value? - * @returns {boolean | undefined} true: primitive type, false: object type, undefined: unknown/runtime-defined + * @param {string} request request + * @param {[number, number]} range range of the arguments of new URL( |> ... <| ) + * @param {[number, number]} outerRange range of the full |> new URL(...) <| + * @param {boolean=} relative use relative urls instead of absolute with base uri */ - isPrimitiveType() { - switch (this.type) { - case TypeUndefined: - case TypeNull: - case TypeString: - case TypeNumber: - case TypeBoolean: - case TypeBigInt: - case TypeWrapped: - case TypeTemplateString: - return true; - case TypeRegExp: - case TypeArray: - case TypeConstArray: - return false; - default: - return undefined; - } + constructor(request, range, outerRange, relative) { + super(request); + this.range = range; + this.outerRange = outerRange; + this.relative = relative || false; + /** @type {Set | boolean} */ + this.usedByExports = undefined; } - /** - * Is expression a runtime or compile-time value? - * @returns {boolean} true: compile time value, false: runtime value - */ - isCompileTimeValue() { - switch (this.type) { - case TypeUndefined: - case TypeNull: - case TypeString: - case TypeNumber: - case TypeBoolean: - case TypeRegExp: - case TypeConstArray: - case TypeBigInt: - return true; - default: - return false; - } + get type() { + return "new URL()"; + } + + get category() { + return "url"; } /** - * Gets the compile-time value of the expression - * @returns {any} the javascript value + * @param {ModuleGraph} moduleGraph module graph + * @returns {null | false | function(ModuleGraphConnection, RuntimeSpec): ConnectionState} function to determine if the connection is active */ - asCompileTimeValue() { - switch (this.type) { - case TypeUndefined: - return undefined; - case TypeNull: - return null; - case TypeString: - return this.string; - case TypeNumber: - return this.number; - case TypeBoolean: - return this.bool; - case TypeRegExp: - return this.regExp; - case TypeConstArray: - return this.array; - case TypeBigInt: - return this.bigint; - default: - throw new Error( - "asCompileTimeValue must only be called for compile-time values" - ); - } + getCondition(moduleGraph) { + return getDependencyUsedByExportsCondition( + this, + this.usedByExports, + moduleGraph + ); } - isTruthy() { - return this.truthy; + /** + * @param {string} context context directory + * @returns {Module} a module + */ + createIgnoredModule(context) { + const RawModule = getRawModule(); + return new RawModule( + 'module.exports = "data:,";', + `ignored-asset`, + `(ignored asset)`, + new Set([RuntimeGlobals.module]) + ); } - isFalsy() { - return this.falsy; + serialize(context) { + const { write } = context; + write(this.outerRange); + write(this.relative); + write(this.usedByExports); + super.serialize(context); } - isNullish() { - return this.nullish; + deserialize(context) { + const { read } = context; + this.outerRange = read(); + this.relative = read(); + this.usedByExports = read(); + super.deserialize(context); } +} +URLDependency.Template = class URLDependencyTemplate extends ( + ModuleDependency.Template +) { /** - * Can this expression have side effects? - * @returns {boolean} false: never has side effects + * @param {Dependency} dependency the dependency for which the template should be applied + * @param {ReplaceSource} source the current replace source which can be modified + * @param {DependencyTemplateContext} templateContext the context object + * @returns {void} */ - couldHaveSideEffects() { - return this.sideEffects; - } - - asBool() { - if (this.truthy) return true; - if (this.falsy || this.nullish) return false; - if (this.isBoolean()) return this.bool; - if (this.isNull()) return false; - if (this.isUndefined()) return false; - if (this.isString()) return this.string !== ""; - if (this.isNumber()) return this.number !== 0; - if (this.isBigInt()) return this.bigint !== BigInt(0); - if (this.isRegExp()) return true; - if (this.isArray()) return true; - if (this.isConstArray()) return true; - if (this.isWrapped()) { - return (this.prefix && this.prefix.asBool()) || - (this.postfix && this.postfix.asBool()) - ? true - : undefined; + apply(dependency, source, templateContext) { + const { + chunkGraph, + moduleGraph, + runtimeRequirements, + runtimeTemplate, + runtime + } = templateContext; + const dep = /** @type {URLDependency} */ (dependency); + const connection = moduleGraph.getConnection(dep); + // Skip rendering depending when dependency is conditional + if (connection && !connection.isTargetActive(runtime)) { + source.replace( + dep.outerRange[0], + dep.outerRange[1] - 1, + "/* unused asset import */ undefined" + ); + return; } - if (this.isTemplateString()) { - const str = this.asString(); - if (typeof str === "string") return str !== ""; + + runtimeRequirements.add(RuntimeGlobals.require); + + if (dep.relative) { + runtimeRequirements.add(RuntimeGlobals.relativeUrl); + source.replace( + dep.outerRange[0], + dep.outerRange[1] - 1, + `/* asset import */ new ${ + RuntimeGlobals.relativeUrl + }(${runtimeTemplate.moduleRaw({ + chunkGraph, + module: moduleGraph.getModule(dep), + request: dep.request, + runtimeRequirements, + weak: false + })})` + ); + } else { + runtimeRequirements.add(RuntimeGlobals.baseURI); + + source.replace( + dep.range[0], + dep.range[1] - 1, + `/* asset import */ ${runtimeTemplate.moduleRaw({ + chunkGraph, + module: moduleGraph.getModule(dep), + request: dep.request, + runtimeRequirements, + weak: false + })}, ${RuntimeGlobals.baseURI}` + ); } - return undefined; } +}; - asNullish() { - const nullish = this.isNullish(); +makeSerializable(URLDependency, "webpack/lib/dependencies/URLDependency"); - if (nullish === true || this.isNull() || this.isUndefined()) return true; +module.exports = URLDependency; - if (nullish === false) return false; - if (this.isTruthy()) return false; - if (this.isBoolean()) return false; - if (this.isString()) return false; - if (this.isNumber()) return false; - if (this.isBigInt()) return false; - if (this.isRegExp()) return false; - if (this.isArray()) return false; - if (this.isConstArray()) return false; - if (this.isTemplateString()) return false; - if (this.isRegExp()) return false; - return undefined; - } +/***/ }), - asString() { - if (this.isBoolean()) return `${this.bool}`; - if (this.isNull()) return "null"; - if (this.isUndefined()) return "undefined"; - if (this.isString()) return this.string; - if (this.isNumber()) return `${this.number}`; - if (this.isBigInt()) return `${this.bigint}`; - if (this.isRegExp()) return `${this.regExp}`; - if (this.isArray()) { - let array = []; - for (const item of this.items) { - const itemStr = item.asString(); - if (itemStr === undefined) return undefined; - array.push(itemStr); - } - return `${array}`; - } - if (this.isConstArray()) return `${this.array}`; - if (this.isTemplateString()) { - let str = ""; - for (const part of this.parts) { - const partStr = part.asString(); - if (partStr === undefined) return undefined; - str += partStr; - } - return str; - } - return undefined; - } +/***/ 97950: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - setString(string) { - this.type = TypeString; - this.string = string; - this.sideEffects = false; - return this; - } +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Ivan Kopeykin @vankop +*/ - setUndefined() { - this.type = TypeUndefined; - this.sideEffects = false; - return this; - } - setNull() { - this.type = TypeNull; - this.sideEffects = false; - return this; - } - setNumber(number) { - this.type = TypeNumber; - this.number = number; - this.sideEffects = false; - return this; - } +const { approve } = __webpack_require__(28723); +const InnerGraph = __webpack_require__(92886); +const URLDependency = __webpack_require__(30990); - setBigInt(bigint) { - this.type = TypeBigInt; - this.bigint = bigint; - this.sideEffects = false; - return this; - } +/** @typedef {import("estree").NewExpression} NewExpressionNode */ +/** @typedef {import("../Compiler")} Compiler */ +/** @typedef {import("../javascript/JavascriptParser")} JavascriptParser */ - setBoolean(bool) { - this.type = TypeBoolean; - this.bool = bool; - this.sideEffects = false; - return this; - } +class URLPlugin { + /** + * @param {Compiler} compiler compiler + */ + apply(compiler) { + compiler.hooks.compilation.tap( + "URLPlugin", + (compilation, { normalModuleFactory }) => { + compilation.dependencyFactories.set(URLDependency, normalModuleFactory); + compilation.dependencyTemplates.set( + URLDependency, + new URLDependency.Template() + ); - setRegExp(regExp) { - this.type = TypeRegExp; - this.regExp = regExp; - this.sideEffects = false; - return this; - } + /** + * @param {JavascriptParser} parser parser + * @param {object} parserOptions options + */ + const parserCallback = (parser, parserOptions) => { + if (parserOptions.url === false) return; + const relative = parserOptions.url === "relative"; - setIdentifier(identifier, rootInfo, getMembers) { - this.type = TypeIdentifier; - this.identifier = identifier; - this.rootInfo = rootInfo; - this.getMembers = getMembers; - this.sideEffects = true; - return this; - } + /** + * @param {NewExpressionNode} expr expression + * @returns {undefined | string} request + */ + const getUrlRequest = expr => { + if (expr.arguments.length !== 2) return; - setWrapped(prefix, postfix, innerExpressions) { - this.type = TypeWrapped; - this.prefix = prefix; - this.postfix = postfix; - this.wrappedInnerExpressions = innerExpressions; - this.sideEffects = true; - return this; - } + const [arg1, arg2] = expr.arguments; - setOptions(options) { - this.type = TypeConditional; - this.options = options; - this.sideEffects = true; - return this; - } + if ( + arg2.type !== "MemberExpression" || + arg1.type === "SpreadElement" + ) + return; - addOptions(options) { - if (!this.options) { - this.type = TypeConditional; - this.options = []; - this.sideEffects = true; - } - for (const item of options) { - this.options.push(item); - } - return this; - } + const chain = parser.extractMemberExpressionChain(arg2); + + if ( + chain.members.length !== 1 || + chain.object.type !== "MetaProperty" || + chain.object.meta.name !== "import" || + chain.object.property.name !== "meta" || + chain.members[0] !== "url" + ) + return; + + const request = parser.evaluateExpression(arg1).asString(); + + return request; + }; + + parser.hooks.canRename.for("URL").tap("URLPlugin", approve); + parser.hooks.new.for("URL").tap("URLPlugin", _expr => { + const expr = /** @type {NewExpressionNode} */ (_expr); + + const request = getUrlRequest(expr); + + if (!request) return; + + const [arg1, arg2] = expr.arguments; + const dep = new URLDependency( + request, + [arg1.range[0], arg2.range[1]], + expr.range, + relative + ); + dep.loc = expr.loc; + parser.state.current.addDependency(dep); + InnerGraph.onUsage(parser.state, e => (dep.usedByExports = e)); + return true; + }); + parser.hooks.isPure.for("NewExpression").tap("URLPlugin", _expr => { + const expr = /** @type {NewExpressionNode} */ (_expr); + const { callee } = expr; + if (callee.type !== "Identifier") return; + const calleeInfo = parser.getFreeInfoFromVariable(callee.name); + if (!calleeInfo || calleeInfo.name !== "URL") return; + + const request = getUrlRequest(expr); + + if (request) return true; + }); + }; + + normalModuleFactory.hooks.parser + .for("javascript/auto") + .tap("URLPlugin", parserCallback); - setItems(items) { - this.type = TypeArray; - this.items = items; - this.sideEffects = items.some(i => i.couldHaveSideEffects()); - return this; + normalModuleFactory.hooks.parser + .for("javascript/esm") + .tap("URLPlugin", parserCallback); + } + ); } +} - setArray(array) { - this.type = TypeConstArray; - this.array = array; - this.sideEffects = false; - return this; - } +module.exports = URLPlugin; - setTemplateString(quasis, parts, kind) { - this.type = TypeTemplateString; - this.quasis = quasis; - this.parts = parts; - this.templateStringKind = kind; - this.sideEffects = parts.some(p => p.sideEffects); - return this; - } - setTruthy() { - this.falsy = false; - this.truthy = true; - this.nullish = false; - return this; - } +/***/ }), - setFalsy() { - this.falsy = true; - this.truthy = false; - return this; - } +/***/ 41381: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - setNullish(value) { - this.nullish = value; +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ - if (value) return this.setFalsy(); - return this; - } - setRange(range) { +const makeSerializable = __webpack_require__(26522); +const NullDependency = __webpack_require__(65845); + +/** @typedef {import("webpack-sources").ReplaceSource} ReplaceSource */ +/** @typedef {import("../Dependency")} Dependency */ +/** @typedef {import("../DependencyTemplate").DependencyTemplateContext} DependencyTemplateContext */ + +class UnsupportedDependency extends NullDependency { + constructor(request, range) { + super(); + + this.request = request; this.range = range; - return this; } - setSideEffects(sideEffects = true) { - this.sideEffects = sideEffects; - return this; - } + serialize(context) { + const { write } = context; - setExpression(expression) { - this.expression = expression; - return this; + write(this.request); + write(this.range); + + super.serialize(context); } -} -/** - * @param {string} flags regexp flags - * @returns {boolean} is valid flags - */ -BasicEvaluatedExpression.isValidRegExpFlags = flags => { - const len = flags.length; + deserialize(context) { + const { read } = context; - if (len === 0) return true; - if (len > 4) return false; + this.request = read(); + this.range = read(); - // cspell:word gimy - let remaining = 0b0000; // bit per RegExp flag: gimy + super.deserialize(context); + } +} - for (let i = 0; i < len; i++) - switch (flags.charCodeAt(i)) { - case 103 /* g */: - if (remaining & 0b1000) return false; - remaining |= 0b1000; - break; - case 105 /* i */: - if (remaining & 0b0100) return false; - remaining |= 0b0100; - break; - case 109 /* m */: - if (remaining & 0b0010) return false; - remaining |= 0b0010; - break; - case 121 /* y */: - if (remaining & 0b0001) return false; - remaining |= 0b0001; - break; - default: - return false; - } +makeSerializable( + UnsupportedDependency, + "webpack/lib/dependencies/UnsupportedDependency" +); - return true; +UnsupportedDependency.Template = class UnsupportedDependencyTemplate extends ( + NullDependency.Template +) { + /** + * @param {Dependency} dependency the dependency for which the template should be applied + * @param {ReplaceSource} source the current replace source which can be modified + * @param {DependencyTemplateContext} templateContext the context object + * @returns {void} + */ + apply(dependency, source, { runtimeTemplate }) { + const dep = /** @type {UnsupportedDependency} */ (dependency); + + source.replace( + dep.range[0], + dep.range[1], + runtimeTemplate.missingModule({ + request: dep.request + }) + ); + } }; -module.exports = BasicEvaluatedExpression; +module.exports = UnsupportedDependency; /***/ }), -/***/ 57634: +/***/ 18248: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; @@ -90722,176 +87770,83 @@ module.exports = BasicEvaluatedExpression; -const { ConcatSource, RawSource } = __webpack_require__(96192); -const RuntimeGlobals = __webpack_require__(49404); -const Template = __webpack_require__(92066); -const { - getChunkFilenameTemplate, - getCompilationHooks -} = __webpack_require__(76767); -const { - generateEntryStartup, - updateHashForEntryStartup -} = __webpack_require__(30951); +const Dependency = __webpack_require__(50384); +const makeSerializable = __webpack_require__(26522); +const ModuleDependency = __webpack_require__(80944); -/** @typedef {import("../Compiler")} Compiler */ +/** @typedef {import("../Dependency").ReferencedExport} ReferencedExport */ +/** @typedef {import("../Dependency").TRANSITIVE} TRANSITIVE */ +/** @typedef {import("../ModuleGraph")} ModuleGraph */ +/** @typedef {import("../util/runtime").RuntimeSpec} RuntimeSpec */ + +class WebAssemblyExportImportedDependency extends ModuleDependency { + constructor(exportName, request, name, valueType) { + super(request); + /** @type {string} */ + this.exportName = exportName; + /** @type {string} */ + this.name = name; + /** @type {string} */ + this.valueType = valueType; + } -class CommonJsChunkFormatPlugin { /** - * Apply the plugin - * @param {Compiler} compiler the compiler instance - * @returns {void} + * @returns {boolean | TRANSITIVE} true, when changes to the referenced module could affect the referencing module; TRANSITIVE, when changes to the referenced module could affect referencing modules of the referencing module */ - apply(compiler) { - compiler.hooks.thisCompilation.tap( - "CommonJsChunkFormatPlugin", - compilation => { - compilation.hooks.additionalChunkRuntimeRequirements.tap( - "CommonJsChunkLoadingPlugin", - (chunk, set, { chunkGraph }) => { - if (chunk.hasRuntime()) return; - if (chunkGraph.getNumberOfEntryModules(chunk) > 0) { - set.add(RuntimeGlobals.require); - set.add(RuntimeGlobals.startupEntrypoint); - set.add(RuntimeGlobals.externalInstallChunk); - } - } - ); - const hooks = getCompilationHooks(compilation); - hooks.renderChunk.tap( - "CommonJsChunkFormatPlugin", - (modules, renderContext) => { - const { chunk, chunkGraph, runtimeTemplate } = renderContext; - const source = new ConcatSource(); - source.add(`exports.id = ${JSON.stringify(chunk.id)};\n`); - source.add(`exports.ids = ${JSON.stringify(chunk.ids)};\n`); - source.add(`exports.modules = `); - source.add(modules); - source.add(";\n"); - const runtimeModules = - chunkGraph.getChunkRuntimeModulesInOrder(chunk); - if (runtimeModules.length > 0) { - source.add("exports.runtime =\n"); - source.add( - Template.renderChunkRuntimeModules( - runtimeModules, - renderContext - ) - ); - } - const entries = Array.from( - chunkGraph.getChunkEntryModulesWithChunkGroupIterable(chunk) - ); - if (entries.length > 0) { - const runtimeChunk = entries[0][1].getRuntimeChunk(); - const currentOutputName = compilation - .getPath( - getChunkFilenameTemplate(chunk, compilation.outputOptions), - { - chunk, - contentHashType: "javascript" - } - ) - .split("/"); - const runtimeOutputName = compilation - .getPath( - getChunkFilenameTemplate( - runtimeChunk, - compilation.outputOptions - ), - { - chunk: runtimeChunk, - contentHashType: "javascript" - } - ) - .split("/"); + couldAffectReferencingModule() { + return Dependency.TRANSITIVE; + } - // remove filename, we only need the directory - currentOutputName.pop(); + /** + * Returns list of exports referenced by this dependency + * @param {ModuleGraph} moduleGraph module graph + * @param {RuntimeSpec} runtime the runtime for which the module is analysed + * @returns {(string[] | ReferencedExport)[]} referenced exports + */ + getReferencedExports(moduleGraph, runtime) { + return [[this.name]]; + } - // remove common parts - while ( - currentOutputName.length > 0 && - runtimeOutputName.length > 0 && - currentOutputName[0] === runtimeOutputName[0] - ) { - currentOutputName.shift(); - runtimeOutputName.shift(); - } + get type() { + return "wasm export import"; + } - // create final path - const runtimePath = - (currentOutputName.length > 0 - ? "../".repeat(currentOutputName.length) - : "./") + runtimeOutputName.join("/"); + get category() { + return "wasm"; + } - const entrySource = new ConcatSource(); - entrySource.add( - `(${ - runtimeTemplate.supportsArrowFunction() - ? "() => " - : "function() " - }{\n` - ); - entrySource.add("var exports = {};\n"); - entrySource.add(source); - entrySource.add(";\n\n// load runtime\n"); - entrySource.add( - `var __webpack_require__ = require(${JSON.stringify( - runtimePath - )});\n` - ); - entrySource.add( - `${RuntimeGlobals.externalInstallChunk}(exports);\n` - ); - const startupSource = new RawSource( - generateEntryStartup( - chunkGraph, - runtimeTemplate, - entries, - chunk, - false - ) - ); - entrySource.add( - hooks.renderStartup.call( - startupSource, - entries[entries.length - 1][0], - { - ...renderContext, - inlined: false - } - ) - ); - entrySource.add("\n})()"); - return entrySource; - } - return source; - } - ); - hooks.chunkHash.tap( - "CommonJsChunkFormatPlugin", - (chunk, hash, { chunkGraph }) => { - if (chunk.hasRuntime()) return; - hash.update("CommonJsChunkFormatPlugin"); - hash.update("1"); - const entries = Array.from( - chunkGraph.getChunkEntryModulesWithChunkGroupIterable(chunk) - ); - updateHashForEntryStartup(hash, chunkGraph, entries, chunk); - } - ); - } - ); + serialize(context) { + const { write } = context; + + write(this.exportName); + write(this.name); + write(this.valueType); + + super.serialize(context); + } + + deserialize(context) { + const { read } = context; + + this.exportName = read(); + this.name = read(); + this.valueType = read(); + + super.deserialize(context); } } -module.exports = CommonJsChunkFormatPlugin; +makeSerializable( + WebAssemblyExportImportedDependency, + "webpack/lib/dependencies/WebAssemblyExportImportedDependency" +); + +module.exports = WebAssemblyExportImportedDependency; /***/ }), -/***/ 34726: +/***/ 97093: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; @@ -90902,1707 +87857,1626 @@ module.exports = CommonJsChunkFormatPlugin; -/** @typedef {import("../../declarations/WebpackOptions").ChunkLoadingType} ChunkLoadingType */ -/** @typedef {import("../Compiler")} Compiler */ - -/** @type {WeakMap>} */ -const enabledTypes = new WeakMap(); +const makeSerializable = __webpack_require__(26522); +const UnsupportedWebAssemblyFeatureError = __webpack_require__(13475); +const ModuleDependency = __webpack_require__(80944); -const getEnabledTypes = compiler => { - let set = enabledTypes.get(compiler); - if (set === undefined) { - set = new Set(); - enabledTypes.set(compiler, set); - } - return set; -}; +/** @typedef {import("@webassemblyjs/ast").ModuleImportDescription} ModuleImportDescription */ +/** @typedef {import("../Dependency").ReferencedExport} ReferencedExport */ +/** @typedef {import("../ModuleGraph")} ModuleGraph */ +/** @typedef {import("../WebpackError")} WebpackError */ +/** @typedef {import("../util/runtime").RuntimeSpec} RuntimeSpec */ -class EnableChunkLoadingPlugin { +class WebAssemblyImportDependency extends ModuleDependency { /** - * @param {ChunkLoadingType} type library type that should be available + * @param {string} request the request + * @param {string} name the imported name + * @param {ModuleImportDescription} description the WASM ast node + * @param {false | string} onlyDirectImport if only direct imports are allowed */ - constructor(type) { - this.type = type; + constructor(request, name, description, onlyDirectImport) { + super(request); + /** @type {string} */ + this.name = name; + /** @type {ModuleImportDescription} */ + this.description = description; + /** @type {false | string} */ + this.onlyDirectImport = onlyDirectImport; + } + + get type() { + return "wasm import"; + } + + get category() { + return "wasm"; } /** - * @param {Compiler} compiler the compiler instance - * @param {ChunkLoadingType} type type of library - * @returns {void} + * Returns list of exports referenced by this dependency + * @param {ModuleGraph} moduleGraph module graph + * @param {RuntimeSpec} runtime the runtime for which the module is analysed + * @returns {(string[] | ReferencedExport)[]} referenced exports */ - static setEnabled(compiler, type) { - getEnabledTypes(compiler).add(type); + getReferencedExports(moduleGraph, runtime) { + return [[this.name]]; } /** - * @param {Compiler} compiler the compiler instance - * @param {ChunkLoadingType} type type of library - * @returns {void} + * Returns errors + * @param {ModuleGraph} moduleGraph module graph + * @returns {WebpackError[]} errors */ - static checkEnabled(compiler, type) { - if (!getEnabledTypes(compiler).has(type)) { - throw new Error( - `Chunk loading type "${type}" is not enabled. ` + - "EnableChunkLoadingPlugin need to be used to enable this type of chunk loading. " + - 'This usually happens through the "output.enabledChunkLoadingTypes" option. ' + - 'If you are using a function as entry which sets "chunkLoading", you need to add all potential chunk loading types to "output.enabledChunkLoadingTypes". ' + - "These types are enabled: " + - Array.from(getEnabledTypes(compiler)).join(", ") - ); + getErrors(moduleGraph) { + const module = moduleGraph.getModule(this); + + if ( + this.onlyDirectImport && + module && + !module.type.startsWith("webassembly") + ) { + return [ + new UnsupportedWebAssemblyFeatureError( + `Import "${this.name}" from "${this.request}" with ${this.onlyDirectImport} can only be used for direct wasm to wasm dependencies` + ) + ]; } } - /** - * Apply the plugin - * @param {Compiler} compiler the compiler instance - * @returns {void} - */ - apply(compiler) { - const { type } = this; + serialize(context) { + const { write } = context; - // Only enable once - const enabled = getEnabledTypes(compiler); - if (enabled.has(type)) return; - enabled.add(type); + write(this.name); + write(this.description); + write(this.onlyDirectImport); - if (typeof type === "string") { - switch (type) { - case "jsonp": { - const JsonpChunkLoadingPlugin = __webpack_require__(9253); - new JsonpChunkLoadingPlugin().apply(compiler); - break; - } - case "import-scripts": { - const ImportScriptsChunkLoadingPlugin = __webpack_require__(56354); - new ImportScriptsChunkLoadingPlugin().apply(compiler); - break; - } - case "require": { - //@ts-expect-error https://github.com/microsoft/TypeScript/issues/41697 - const CommonJsChunkLoadingPlugin = __webpack_require__(32610); - new CommonJsChunkLoadingPlugin({ - asyncChunkLoading: false - }).apply(compiler); - break; - } - case "async-node": { - //@ts-expect-error https://github.com/microsoft/TypeScript/issues/41697 - const CommonJsChunkLoadingPlugin = __webpack_require__(32610); - new CommonJsChunkLoadingPlugin({ - asyncChunkLoading: true - }).apply(compiler); - break; - } - case "import": { - const ModuleChunkLoadingPlugin = __webpack_require__(94970); - new ModuleChunkLoadingPlugin().apply(compiler); - break; - } - case "universal": - // TODO implement universal chunk loading - throw new Error("Universal Chunk Loading is not implemented yet"); - default: - throw new Error(`Unsupported chunk loading type ${type}. -Plugins which provide custom chunk loading types must call EnableChunkLoadingPlugin.setEnabled(compiler, type) to disable this error.`); - } - } else { - // TODO support plugin instances here - // apply them to the compiler - } + super.serialize(context); + } + + deserialize(context) { + const { read } = context; + + this.name = read(); + this.description = read(); + this.onlyDirectImport = read(); + + super.deserialize(context); } } -module.exports = EnableChunkLoadingPlugin; +makeSerializable( + WebAssemblyImportDependency, + "webpack/lib/dependencies/WebAssemblyImportDependency" +); + +module.exports = WebAssemblyImportDependency; /***/ }), -/***/ 41813: +/***/ 41744: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; /* MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra + Author Ivan Kopeykin @vankop */ -const util = __webpack_require__(31669); -const { RawSource, ReplaceSource } = __webpack_require__(96192); -const Generator = __webpack_require__(1826); -const InitFragment = __webpack_require__(51739); -const HarmonyCompatibilityDependency = __webpack_require__(56164); - -/** @typedef {import("webpack-sources").Source} Source */ -/** @typedef {import("../DependenciesBlock")} DependenciesBlock */ -/** @typedef {import("../Dependency")} Dependency */ -/** @typedef {import("../DependencyTemplates")} DependencyTemplates */ -/** @typedef {import("../Generator").GenerateContext} GenerateContext */ -/** @typedef {import("../Module")} Module */ -/** @typedef {import("../Module").ConcatenationBailoutReasonContext} ConcatenationBailoutReasonContext */ -/** @typedef {import("../NormalModule")} NormalModule */ -/** @typedef {import("../RuntimeTemplate")} RuntimeTemplate */ - -// TODO: clean up this file -// replace with newer constructs - -const deprecatedGetInitFragments = util.deprecate( - (template, dependency, templateContext) => - template.getInitFragments(dependency, templateContext), - "DependencyTemplate.getInitFragment is deprecated (use apply(dep, source, { initFragments }) instead)", - "DEP_WEBPACK_JAVASCRIPT_GENERATOR_GET_INIT_FRAGMENTS" -); +const Dependency = __webpack_require__(50384); +const Template = __webpack_require__(92066); +const makeSerializable = __webpack_require__(26522); +const ModuleDependency = __webpack_require__(80944); -const TYPES = new Set(["javascript"]); +/** @typedef {import("webpack-sources").ReplaceSource} ReplaceSource */ +/** @typedef {import("../Compilation")} Compilation */ +/** @typedef {import("../Dependency").ReferencedExport} ReferencedExport */ +/** @typedef {import("../DependencyTemplate").DependencyTemplateContext} DependencyTemplateContext */ +/** @typedef {import("../ModuleGraph")} ModuleGraph */ +/** @typedef {import("../util/runtime").RuntimeSpec} RuntimeSpec */ -class JavascriptGenerator extends Generator { - /** - * @param {NormalModule} module fresh module - * @returns {Set} available types (do not mutate) - */ - getTypes(module) { - return TYPES; - } +class WebpackIsIncludedDependency extends ModuleDependency { + constructor(request, range) { + super(request); - /** - * @param {NormalModule} module the module - * @param {string=} type source type - * @returns {number} estimate size of the module - */ - getSize(module, type) { - const originalSource = module.originalSource(); - if (!originalSource) { - return 39; - } - return originalSource.size(); + this.weak = true; + this.range = range; } /** - * @param {NormalModule} module module for which the bailout reason should be determined - * @param {ConcatenationBailoutReasonContext} context context - * @returns {string | undefined} reason why this module can't be concatenated, undefined when it can be concatenated + * Returns list of exports referenced by this dependency + * @param {ModuleGraph} moduleGraph module graph + * @param {RuntimeSpec} runtime the runtime for which the module is analysed + * @returns {(string[] | ReferencedExport)[]} referenced exports */ - getConcatenationBailoutReason(module, context) { - // Only harmony modules are valid for optimization - if ( - !module.buildMeta || - module.buildMeta.exportsType !== "namespace" || - module.presentationalDependencies === undefined || - !module.presentationalDependencies.some( - d => d instanceof HarmonyCompatibilityDependency - ) - ) { - return "Module is not an ECMAScript module"; - } - - // Some expressions are not compatible with module concatenation - // because they may produce unexpected results. The plugin bails out - // if some were detected upfront. - if (module.buildInfo && module.buildInfo.moduleConcatenationBailout) { - return `Module uses ${module.buildInfo.moduleConcatenationBailout}`; - } + getReferencedExports(moduleGraph, runtime) { + // This doesn't use any export + return Dependency.NO_EXPORTS_REFERENCED; } - /** - * @param {NormalModule} module module for which the code should be generated - * @param {GenerateContext} generateContext context for generate - * @returns {Source} generated code - */ - generate(module, generateContext) { - const originalSource = module.originalSource(); - if (!originalSource) { - return new RawSource("throw new Error('No source available');"); - } - - const source = new ReplaceSource(originalSource); - const initFragments = []; - - this.sourceModule(module, initFragments, source, generateContext); - - return InitFragment.addToSource(source, initFragments, generateContext); + get type() { + return "__webpack_is_included__"; } +} - /** - * @param {Module} module the module to generate - * @param {InitFragment[]} initFragments mutable list of init fragments - * @param {ReplaceSource} source the current replace source which can be modified - * @param {GenerateContext} generateContext the generateContext - * @returns {void} - */ - sourceModule(module, initFragments, source, generateContext) { - for (const dependency of module.dependencies) { - this.sourceDependency( - module, - dependency, - initFragments, - source, - generateContext - ); - } - - if (module.presentationalDependencies !== undefined) { - for (const dependency of module.presentationalDependencies) { - this.sourceDependency( - module, - dependency, - initFragments, - source, - generateContext - ); - } - } - - for (const childBlock of module.blocks) { - this.sourceBlock( - module, - childBlock, - initFragments, - source, - generateContext - ); - } - } +makeSerializable( + WebpackIsIncludedDependency, + "webpack/lib/dependencies/WebpackIsIncludedDependency" +); +WebpackIsIncludedDependency.Template = class WebpackIsIncludedDependencyTemplate extends ( + ModuleDependency.Template +) { /** - * @param {Module} module the module to generate - * @param {DependenciesBlock} block the dependencies block which will be processed - * @param {InitFragment[]} initFragments mutable list of init fragments + * @param {Dependency} dependency the dependency for which the template should be applied * @param {ReplaceSource} source the current replace source which can be modified - * @param {GenerateContext} generateContext the generateContext + * @param {DependencyTemplateContext} templateContext the context object * @returns {void} */ - sourceBlock(module, block, initFragments, source, generateContext) { - for (const dependency of block.dependencies) { - this.sourceDependency( - module, - dependency, - initFragments, - source, - generateContext - ); - } - - for (const childBlock of block.blocks) { - this.sourceBlock( - module, - childBlock, - initFragments, - source, - generateContext - ); - } - } + apply(dependency, source, { runtimeTemplate, chunkGraph, moduleGraph }) { + const dep = /** @type {WebpackIsIncludedDependency} */ (dependency); + const connection = moduleGraph.getConnection(dep); + const included = connection + ? chunkGraph.getNumberOfModuleChunks(connection.module) > 0 + : false; + const comment = runtimeTemplate.outputOptions.pathinfo + ? Template.toComment( + `__webpack_is_included__ ${runtimeTemplate.requestShortener.shorten( + dep.request + )}` + ) + : ""; - /** - * @param {Module} module the current module - * @param {Dependency} dependency the dependency to generate - * @param {InitFragment[]} initFragments mutable list of init fragments - * @param {ReplaceSource} source the current replace source which can be modified - * @param {GenerateContext} generateContext the render context - * @returns {void} - */ - sourceDependency(module, dependency, initFragments, source, generateContext) { - const constructor = /** @type {new (...args: any[]) => Dependency} */ ( - dependency.constructor + source.replace( + dep.range[0], + dep.range[1] - 1, + `${comment}${JSON.stringify(included)}` ); - const template = generateContext.dependencyTemplates.get(constructor); - if (!template) { - throw new Error( - "No template for dependency: " + dependency.constructor.name - ); - } - - const templateContext = { - runtimeTemplate: generateContext.runtimeTemplate, - dependencyTemplates: generateContext.dependencyTemplates, - moduleGraph: generateContext.moduleGraph, - chunkGraph: generateContext.chunkGraph, - module, - runtime: generateContext.runtime, - runtimeRequirements: generateContext.runtimeRequirements, - concatenationScope: generateContext.concatenationScope, - initFragments - }; - - template.apply(dependency, source, templateContext); - - // TODO remove in webpack 6 - if ("getInitFragments" in template) { - const fragments = deprecatedGetInitFragments( - template, - dependency, - templateContext - ); - - if (fragments) { - for (const fragment of fragments) { - initFragments.push(fragment); - } - } - } } -} +}; -module.exports = JavascriptGenerator; +module.exports = WebpackIsIncludedDependency; /***/ }), -/***/ 76767: +/***/ 73016: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; /* MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra + Author Ivan Kopeykin @vankop */ -const { SyncWaterfallHook, SyncHook, SyncBailHook } = __webpack_require__(34718); -const vm = __webpack_require__(92184); -const { - ConcatSource, - OriginalSource, - PrefixSource, - RawSource, - CachedSource -} = __webpack_require__(96192); -const Compilation = __webpack_require__(59622); -const { tryRunOrWebpackError } = __webpack_require__(89935); -const HotUpdateChunk = __webpack_require__(39222); -const InitFragment = __webpack_require__(51739); +const Dependency = __webpack_require__(50384); const RuntimeGlobals = __webpack_require__(49404); -const Template = __webpack_require__(92066); -const { last, someInIterable } = __webpack_require__(31065); -const StringXor = __webpack_require__(23877); -const { compareModulesByIdentifier } = __webpack_require__(26296); -const createHash = __webpack_require__(24123); -const { intersectRuntime } = __webpack_require__(19655); -const JavascriptGenerator = __webpack_require__(41813); -const JavascriptParser = __webpack_require__(42060); +const makeSerializable = __webpack_require__(26522); +const ModuleDependency = __webpack_require__(80944); -/** @typedef {import("webpack-sources").Source} Source */ -/** @typedef {import("../Chunk")} Chunk */ +/** @typedef {import("webpack-sources").ReplaceSource} ReplaceSource */ +/** @typedef {import("../AsyncDependenciesBlock")} AsyncDependenciesBlock */ /** @typedef {import("../ChunkGraph")} ChunkGraph */ -/** @typedef {import("../CodeGenerationResults")} CodeGenerationResults */ -/** @typedef {import("../Compilation").ChunkHashContext} ChunkHashContext */ -/** @typedef {import("../Compiler")} Compiler */ -/** @typedef {import("../DependencyTemplates")} DependencyTemplates */ -/** @typedef {import("../Module")} Module */ +/** @typedef {import("../Dependency").ReferencedExport} ReferencedExport */ +/** @typedef {import("../Dependency").UpdateHashContext} UpdateHashContext */ +/** @typedef {import("../DependencyTemplate").DependencyTemplateContext} DependencyTemplateContext */ +/** @typedef {import("../Entrypoint")} Entrypoint */ /** @typedef {import("../ModuleGraph")} ModuleGraph */ -/** @typedef {import("../RuntimeTemplate")} RuntimeTemplate */ /** @typedef {import("../util/Hash")} Hash */ +/** @typedef {import("../util/runtime").RuntimeSpec} RuntimeSpec */ -/** - * @param {Chunk} chunk a chunk - * @param {ChunkGraph} chunkGraph the chunk graph - * @returns {boolean} true, when a JS file is needed for this chunk - */ -const chunkHasJs = (chunk, chunkGraph) => { - if (chunkGraph.getNumberOfEntryModules(chunk) > 0) return true; +class WorkerDependency extends ModuleDependency { + /** + * @param {string} request request + * @param {[number, number]} range range + */ + constructor(request, range) { + super(request); + this.range = range; + } - return chunkGraph.getChunkModulesIterableBySourceType(chunk, "javascript") - ? true - : false; -}; + /** + * Returns list of exports referenced by this dependency + * @param {ModuleGraph} moduleGraph module graph + * @param {RuntimeSpec} runtime the runtime for which the module is analysed + * @returns {(string[] | ReferencedExport)[]} referenced exports + */ + getReferencedExports(moduleGraph, runtime) { + return Dependency.NO_EXPORTS_REFERENCED; + } -const printGeneratedCodeForStack = (module, code) => { - const lines = code.split("\n"); - const n = `${lines.length}`.length; - return `\n\nGenerated code for ${module.identifier()}\n${lines - .map((line, i, lines) => { - const iStr = `${i + 1}`; - return `${" ".repeat(n - iStr.length)}${iStr} | ${line}`; - }) - .join("\n")}`; -}; + get type() { + return "new Worker()"; + } -/** - * @typedef {Object} RenderContext - * @property {Chunk} chunk the chunk - * @property {DependencyTemplates} dependencyTemplates the dependency templates - * @property {RuntimeTemplate} runtimeTemplate the runtime template - * @property {ModuleGraph} moduleGraph the module graph - * @property {ChunkGraph} chunkGraph the chunk graph - * @property {CodeGenerationResults} codeGenerationResults results of code generation - * @property {boolean} strictMode rendering in strict context - */ + get category() { + return "worker"; + } +} -/** - * @typedef {Object} MainRenderContext - * @property {Chunk} chunk the chunk - * @property {DependencyTemplates} dependencyTemplates the dependency templates - * @property {RuntimeTemplate} runtimeTemplate the runtime template - * @property {ModuleGraph} moduleGraph the module graph - * @property {ChunkGraph} chunkGraph the chunk graph - * @property {CodeGenerationResults} codeGenerationResults results of code generation - * @property {string} hash hash to be used for render call - * @property {boolean} strictMode rendering in strict context - */ +WorkerDependency.Template = class WorkerDependencyTemplate extends ( + ModuleDependency.Template +) { + /** + * @param {Dependency} dependency the dependency for which the template should be applied + * @param {ReplaceSource} source the current replace source which can be modified + * @param {DependencyTemplateContext} templateContext the context object + * @returns {void} + */ + apply(dependency, source, templateContext) { + const { chunkGraph, moduleGraph, runtimeRequirements } = templateContext; + const dep = /** @type {WorkerDependency} */ (dependency); + const block = /** @type {AsyncDependenciesBlock} */ ( + moduleGraph.getParentBlock(dependency) + ); + const entrypoint = /** @type {Entrypoint} */ ( + chunkGraph.getBlockChunkGroup(block) + ); + const chunk = entrypoint.getEntrypointChunk(); -/** - * @typedef {Object} ChunkRenderContext - * @property {Chunk} chunk the chunk - * @property {DependencyTemplates} dependencyTemplates the dependency templates - * @property {RuntimeTemplate} runtimeTemplate the runtime template - * @property {ModuleGraph} moduleGraph the module graph - * @property {ChunkGraph} chunkGraph the chunk graph - * @property {CodeGenerationResults} codeGenerationResults results of code generation - * @property {InitFragment[]} chunkInitFragments init fragments for the chunk - * @property {boolean} strictMode rendering in strict context - */ + runtimeRequirements.add(RuntimeGlobals.publicPath); + runtimeRequirements.add(RuntimeGlobals.baseURI); + runtimeRequirements.add(RuntimeGlobals.getChunkScriptFilename); -/** - * @typedef {Object} RenderBootstrapContext - * @property {Chunk} chunk the chunk - * @property {RuntimeTemplate} runtimeTemplate the runtime template - * @property {ModuleGraph} moduleGraph the module graph - * @property {ChunkGraph} chunkGraph the chunk graph - * @property {string} hash hash to be used for render call - */ + source.replace( + dep.range[0], + dep.range[1] - 1, + `/* worker import */ ${RuntimeGlobals.publicPath} + ${ + RuntimeGlobals.getChunkScriptFilename + }(${JSON.stringify(chunk.id)}), ${RuntimeGlobals.baseURI}` + ); + } +}; -/** @typedef {RenderContext & { inlined: boolean }} StartupRenderContext */ +makeSerializable(WorkerDependency, "webpack/lib/dependencies/WorkerDependency"); -/** - * @typedef {Object} CompilationHooks - * @property {SyncWaterfallHook<[Source, Module, ChunkRenderContext]>} renderModuleContent - * @property {SyncWaterfallHook<[Source, Module, ChunkRenderContext]>} renderModuleContainer - * @property {SyncWaterfallHook<[Source, Module, ChunkRenderContext]>} renderModulePackage - * @property {SyncWaterfallHook<[Source, RenderContext]>} renderChunk - * @property {SyncWaterfallHook<[Source, RenderContext]>} renderMain - * @property {SyncWaterfallHook<[Source, RenderContext]>} renderContent - * @property {SyncWaterfallHook<[Source, RenderContext]>} render - * @property {SyncWaterfallHook<[Source, Module, StartupRenderContext]>} renderStartup - * @property {SyncWaterfallHook<[string, RenderBootstrapContext]>} renderRequire - * @property {SyncBailHook<[Module, RenderBootstrapContext], string>} inlineInRuntimeBailout - * @property {SyncBailHook<[Module, RenderContext], string>} embedInRuntimeBailout - * @property {SyncBailHook<[RenderContext], string>} strictRuntimeBailout - * @property {SyncHook<[Chunk, Hash, ChunkHashContext]>} chunkHash - * @property {SyncBailHook<[Chunk, RenderContext], boolean>} useSourceMap - */ +module.exports = WorkerDependency; -/** @type {WeakMap} */ -const compilationHooksMap = new WeakMap(); -class JavascriptModulesPlugin { - /** - * @param {Compilation} compilation the compilation - * @returns {CompilationHooks} the attached hooks - */ - static getCompilationHooks(compilation) { - if (!(compilation instanceof Compilation)) { - throw new TypeError( - "The 'compilation' argument must be an instance of Compilation" - ); - } - let hooks = compilationHooksMap.get(compilation); - if (hooks === undefined) { - hooks = { - renderModuleContent: new SyncWaterfallHook([ - "source", - "module", - "renderContext" - ]), - renderModuleContainer: new SyncWaterfallHook([ - "source", - "module", - "renderContext" - ]), - renderModulePackage: new SyncWaterfallHook([ - "source", - "module", - "renderContext" - ]), - render: new SyncWaterfallHook(["source", "renderContext"]), - renderContent: new SyncWaterfallHook(["source", "renderContext"]), - renderStartup: new SyncWaterfallHook([ - "source", - "module", - "startupRenderContext" - ]), - renderChunk: new SyncWaterfallHook(["source", "renderContext"]), - renderMain: new SyncWaterfallHook(["source", "renderContext"]), - renderRequire: new SyncWaterfallHook(["code", "renderContext"]), - inlineInRuntimeBailout: new SyncBailHook(["module", "renderContext"]), - embedInRuntimeBailout: new SyncBailHook(["module", "renderContext"]), - strictRuntimeBailout: new SyncBailHook(["renderContext"]), - chunkHash: new SyncHook(["chunk", "hash", "context"]), - useSourceMap: new SyncBailHook(["chunk", "renderContext"]) - }; - compilationHooksMap.set(compilation, hooks); - } - return hooks; - } +/***/ }), + +/***/ 93493: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ - constructor(options = {}) { - this.options = options; - /** @type {WeakMap} */ - this._moduleFactoryCache = new WeakMap(); - } + +const { pathToFileURL } = __webpack_require__(78835); +const AsyncDependenciesBlock = __webpack_require__(11315); +const CommentCompilationWarning = __webpack_require__(28151); +const UnsupportedFeatureWarning = __webpack_require__(9532); +const EnableChunkLoadingPlugin = __webpack_require__(34726); +const { equals } = __webpack_require__(21537); +const createHash = __webpack_require__(24123); +const { contextify } = __webpack_require__(96236); +const EnableWasmLoadingPlugin = __webpack_require__(93943); +const ConstDependency = __webpack_require__(60864); +const CreateScriptUrlDependency = __webpack_require__(29829); +const { + harmonySpecifierTag +} = __webpack_require__(76581); +const WorkerDependency = __webpack_require__(73016); + +/** @typedef {import("estree").Expression} Expression */ +/** @typedef {import("estree").ObjectExpression} ObjectExpression */ +/** @typedef {import("estree").Pattern} Pattern */ +/** @typedef {import("estree").Property} Property */ +/** @typedef {import("estree").SpreadElement} SpreadElement */ +/** @typedef {import("../Compiler")} Compiler */ +/** @typedef {import("../Entrypoint").EntryOptions} EntryOptions */ +/** @typedef {import("../Parser").ParserState} ParserState */ +/** @typedef {import("../javascript/BasicEvaluatedExpression")} BasicEvaluatedExpression */ +/** @typedef {import("../javascript/JavascriptParser")} JavascriptParser */ +/** @typedef {import("./HarmonyImportDependencyParserPlugin").HarmonySettings} HarmonySettings */ + +const getUrl = module => { + return pathToFileURL(module.resource).toString(); +}; + +const DEFAULT_SYNTAX = [ + "Worker", + "SharedWorker", + "navigator.serviceWorker.register()", + "Worker from worker_threads" +]; + +/** @type {WeakMap} */ +const workerIndexMap = new WeakMap(); + +class WorkerPlugin { + constructor(chunkLoading, wasmLoading, module) { + this._chunkLoading = chunkLoading; + this._wasmLoading = wasmLoading; + this._module = module; + } /** * Apply the plugin * @param {Compiler} compiler the compiler instance * @returns {void} */ apply(compiler) { - compiler.hooks.compilation.tap( - "JavascriptModulesPlugin", + if (this._chunkLoading) { + new EnableChunkLoadingPlugin(this._chunkLoading).apply(compiler); + } + if (this._wasmLoading) { + new EnableWasmLoadingPlugin(this._wasmLoading).apply(compiler); + } + const cachedContextify = contextify.bindContextCache( + compiler.context, + compiler.root + ); + compiler.hooks.thisCompilation.tap( + "WorkerPlugin", (compilation, { normalModuleFactory }) => { - const hooks = JavascriptModulesPlugin.getCompilationHooks(compilation); - normalModuleFactory.hooks.createParser - .for("javascript/auto") - .tap("JavascriptModulesPlugin", options => { - return new JavascriptParser("auto"); - }); - normalModuleFactory.hooks.createParser - .for("javascript/dynamic") - .tap("JavascriptModulesPlugin", options => { - return new JavascriptParser("script"); - }); - normalModuleFactory.hooks.createParser - .for("javascript/esm") - .tap("JavascriptModulesPlugin", options => { - return new JavascriptParser("module"); - }); - normalModuleFactory.hooks.createGenerator - .for("javascript/auto") - .tap("JavascriptModulesPlugin", () => { - return new JavascriptGenerator(); - }); - normalModuleFactory.hooks.createGenerator - .for("javascript/dynamic") - .tap("JavascriptModulesPlugin", () => { - return new JavascriptGenerator(); - }); - normalModuleFactory.hooks.createGenerator - .for("javascript/esm") - .tap("JavascriptModulesPlugin", () => { - return new JavascriptGenerator(); - }); - compilation.hooks.renderManifest.tap( - "JavascriptModulesPlugin", - (result, options) => { - const { - hash, - chunk, - chunkGraph, - moduleGraph, - runtimeTemplate, - dependencyTemplates, - outputOptions, - codeGenerationResults - } = options; + compilation.dependencyFactories.set( + WorkerDependency, + normalModuleFactory + ); + compilation.dependencyTemplates.set( + WorkerDependency, + new WorkerDependency.Template() + ); + compilation.dependencyTemplates.set( + CreateScriptUrlDependency, + new CreateScriptUrlDependency.Template() + ); - const hotUpdateChunk = - chunk instanceof HotUpdateChunk ? chunk : null; + /** + * @param {JavascriptParser} parser the parser + * @param {Expression} expr expression + * @returns {[BasicEvaluatedExpression, [number, number]]} parsed + */ + const parseModuleUrl = (parser, expr) => { + if ( + expr.type !== "NewExpression" || + expr.callee.type === "Super" || + expr.arguments.length !== 2 + ) + return; + const [arg1, arg2] = expr.arguments; + if (arg1.type === "SpreadElement") return; + if (arg2.type === "SpreadElement") return; + const callee = parser.evaluateExpression(expr.callee); + if (!callee.isIdentifier() || callee.identifier !== "URL") return; + const arg2Value = parser.evaluateExpression(arg2); + if ( + !arg2Value.isString() || + !arg2Value.string.startsWith("file://") || + arg2Value.string !== getUrl(parser.state.module) + ) { + return; + } + const arg1Value = parser.evaluateExpression(arg1); + return [arg1Value, [arg1.range[0], arg2.range[1]]]; + }; - let render; - const filenameTemplate = - JavascriptModulesPlugin.getChunkFilenameTemplate( - chunk, - outputOptions - ); - if (hotUpdateChunk) { - render = () => - this.renderChunk( - { - chunk, - dependencyTemplates, - runtimeTemplate, - moduleGraph, - chunkGraph, - codeGenerationResults, - strictMode: runtimeTemplate.isModule() - }, - hooks - ); - } else if (chunk.hasRuntime()) { - render = () => - this.renderMain( - { - hash, - chunk, - dependencyTemplates, - runtimeTemplate, - moduleGraph, - chunkGraph, - codeGenerationResults, - strictMode: runtimeTemplate.isModule() - }, - hooks, - compilation + /** + * @param {JavascriptParser} parser the parser + * @param {ObjectExpression} expr expression + * @returns {{ expressions: Record, otherElements: (Property | SpreadElement)[], values: Record, spread: boolean, insertType: "comma" | "single", insertLocation: number }} parsed object + */ + const parseObjectExpression = (parser, expr) => { + /** @type {Record} */ + const values = {}; + /** @type {Record} */ + const expressions = {}; + /** @type {(Property | SpreadElement)[]} */ + const otherElements = []; + let spread = false; + for (const prop of expr.properties) { + if (prop.type === "SpreadElement") { + spread = true; + } else if ( + prop.type === "Property" && + !prop.method && + !prop.computed && + prop.key.type === "Identifier" + ) { + expressions[prop.key.name] = prop.value; + if (!prop.shorthand && !prop.value.type.endsWith("Pattern")) { + const value = parser.evaluateExpression( + /** @type {Expression} */ (prop.value) ); - } else { - if (!chunkHasJs(chunk, chunkGraph)) { - return result; + if (value.isCompileTimeValue()) + values[prop.key.name] = value.asCompileTimeValue(); } + } else { + otherElements.push(prop); + } + } + const insertType = expr.properties.length > 0 ? "comma" : "single"; + const insertLocation = + expr.properties[expr.properties.length - 1].range[1]; + return { + expressions, + otherElements, + values, + spread, + insertType, + insertLocation + }; + }; - render = () => - this.renderChunk( - { - chunk, - dependencyTemplates, - runtimeTemplate, - moduleGraph, - chunkGraph, - codeGenerationResults, - strictMode: runtimeTemplate.isModule() - }, - hooks + /** + * @param {JavascriptParser} parser the parser + * @param {object} parserOptions options + */ + const parserPlugin = (parser, parserOptions) => { + if (parserOptions.worker === false) return; + const options = !Array.isArray(parserOptions.worker) + ? ["..."] + : parserOptions.worker; + const handleNewWorker = expr => { + if (expr.arguments.length === 0 || expr.arguments.length > 2) + return; + const [arg1, arg2] = expr.arguments; + if (arg1.type === "SpreadElement") return; + if (arg2 && arg2.type === "SpreadElement") return; + const parsedUrl = parseModuleUrl(parser, arg1); + if (!parsedUrl) return; + const [url, range] = parsedUrl; + if (!url.isString()) return; + const { + expressions, + otherElements, + values: options, + spread: hasSpreadInOptions, + insertType, + insertLocation + } = arg2 && arg2.type === "ObjectExpression" + ? parseObjectExpression(parser, arg2) + : { + expressions: {}, + otherElements: [], + values: {}, + spread: false, + insertType: arg2 ? "spread" : "argument", + insertLocation: arg2 ? arg2.range : arg1.range[1] + }; + const { options: importOptions, errors: commentErrors } = + parser.parseCommentOptions(expr.range); + + if (commentErrors) { + for (const e of commentErrors) { + const { comment } = e; + parser.state.module.addWarning( + new CommentCompilationWarning( + `Compilation error while processing magic comment(-s): /*${comment.value}*/: ${e.message}`, + comment.loc + ) ); + } } - result.push({ - render, - filenameTemplate, - pathOptions: { - hash, - runtime: chunk.runtime, - chunk, - contentHashType: "javascript" - }, - info: { - javascriptModule: compilation.runtimeTemplate.isModule() - }, - identifier: hotUpdateChunk - ? `hotupdatechunk${chunk.id}` - : `chunk${chunk.id}`, - hash: chunk.contentHash.javascript - }); + /** @type {EntryOptions} */ + let entryOptions = {}; - return result; - } - ); - compilation.hooks.chunkHash.tap( - "JavascriptModulesPlugin", - (chunk, hash, context) => { - hooks.chunkHash.call(chunk, hash, context); - if (chunk.hasRuntime()) { - this.updateHashWithBootstrap( - hash, - { - hash: "0000", - chunk, - chunkGraph: context.chunkGraph, - moduleGraph: context.moduleGraph, - runtimeTemplate: context.runtimeTemplate - }, - hooks - ); - } - } - ); - compilation.hooks.contentHash.tap("JavascriptModulesPlugin", chunk => { - const { - chunkGraph, - moduleGraph, - runtimeTemplate, - outputOptions: { - hashSalt, - hashDigest, - hashDigestLength, - hashFunction - } - } = compilation; - const hash = createHash(hashFunction); - if (hashSalt) hash.update(hashSalt); - if (chunk.hasRuntime()) { - this.updateHashWithBootstrap( - hash, - { - hash: "0000", - chunk, - chunkGraph: compilation.chunkGraph, - moduleGraph: compilation.moduleGraph, - runtimeTemplate: compilation.runtimeTemplate - }, - hooks - ); - } else { - hash.update(`${chunk.id} `); - hash.update(chunk.ids ? chunk.ids.join(",") : ""); - } - hooks.chunkHash.call(chunk, hash, { - chunkGraph, - moduleGraph, - runtimeTemplate - }); - const modules = chunkGraph.getChunkModulesIterableBySourceType( - chunk, - "javascript" - ); - if (modules) { - const xor = new StringXor(); - for (const m of modules) { - xor.add(chunkGraph.getModuleHash(m, chunk.runtime)); - } - xor.updateHash(hash); - } - const runtimeModules = chunkGraph.getChunkModulesIterableBySourceType( - chunk, - "runtime" - ); - if (runtimeModules) { - const xor = new StringXor(); - for (const m of runtimeModules) { - xor.add(chunkGraph.getModuleHash(m, chunk.runtime)); + if (importOptions) { + if (importOptions.webpackIgnore !== undefined) { + if (typeof importOptions.webpackIgnore !== "boolean") { + parser.state.module.addWarning( + new UnsupportedFeatureWarning( + `\`webpackIgnore\` expected a boolean, but received: ${importOptions.webpackIgnore}.`, + expr.loc + ) + ); + } else { + if (importOptions.webpackIgnore) { + return false; + } + } + } + if (importOptions.webpackEntryOptions !== undefined) { + if ( + typeof importOptions.webpackEntryOptions !== "object" || + importOptions.webpackEntryOptions === null + ) { + parser.state.module.addWarning( + new UnsupportedFeatureWarning( + `\`webpackEntryOptions\` expected a object, but received: ${importOptions.webpackEntryOptions}.`, + expr.loc + ) + ); + } else { + Object.assign( + entryOptions, + importOptions.webpackEntryOptions + ); + } + } + if (importOptions.webpackChunkName !== undefined) { + if (typeof importOptions.webpackChunkName !== "string") { + parser.state.module.addWarning( + new UnsupportedFeatureWarning( + `\`webpackChunkName\` expected a string, but received: ${importOptions.webpackChunkName}.`, + expr.loc + ) + ); + } else { + entryOptions.name = importOptions.webpackChunkName; + } + } } - xor.updateHash(hash); - } - const digest = /** @type {string} */ (hash.digest(hashDigest)); - chunk.contentHash.javascript = digest.substr(0, hashDigestLength); - }); - compilation.hooks.additionalTreeRuntimeRequirements.tap( - "JavascriptModulesPlugin", - (chunk, set, { chunkGraph }) => { + if ( - !set.has(RuntimeGlobals.startupNoDefault) && - chunkGraph.hasChunkEntryDependentChunks(chunk) + !Object.prototype.hasOwnProperty.call(entryOptions, "name") && + options && + typeof options.name === "string" ) { - set.add(RuntimeGlobals.onChunksLoaded); - set.add(RuntimeGlobals.require); + entryOptions.name = options.name; } - } - ); - compilation.hooks.executeModule.tap( - "JavascriptModulesPlugin", - (options, context) => { - const source = - options.codeGenerationResult.sources.get("javascript"); - if (source === undefined) return; - const { module, moduleObject } = options; - const code = source.source(); - const fn = vm.runInThisContext( - `(function(${module.moduleArgument}, ${module.exportsArgument}, __webpack_require__) {\n${code}\n/**/})`, - { - filename: module.identifier(), - lineOffset: -1 + if (entryOptions.runtime === undefined) { + let i = workerIndexMap.get(parser.state) || 0; + workerIndexMap.set(parser.state, i + 1); + let name = `${cachedContextify( + parser.state.module.identifier() + )}|${i}`; + const hash = createHash(compilation.outputOptions.hashFunction); + hash.update(name); + const digest = /** @type {string} */ ( + hash.digest(compilation.outputOptions.hashDigest) + ); + entryOptions.runtime = digest.slice( + 0, + compilation.outputOptions.hashDigestLength + ); + } + + const block = new AsyncDependenciesBlock({ + name: entryOptions.name, + entryOptions: { + chunkLoading: this._chunkLoading, + wasmLoading: this._wasmLoading, + ...entryOptions + } + }); + block.loc = expr.loc; + const dep = new WorkerDependency(url.string, range); + dep.loc = expr.loc; + block.addDependency(dep); + parser.state.module.addBlock(block); + + if (compilation.outputOptions.trustedTypes) { + const dep = new CreateScriptUrlDependency( + expr.arguments[0].range + ); + dep.loc = expr.loc; + parser.state.module.addDependency(dep); + } + + if (expressions.type) { + const expr = expressions.type; + if (options.type !== false) { + const dep = new ConstDependency( + this._module ? '"module"' : "undefined", + expr.range + ); + dep.loc = expr.loc; + parser.state.module.addPresentationalDependency(dep); + expressions.type = undefined; } - ); - try { - fn.call( - moduleObject.exports, - moduleObject, - moduleObject.exports, - context.__webpack_require__ + } else if (insertType === "comma") { + if (this._module || hasSpreadInOptions) { + const dep = new ConstDependency( + `, type: ${this._module ? '"module"' : "undefined"}`, + insertLocation + ); + dep.loc = expr.loc; + parser.state.module.addPresentationalDependency(dep); + } + } else if (insertType === "spread") { + const dep1 = new ConstDependency( + "Object.assign({}, ", + insertLocation[0] ); - } catch (e) { - e.stack += printGeneratedCodeForStack(options.module, code); - throw e; + const dep2 = new ConstDependency( + `, { type: ${this._module ? '"module"' : "undefined"} })`, + insertLocation[1] + ); + dep1.loc = expr.loc; + dep2.loc = expr.loc; + parser.state.module.addPresentationalDependency(dep1); + parser.state.module.addPresentationalDependency(dep2); + } else if (insertType === "argument") { + if (this._module) { + const dep = new ConstDependency( + ', { type: "module" }', + insertLocation + ); + dep.loc = expr.loc; + parser.state.module.addPresentationalDependency(dep); + } } - } - ); - compilation.hooks.executeModule.tap( - "JavascriptModulesPlugin", - (options, context) => { - const source = options.codeGenerationResult.sources.get("runtime"); - if (source === undefined) return; - let code = source.source(); - if (typeof code !== "string") code = code.toString(); - const fn = vm.runInThisContext( - `(function(__webpack_require__) {\n${code}\n/**/})`, - { - filename: options.module.identifier(), - lineOffset: -1 + parser.walkExpression(expr.callee); + for (const key of Object.keys(expressions)) { + if (expressions[key]) parser.walkExpression(expressions[key]); + } + for (const prop of otherElements) { + parser.walkProperty(prop); + } + if (insertType === "spread") { + parser.walkExpression(arg2); + } + + return true; + }; + const processItem = item => { + if (item.endsWith("()")) { + parser.hooks.call + .for(item.slice(0, -2)) + .tap("WorkerPlugin", handleNewWorker); + } else { + const match = /^(.+?)(\(\))?\s+from\s+(.+)$/.exec(item); + if (match) { + const ids = match[1].split("."); + const call = match[2]; + const source = match[3]; + (call ? parser.hooks.call : parser.hooks.new) + .for(harmonySpecifierTag) + .tap("WorkerPlugin", expr => { + const settings = /** @type {HarmonySettings} */ ( + parser.currentTagData + ); + if ( + !settings || + settings.source !== source || + !equals(settings.ids, ids) + ) { + return; + } + return handleNewWorker(expr); + }); + } else { + parser.hooks.new.for(item).tap("WorkerPlugin", handleNewWorker); } - ); - try { - fn.call(null, context.__webpack_require__); - } catch (e) { - e.stack += printGeneratedCodeForStack(options.module, code); - throw e; } + }; + for (const item of options) { + if (item === "...") { + DEFAULT_SYNTAX.forEach(processItem); + } else processItem(item); } - ); + }; + normalModuleFactory.hooks.parser + .for("javascript/auto") + .tap("WorkerPlugin", parserPlugin); + normalModuleFactory.hooks.parser + .for("javascript/esm") + .tap("WorkerPlugin", parserPlugin); } ); } +} +module.exports = WorkerPlugin; - static getChunkFilenameTemplate(chunk, outputOptions) { - if (chunk.filenameTemplate) { - return chunk.filenameTemplate; - } else if (chunk instanceof HotUpdateChunk) { - return outputOptions.hotUpdateChunkFilename; - } else if (chunk.canBeInitial()) { - return outputOptions.filename; - } else { - return outputOptions.chunkFilename; - } + +/***/ }), + +/***/ 70108: +/***/ (function(module) { + +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ + + + +module.exports = expr => { + // + if ( + expr.type === "FunctionExpression" || + expr.type === "ArrowFunctionExpression" + ) { + return { + fn: expr, + expressions: [], + needThis: false + }; + } + + // .bind() + if ( + expr.type === "CallExpression" && + expr.callee.type === "MemberExpression" && + expr.callee.object.type === "FunctionExpression" && + expr.callee.property.type === "Identifier" && + expr.callee.property.name === "bind" && + expr.arguments.length === 1 + ) { + return { + fn: expr.callee.object, + expressions: [expr.arguments[0]], + needThis: undefined + }; + } + // (function(_this) {return })(this) (Coffeescript) + if ( + expr.type === "CallExpression" && + expr.callee.type === "FunctionExpression" && + expr.callee.body.type === "BlockStatement" && + expr.arguments.length === 1 && + expr.arguments[0].type === "ThisExpression" && + expr.callee.body.body && + expr.callee.body.body.length === 1 && + expr.callee.body.body[0].type === "ReturnStatement" && + expr.callee.body.body[0].argument && + expr.callee.body.body[0].argument.type === "FunctionExpression" + ) { + return { + fn: expr.callee.body.body[0].argument, + expressions: [], + needThis: true + }; + } +}; + + +/***/ }), + +/***/ 35873: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ + + + +const { UsageState } = __webpack_require__(4295); + +/** @typedef {import("../ExportsInfo").ExportInfo} ExportInfo */ +/** @typedef {import("../util/runtime").RuntimeSpec} RuntimeSpec */ + +/** + * @param {RuntimeSpec} runtime the runtime + * @param {string[][]} referencedExports list of referenced exports, will be added to + * @param {string[]} prefix export prefix + * @param {ExportInfo=} exportInfo the export info + * @param {boolean} defaultPointsToSelf when true, using default will reference itself + * @param {Set} alreadyVisited already visited export info (to handle circular reexports) + */ +const processExportInfo = ( + runtime, + referencedExports, + prefix, + exportInfo, + defaultPointsToSelf = false, + alreadyVisited = new Set() +) => { + if (!exportInfo) { + referencedExports.push(prefix); + return; + } + const used = exportInfo.getUsed(runtime); + if (used === UsageState.Unused) return; + if (alreadyVisited.has(exportInfo)) { + referencedExports.push(prefix); + return; + } + alreadyVisited.add(exportInfo); + if ( + used !== UsageState.OnlyPropertiesUsed || + !exportInfo.exportsInfo || + exportInfo.exportsInfo.otherExportsInfo.getUsed(runtime) !== + UsageState.Unused + ) { + alreadyVisited.delete(exportInfo); + referencedExports.push(prefix); + return; + } + const exportsInfo = exportInfo.exportsInfo; + for (const exportInfo of exportsInfo.orderedExports) { + processExportInfo( + runtime, + referencedExports, + defaultPointsToSelf && exportInfo.name === "default" + ? prefix + : prefix.concat(exportInfo.name), + exportInfo, + false, + alreadyVisited + ); } + alreadyVisited.delete(exportInfo); +}; +module.exports = processExportInfo; + + +/***/ }), + +/***/ 88362: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ + + + +const ExternalsPlugin = __webpack_require__(361); + +/** @typedef {import("../Compiler")} Compiler */ +class ElectronTargetPlugin { /** - * @param {Module} module the rendered module - * @param {ChunkRenderContext} renderContext options object - * @param {CompilationHooks} hooks hooks - * @param {boolean} factory true: renders as factory method, false: pure module content - * @returns {Source} the newly generated source from rendering + * @param {"main" | "preload" | "renderer"=} context in main, preload or renderer context? */ - renderModule(module, renderContext, hooks, factory) { - const { - chunk, - chunkGraph, - runtimeTemplate, - codeGenerationResults, - strictMode - } = renderContext; - try { - const codeGenResult = codeGenerationResults.get(module, chunk.runtime); - const moduleSource = codeGenResult.sources.get("javascript"); - if (!moduleSource) return null; - if (codeGenResult.data !== undefined) { - const chunkInitFragments = codeGenResult.data.get("chunkInitFragments"); - if (chunkInitFragments) { - for (const i of chunkInitFragments) - renderContext.chunkInitFragments.push(i); - } - } - const moduleSourcePostContent = tryRunOrWebpackError( - () => - hooks.renderModuleContent.call(moduleSource, module, renderContext), - "JavascriptModulesPlugin.getCompilationHooks().renderModuleContent" - ); - let moduleSourcePostContainer; - if (factory) { - const runtimeRequirements = chunkGraph.getModuleRuntimeRequirements( - module, - chunk.runtime - ); - const needModule = runtimeRequirements.has(RuntimeGlobals.module); - const needExports = runtimeRequirements.has(RuntimeGlobals.exports); - const needRequire = - runtimeRequirements.has(RuntimeGlobals.require) || - runtimeRequirements.has(RuntimeGlobals.requireScope); - const needThisAsExports = runtimeRequirements.has( - RuntimeGlobals.thisAsExports - ); - const needStrict = module.buildInfo.strict && !strictMode; - const cacheEntry = this._moduleFactoryCache.get( - moduleSourcePostContent - ); - let source; - if ( - cacheEntry && - cacheEntry.needModule === needModule && - cacheEntry.needExports === needExports && - cacheEntry.needRequire === needRequire && - cacheEntry.needThisAsExports === needThisAsExports && - cacheEntry.needStrict === needStrict - ) { - source = cacheEntry.source; - } else { - const factorySource = new ConcatSource(); - const args = []; - if (needExports || needRequire || needModule) - args.push( - needModule - ? module.moduleArgument - : "__unused_webpack_" + module.moduleArgument - ); - if (needExports || needRequire) - args.push( - needExports - ? module.exportsArgument - : "__unused_webpack_" + module.exportsArgument - ); - if (needRequire) args.push("__webpack_require__"); - if (!needThisAsExports && runtimeTemplate.supportsArrowFunction()) { - factorySource.add("/***/ ((" + args.join(", ") + ") => {\n\n"); - } else { - factorySource.add("/***/ (function(" + args.join(", ") + ") {\n\n"); - } - if (needStrict) { - factorySource.add('"use strict";\n'); - } - factorySource.add(moduleSourcePostContent); - factorySource.add("\n\n/***/ })"); - source = new CachedSource(factorySource); - this._moduleFactoryCache.set(moduleSourcePostContent, { - source, - needModule, - needExports, - needRequire, - needThisAsExports, - needStrict - }); - } - moduleSourcePostContainer = tryRunOrWebpackError( - () => hooks.renderModuleContainer.call(source, module, renderContext), - "JavascriptModulesPlugin.getCompilationHooks().renderModuleContainer" - ); - } else { - moduleSourcePostContainer = moduleSourcePostContent; - } - return tryRunOrWebpackError( - () => - hooks.renderModulePackage.call( - moduleSourcePostContainer, - module, - renderContext - ), - "JavascriptModulesPlugin.getCompilationHooks().renderModulePackage" - ); - } catch (e) { - e.module = module; - throw e; - } + constructor(context) { + this._context = context; } - /** - * @param {RenderContext} renderContext the render context - * @param {CompilationHooks} hooks hooks - * @returns {Source} the rendered source + * Apply the plugin + * @param {Compiler} compiler the compiler instance + * @returns {void} */ - renderChunk(renderContext, hooks) { - const { chunk, chunkGraph } = renderContext; - const modules = chunkGraph.getOrderedChunkModulesIterableBySourceType( - chunk, - "javascript", - compareModulesByIdentifier - ); - const allModules = modules ? Array.from(modules) : []; - let strictHeader; - let allStrict = renderContext.strictMode; - if (!allStrict && allModules.every(m => m.buildInfo.strict)) { - const strictBailout = hooks.strictRuntimeBailout.call(renderContext); - strictHeader = strictBailout - ? `// runtime can't be in strict mode because ${strictBailout}.\n` - : '"use strict";\n'; - if (!strictBailout) allStrict = true; - } - /** @type {ChunkRenderContext} */ - const chunkRenderContext = { - ...renderContext, - chunkInitFragments: [], - strictMode: allStrict - }; - const moduleSources = - Template.renderChunkModules(chunkRenderContext, allModules, module => - this.renderModule(module, chunkRenderContext, hooks, true) - ) || new RawSource("{}"); - let source = tryRunOrWebpackError( - () => hooks.renderChunk.call(moduleSources, chunkRenderContext), - "JavascriptModulesPlugin.getCompilationHooks().renderChunk" - ); - source = tryRunOrWebpackError( - () => hooks.renderContent.call(source, chunkRenderContext), - "JavascriptModulesPlugin.getCompilationHooks().renderContent" - ); - if (!source) { - throw new Error( - "JavascriptModulesPlugin error: JavascriptModulesPlugin.getCompilationHooks().renderContent plugins should return something" - ); + apply(compiler) { + new ExternalsPlugin("node-commonjs", [ + "clipboard", + "crash-reporter", + "electron", + "ipc", + "native-image", + "original-fs", + "screen", + "shell" + ]).apply(compiler); + switch (this._context) { + case "main": + new ExternalsPlugin("node-commonjs", [ + "app", + "auto-updater", + "browser-window", + "content-tracing", + "dialog", + "global-shortcut", + "ipc-main", + "menu", + "menu-item", + "power-monitor", + "power-save-blocker", + "protocol", + "session", + "tray", + "web-contents" + ]).apply(compiler); + break; + case "preload": + case "renderer": + new ExternalsPlugin("node-commonjs", [ + "desktop-capturer", + "ipc-renderer", + "remote", + "web-frame" + ]).apply(compiler); + break; } - source = InitFragment.addToSource( - source, - chunkRenderContext.chunkInitFragments, - chunkRenderContext - ); - source = tryRunOrWebpackError( - () => hooks.render.call(source, chunkRenderContext), - "JavascriptModulesPlugin.getCompilationHooks().render" + } +} + +module.exports = ElectronTargetPlugin; + + +/***/ }), + +/***/ 1808: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ + + + +const WebpackError = __webpack_require__(68422); + +/** @typedef {import("../Module")} Module */ + +class BuildCycleError extends WebpackError { + /** + * Creates an instance of ModuleDependencyError. + * @param {Module} module the module starting the cycle + */ + constructor(module) { + super( + "There is a circular build dependency, which makes it impossible to create this module" ); - if (!source) { - throw new Error( - "JavascriptModulesPlugin error: JavascriptModulesPlugin.getCompilationHooks().render plugins should return something" - ); - } - chunk.rendered = true; - return strictHeader - ? new ConcatSource(strictHeader, source, ";") - : renderContext.runtimeTemplate.isModule() - ? source - : new ConcatSource(source, ";"); + + this.name = "BuildCycleError"; + this.module = module; + } +} + +module.exports = BuildCycleError; + + +/***/ }), + +/***/ 80744: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php +*/ + + + +const RuntimeModule = __webpack_require__(61439); + +class ExportWebpackRequireRuntimeModule extends RuntimeModule { + constructor() { + super("export webpack runtime", RuntimeModule.STAGE_ATTACH); } /** - * @param {MainRenderContext} renderContext options object - * @param {CompilationHooks} hooks hooks - * @param {Compilation} compilation the compilation - * @returns {Source} the newly generated source from rendering + * @returns {boolean} true, if the runtime module should get it's own scope */ - renderMain(renderContext, hooks, compilation) { - const { chunk, chunkGraph, runtimeTemplate } = renderContext; + shouldIsolate() { + return false; + } - const runtimeRequirements = chunkGraph.getTreeRuntimeRequirements(chunk); - const iife = runtimeTemplate.isIIFE(); + /** + * @returns {string} runtime code + */ + generate() { + return "export default __webpack_require__;"; + } +} - const bootstrap = this.renderBootstrap(renderContext, hooks); - const useSourceMap = hooks.useSourceMap.call(chunk, renderContext); +module.exports = ExportWebpackRequireRuntimeModule; - const allModules = Array.from( - chunkGraph.getOrderedChunkModulesIterableBySourceType( - chunk, - "javascript", - compareModulesByIdentifier - ) || [] - ); - const hasEntryModules = chunkGraph.getNumberOfEntryModules(chunk) > 0; - let inlinedModules; - if (bootstrap.allowInlineStartup && hasEntryModules) { - inlinedModules = new Set(chunkGraph.getChunkEntryModulesIterable(chunk)); - } +/***/ }), - let source = new ConcatSource(); - let prefix; - if (iife) { - if (runtimeTemplate.supportsArrowFunction()) { - source.add("/******/ (() => { // webpackBootstrap\n"); - } else { - source.add("/******/ (function() { // webpackBootstrap\n"); - } - prefix = "/******/ \t"; - } else { - prefix = "/******/ "; - } - let allStrict = renderContext.strictMode; - if (!allStrict && allModules.every(m => m.buildInfo.strict)) { - const strictBailout = hooks.strictRuntimeBailout.call(renderContext); - if (strictBailout) { - source.add( - prefix + - `// runtime can't be in strict mode because ${strictBailout}.\n` - ); - } else { - allStrict = true; - source.add(prefix + '"use strict";\n'); - } - } +/***/ 29181: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - /** @type {ChunkRenderContext} */ - const chunkRenderContext = { - ...renderContext, - chunkInitFragments: [], - strictMode: allStrict - }; +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ - const chunkModules = Template.renderChunkModules( - chunkRenderContext, - inlinedModules - ? allModules.filter(m => !inlinedModules.has(m)) - : allModules, - module => this.renderModule(module, chunkRenderContext, hooks, true), - prefix - ); - if ( - chunkModules || - runtimeRequirements.has(RuntimeGlobals.moduleFactories) || - runtimeRequirements.has(RuntimeGlobals.moduleFactoriesAddOnly) || - runtimeRequirements.has(RuntimeGlobals.require) - ) { - source.add(prefix + "var __webpack_modules__ = ("); - source.add(chunkModules || "{}"); - source.add(");\n"); - source.add( - "/************************************************************************/\n" - ); - } - if (bootstrap.header.length > 0) { - const header = Template.asString(bootstrap.header) + "\n"; - source.add( - new PrefixSource( - prefix, - useSourceMap - ? new OriginalSource(header, "webpack/bootstrap") - : new RawSource(header) - ) - ); - source.add( - "/************************************************************************/\n" - ); - } - const runtimeModules = - renderContext.chunkGraph.getChunkRuntimeModulesInOrder(chunk); +const { ConcatSource, RawSource } = __webpack_require__(96192); +const { RuntimeGlobals } = __webpack_require__(48169); +const HotUpdateChunk = __webpack_require__(39222); +const Template = __webpack_require__(92066); +const { + getCompilationHooks, + getChunkFilenameTemplate +} = __webpack_require__(76767); +const { + generateEntryStartup, + updateHashForEntryStartup +} = __webpack_require__(30951); - if (runtimeModules.length > 0) { - source.add( - new PrefixSource( - prefix, - Template.renderRuntimeModules(runtimeModules, chunkRenderContext) - ) - ); - source.add( - "/************************************************************************/\n" - ); - // runtimeRuntimeModules calls codeGeneration - for (const module of runtimeModules) { - compilation.codeGeneratedModules.add(module); - } - } - if (inlinedModules) { - if (bootstrap.beforeStartup.length > 0) { - const beforeStartup = Template.asString(bootstrap.beforeStartup) + "\n"; - source.add( - new PrefixSource( - prefix, - useSourceMap - ? new OriginalSource(beforeStartup, "webpack/before-startup") - : new RawSource(beforeStartup) - ) - ); - } - const lastInlinedModule = last(inlinedModules); - const startupSource = new ConcatSource(); - startupSource.add(`var __webpack_exports__ = {};\n`); - for (const m of inlinedModules) { - const renderedModule = this.renderModule( - m, - chunkRenderContext, - hooks, - false - ); - if (renderedModule) { - const innerStrict = !allStrict && m.buildInfo.strict; - const runtimeRequirements = chunkGraph.getModuleRuntimeRequirements( - m, - chunk.runtime - ); - const exports = runtimeRequirements.has(RuntimeGlobals.exports); - const webpackExports = - exports && m.exportsArgument === "__webpack_exports__"; - let iife = innerStrict - ? "it need to be in strict mode." - : inlinedModules.size > 1 - ? // TODO check globals and top-level declarations of other entries and chunk modules - // to make a better decision - "it need to be isolated against other entry modules." - : chunkModules - ? "it need to be isolated against other modules in the chunk." - : exports && !webpackExports - ? `it uses a non-standard name for the exports (${m.exportsArgument}).` - : hooks.embedInRuntimeBailout.call(m, renderContext); - let footer; - if (iife !== undefined) { - startupSource.add( - `// This entry need to be wrapped in an IIFE because ${iife}\n` - ); - const arrow = runtimeTemplate.supportsArrowFunction(); - if (arrow) { - startupSource.add("(() => {\n"); - footer = "\n})();\n\n"; - } else { - startupSource.add("!function() {\n"); - footer = "\n}();\n"; +/** @typedef {import("../Compiler")} Compiler */ + +class ModuleChunkFormatPlugin { + /** + * Apply the plugin + * @param {Compiler} compiler the compiler instance + * @returns {void} + */ + apply(compiler) { + compiler.hooks.thisCompilation.tap( + "ModuleChunkFormatPlugin", + compilation => { + compilation.hooks.additionalChunkRuntimeRequirements.tap( + "ModuleChunkFormatPlugin", + (chunk, set) => { + if (chunk.hasRuntime()) return; + if (compilation.chunkGraph.getNumberOfEntryModules(chunk) > 0) { + set.add(RuntimeGlobals.require); + set.add(RuntimeGlobals.startupEntrypoint); + set.add(RuntimeGlobals.externalInstallChunk); } - if (innerStrict) startupSource.add('"use strict";\n'); - } else { - footer = "\n"; } - if (exports) { - if (m !== lastInlinedModule) - startupSource.add(`var ${m.exportsArgument} = {};\n`); - else if (m.exportsArgument !== "__webpack_exports__") - startupSource.add( - `var ${m.exportsArgument} = __webpack_exports__;\n` + ); + const hooks = getCompilationHooks(compilation); + hooks.renderChunk.tap( + "ModuleChunkFormatPlugin", + (modules, renderContext) => { + const { chunk, chunkGraph, runtimeTemplate } = renderContext; + const hotUpdateChunk = + chunk instanceof HotUpdateChunk ? chunk : null; + const source = new ConcatSource(); + if (hotUpdateChunk) { + throw new Error( + "HMR is not implemented for module chunk format yet" + ); + } else { + source.add(`export const id = ${JSON.stringify(chunk.id)};\n`); + source.add(`export const ids = ${JSON.stringify(chunk.ids)};\n`); + source.add(`export const modules = `); + source.add(modules); + source.add(`;\n`); + const runtimeModules = + chunkGraph.getChunkRuntimeModulesInOrder(chunk); + if (runtimeModules.length > 0) { + source.add("export const runtime =\n"); + source.add( + Template.renderChunkRuntimeModules( + runtimeModules, + renderContext + ) + ); + } + const entries = Array.from( + chunkGraph.getChunkEntryModulesWithChunkGroupIterable(chunk) ); + if (entries.length > 0) { + const runtimeChunk = entries[0][1].getRuntimeChunk(); + const currentOutputName = compilation + .getPath( + getChunkFilenameTemplate(chunk, compilation.outputOptions), + { + chunk, + contentHashType: "javascript" + } + ) + .split("/"); + const runtimeOutputName = compilation + .getPath( + getChunkFilenameTemplate( + runtimeChunk, + compilation.outputOptions + ), + { + chunk: runtimeChunk, + contentHashType: "javascript" + } + ) + .split("/"); + + // remove filename, we only need the directory + const outputFilename = currentOutputName.pop(); + + // remove common parts + while ( + currentOutputName.length > 0 && + runtimeOutputName.length > 0 && + currentOutputName[0] === runtimeOutputName[0] + ) { + currentOutputName.shift(); + runtimeOutputName.shift(); + } + + // create final path + const runtimePath = + (currentOutputName.length > 0 + ? "../".repeat(currentOutputName.length) + : "./") + runtimeOutputName.join("/"); + + const entrySource = new ConcatSource(); + entrySource.add(source); + entrySource.add(";\n\n// load runtime\n"); + entrySource.add( + `import __webpack_require__ from ${JSON.stringify( + runtimePath + )};\n` + ); + entrySource.add( + `import * as __webpack_self_exports__ from ${JSON.stringify( + "./" + outputFilename + )};\n` + ); + entrySource.add( + `${RuntimeGlobals.externalInstallChunk}(__webpack_self_exports__);\n` + ); + const startupSource = new RawSource( + generateEntryStartup( + chunkGraph, + runtimeTemplate, + entries, + chunk, + false + ) + ); + entrySource.add( + hooks.renderStartup.call( + startupSource, + entries[entries.length - 1][0], + { + ...renderContext, + inlined: false + } + ) + ); + return entrySource; + } + } + return source; } - startupSource.add(renderedModule); - startupSource.add(footer); - } - } - if (runtimeRequirements.has(RuntimeGlobals.onChunksLoaded)) { - startupSource.add( - `__webpack_exports__ = ${RuntimeGlobals.onChunksLoaded}(__webpack_exports__);\n` ); - } - source.add( - hooks.renderStartup.call(startupSource, lastInlinedModule, { - ...renderContext, - inlined: true - }) - ); - if (bootstrap.afterStartup.length > 0) { - const afterStartup = Template.asString(bootstrap.afterStartup) + "\n"; - source.add( - new PrefixSource( - prefix, - useSourceMap - ? new OriginalSource(afterStartup, "webpack/after-startup") - : new RawSource(afterStartup) - ) + hooks.chunkHash.tap( + "ModuleChunkFormatPlugin", + (chunk, hash, { chunkGraph, runtimeTemplate }) => { + if (chunk.hasRuntime()) return; + hash.update("ModuleChunkFormatPlugin"); + hash.update("1"); + const entries = Array.from( + chunkGraph.getChunkEntryModulesWithChunkGroupIterable(chunk) + ); + updateHashForEntryStartup(hash, chunkGraph, entries, chunk); + } ); } - } else { - const lastEntryModule = last( - chunkGraph.getChunkEntryModulesIterable(chunk) - ); - const toSource = useSourceMap - ? (content, name) => - new OriginalSource(Template.asString(content), name) - : content => new RawSource(Template.asString(content)); - source.add( - new PrefixSource( - prefix, - new ConcatSource( - toSource(bootstrap.beforeStartup, "webpack/before-startup"), - "\n", - hooks.renderStartup.call( - toSource(bootstrap.startup.concat(""), "webpack/startup"), - lastEntryModule, - { - ...renderContext, - inlined: false - } - ), - toSource(bootstrap.afterStartup, "webpack/after-startup"), - "\n" - ) - ) - ); - } - if ( - hasEntryModules && - runtimeRequirements.has(RuntimeGlobals.returnExportsFromRuntime) - ) { - source.add(`${prefix}return __webpack_exports__;\n`); - } - if (iife) { - source.add("/******/ })()\n"); - } - - /** @type {Source} */ - let finalSource = tryRunOrWebpackError( - () => hooks.renderMain.call(source, renderContext), - "JavascriptModulesPlugin.getCompilationHooks().renderMain" - ); - if (!finalSource) { - throw new Error( - "JavascriptModulesPlugin error: JavascriptModulesPlugin.getCompilationHooks().renderMain plugins should return something" - ); - } - finalSource = tryRunOrWebpackError( - () => hooks.renderContent.call(finalSource, renderContext), - "JavascriptModulesPlugin.getCompilationHooks().renderContent" - ); - if (!finalSource) { - throw new Error( - "JavascriptModulesPlugin error: JavascriptModulesPlugin.getCompilationHooks().renderContent plugins should return something" - ); - } - finalSource = InitFragment.addToSource( - finalSource, - chunkRenderContext.chunkInitFragments, - chunkRenderContext - ); - finalSource = tryRunOrWebpackError( - () => hooks.render.call(finalSource, renderContext), - "JavascriptModulesPlugin.getCompilationHooks().render" ); - if (!finalSource) { - throw new Error( - "JavascriptModulesPlugin error: JavascriptModulesPlugin.getCompilationHooks().render plugins should return something" - ); - } - chunk.rendered = true; - return iife ? new ConcatSource(finalSource, ";") : finalSource; } +} + +module.exports = ModuleChunkFormatPlugin; + + +/***/ }), + +/***/ 94970: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ + + + +const RuntimeGlobals = __webpack_require__(49404); +const ExportWebpackRequireRuntimeModule = __webpack_require__(80744); +const ModuleChunkLoadingRuntimeModule = __webpack_require__(53807); + +/** @typedef {import("../Compiler")} Compiler */ +class ModuleChunkLoadingPlugin { /** - * @param {Hash} hash the hash to be updated - * @param {RenderBootstrapContext} renderContext options object - * @param {CompilationHooks} hooks hooks + * Apply the plugin + * @param {Compiler} compiler the compiler instance + * @returns {void} */ - updateHashWithBootstrap(hash, renderContext, hooks) { - const bootstrap = this.renderBootstrap(renderContext, hooks); - for (const key of Object.keys(bootstrap)) { - hash.update(key); - if (Array.isArray(bootstrap[key])) { - for (const line of bootstrap[key]) { - hash.update(line); - } - } else { - hash.update(JSON.stringify(bootstrap[key])); + apply(compiler) { + compiler.hooks.thisCompilation.tap( + "ModuleChunkLoadingPlugin", + compilation => { + const globalChunkLoading = compilation.outputOptions.chunkLoading; + const isEnabledForChunk = chunk => { + const options = chunk.getEntryOptions(); + const chunkLoading = + (options && options.chunkLoading) || globalChunkLoading; + return chunkLoading === "import"; + }; + const onceForChunkSet = new WeakSet(); + const handler = (chunk, set) => { + if (onceForChunkSet.has(chunk)) return; + onceForChunkSet.add(chunk); + if (!isEnabledForChunk(chunk)) return; + set.add(RuntimeGlobals.moduleFactoriesAddOnly); + set.add(RuntimeGlobals.hasOwnProperty); + compilation.addRuntimeModule( + chunk, + new ModuleChunkLoadingRuntimeModule(set) + ); + }; + compilation.hooks.runtimeRequirementInTree + .for(RuntimeGlobals.ensureChunkHandlers) + .tap("ModuleChunkLoadingPlugin", handler); + compilation.hooks.runtimeRequirementInTree + .for(RuntimeGlobals.baseURI) + .tap("ModuleChunkLoadingPlugin", handler); + compilation.hooks.runtimeRequirementInTree + .for(RuntimeGlobals.externalInstallChunk) + .tap("ModuleChunkLoadingPlugin", handler); + compilation.hooks.runtimeRequirementInTree + .for(RuntimeGlobals.onChunksLoaded) + .tap("ModuleChunkLoadingPlugin", handler); + compilation.hooks.runtimeRequirementInTree + .for(RuntimeGlobals.externalInstallChunk) + .tap("ModuleChunkLoadingPlugin", (chunk, set) => { + if (!isEnabledForChunk(chunk)) return; + compilation.addRuntimeModule( + chunk, + new ExportWebpackRequireRuntimeModule() + ); + }); + + compilation.hooks.runtimeRequirementInTree + .for(RuntimeGlobals.ensureChunkHandlers) + .tap("ModuleChunkLoadingPlugin", (chunk, set) => { + if (!isEnabledForChunk(chunk)) return; + set.add(RuntimeGlobals.getChunkScriptFilename); + }); } - } + ); } +} - /** - * @param {RenderBootstrapContext} renderContext options object - * @param {CompilationHooks} hooks hooks - * @returns {{ header: string[], beforeStartup: string[], startup: string[], afterStartup: string[], allowInlineStartup: boolean }} the generated source of the bootstrap code - */ - renderBootstrap(renderContext, hooks) { - const { chunkGraph, moduleGraph, chunk, runtimeTemplate } = renderContext; +module.exports = ModuleChunkLoadingPlugin; - const runtimeRequirements = chunkGraph.getTreeRuntimeRequirements(chunk); - const requireFunction = runtimeRequirements.has(RuntimeGlobals.require); - const moduleCache = runtimeRequirements.has(RuntimeGlobals.moduleCache); - const moduleFactories = runtimeRequirements.has( - RuntimeGlobals.moduleFactories - ); - const moduleUsed = runtimeRequirements.has(RuntimeGlobals.module); - const requireScopeUsed = runtimeRequirements.has( - RuntimeGlobals.requireScope - ); - const interceptModuleExecution = runtimeRequirements.has( - RuntimeGlobals.interceptModuleExecution - ); +/***/ }), - const useRequire = - requireFunction || interceptModuleExecution || moduleUsed; +/***/ 53807: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - const result = { - header: [], - beforeStartup: [], - startup: [], - afterStartup: [], - allowInlineStartup: true - }; +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php +*/ - let { header: buf, startup, beforeStartup, afterStartup } = result; - if (result.allowInlineStartup && moduleFactories) { - startup.push( - "// module factories are used so entry inlining is disabled" - ); - result.allowInlineStartup = false; - } - if (result.allowInlineStartup && moduleCache) { - startup.push("// module cache are used so entry inlining is disabled"); - result.allowInlineStartup = false; - } - if (result.allowInlineStartup && interceptModuleExecution) { - startup.push( - "// module execution is intercepted so entry inlining is disabled" + +const { SyncWaterfallHook } = __webpack_require__(34718); +const Compilation = __webpack_require__(59622); +const RuntimeGlobals = __webpack_require__(49404); +const RuntimeModule = __webpack_require__(61439); +const Template = __webpack_require__(92066); +const { + getChunkFilenameTemplate, + chunkHasJs +} = __webpack_require__(76767); +const { getInitialChunkIds } = __webpack_require__(30951); +const compileBooleanMatcher = __webpack_require__(356); +const { getUndoPath } = __webpack_require__(96236); + +/** @typedef {import("../Chunk")} Chunk */ + +/** + * @typedef {Object} JsonpCompilationPluginHooks + * @property {SyncWaterfallHook<[string, Chunk]>} linkPreload + * @property {SyncWaterfallHook<[string, Chunk]>} linkPrefetch + */ + +/** @type {WeakMap} */ +const compilationHooksMap = new WeakMap(); + +class ModuleChunkLoadingRuntimeModule extends RuntimeModule { + /** + * @param {Compilation} compilation the compilation + * @returns {JsonpCompilationPluginHooks} hooks + */ + static getCompilationHooks(compilation) { + if (!(compilation instanceof Compilation)) { + throw new TypeError( + "The 'compilation' argument must be an instance of Compilation" ); - result.allowInlineStartup = false; } - - if (useRequire || moduleCache) { - buf.push("// The module cache"); - buf.push("var __webpack_module_cache__ = {};"); - buf.push(""); + let hooks = compilationHooksMap.get(compilation); + if (hooks === undefined) { + hooks = { + linkPreload: new SyncWaterfallHook(["source", "chunk"]), + linkPrefetch: new SyncWaterfallHook(["source", "chunk"]) + }; + compilationHooksMap.set(compilation, hooks); } + return hooks; + } - if (useRequire) { - buf.push("// The require function"); - buf.push(`function __webpack_require__(moduleId) {`); - buf.push(Template.indent(this.renderRequire(renderContext, hooks))); - buf.push("}"); - buf.push(""); - } else if (runtimeRequirements.has(RuntimeGlobals.requireScope)) { - buf.push("// The require scope"); - buf.push("var __webpack_require__ = {};"); - buf.push(""); - } + constructor(runtimeRequirements) { + super("import chunk loading", RuntimeModule.STAGE_ATTACH); + this._runtimeRequirements = runtimeRequirements; + } - if ( - moduleFactories || - runtimeRequirements.has(RuntimeGlobals.moduleFactoriesAddOnly) - ) { - buf.push("// expose the modules object (__webpack_modules__)"); - buf.push(`${RuntimeGlobals.moduleFactories} = __webpack_modules__;`); - buf.push(""); - } + /** + * @returns {string} runtime code + */ + generate() { + const { compilation, chunk } = this; + const { + runtimeTemplate, + chunkGraph, + outputOptions: { importFunctionName, importMetaName } + } = compilation; + const fn = RuntimeGlobals.ensureChunkHandlers; + const withBaseURI = this._runtimeRequirements.has(RuntimeGlobals.baseURI); + const withExternalInstallChunk = this._runtimeRequirements.has( + RuntimeGlobals.externalInstallChunk + ); + const withLoading = this._runtimeRequirements.has( + RuntimeGlobals.ensureChunkHandlers + ); + const withOnChunkLoad = this._runtimeRequirements.has( + RuntimeGlobals.onChunksLoaded + ); + const withHmr = this._runtimeRequirements.has( + RuntimeGlobals.hmrDownloadUpdateHandlers + ); + const conditionMap = chunkGraph.getChunkConditionMap(chunk, chunkHasJs); + const hasJsMatcher = compileBooleanMatcher(conditionMap); + const initialChunkIds = getInitialChunkIds(chunk, chunkGraph); - if (moduleCache) { - buf.push("// expose the module cache"); - buf.push(`${RuntimeGlobals.moduleCache} = __webpack_module_cache__;`); - buf.push(""); - } + const outputName = this.compilation.getPath( + getChunkFilenameTemplate(chunk, this.compilation.outputOptions), + { + chunk, + contentHashType: "javascript" + } + ); + const rootOutputDir = getUndoPath( + outputName, + this.compilation.outputOptions.path, + true + ); - if (interceptModuleExecution) { - buf.push("// expose the module execution interceptor"); - buf.push(`${RuntimeGlobals.interceptModuleExecution} = [];`); - buf.push(""); - } + const stateExpression = withHmr + ? `${RuntimeGlobals.hmrRuntimeStatePrefix}_module` + : undefined; - if (!runtimeRequirements.has(RuntimeGlobals.startupNoDefault)) { - if (chunkGraph.getNumberOfEntryModules(chunk) > 0) { - /** @type {string[]} */ - const buf2 = []; - const runtimeRequirements = - chunkGraph.getTreeRuntimeRequirements(chunk); - buf2.push("// Load entry module and return exports"); - let i = chunkGraph.getNumberOfEntryModules(chunk); - for (const [ - entryModule, - entrypoint - ] of chunkGraph.getChunkEntryModulesWithChunkGroupIterable(chunk)) { - const chunks = entrypoint.chunks.filter(c => c !== chunk); - if (result.allowInlineStartup && chunks.length > 0) { - buf2.push( - "// This entry module depends on other loaded chunks and execution need to be delayed" - ); - result.allowInlineStartup = false; - } - if ( - result.allowInlineStartup && - someInIterable( - moduleGraph.getIncomingConnectionsByOriginModule(entryModule), - ([originModule, connections]) => - originModule && - connections.some(c => c.isTargetActive(chunk.runtime)) && - someInIterable( - chunkGraph.getModuleRuntimes(originModule), - runtime => - intersectRuntime(runtime, chunk.runtime) !== undefined - ) - ) - ) { - buf2.push( - "// This entry module is referenced by other modules so it can't be inlined" - ); - result.allowInlineStartup = false; - } - if ( - result.allowInlineStartup && - (!entryModule.buildInfo || - !entryModule.buildInfo.topLevelDeclarations) - ) { - buf2.push( - "// This entry module doesn't tell about it's top-level declarations so it can't be inlined" - ); - result.allowInlineStartup = false; - } - if (result.allowInlineStartup) { - const bailout = hooks.inlineInRuntimeBailout.call( - entryModule, - renderContext - ); - if (bailout !== undefined) { - buf2.push( - `// This entry module can't be inlined because ${bailout}` - ); - result.allowInlineStartup = false; - } - } - i--; - const moduleId = chunkGraph.getModuleId(entryModule); - const entryRuntimeRequirements = - chunkGraph.getModuleRuntimeRequirements(entryModule, chunk.runtime); - let moduleIdExpr = JSON.stringify(moduleId); - if (runtimeRequirements.has(RuntimeGlobals.entryModuleId)) { - moduleIdExpr = `${RuntimeGlobals.entryModuleId} = ${moduleIdExpr}`; - } - if ( - result.allowInlineStartup && - entryRuntimeRequirements.has(RuntimeGlobals.module) - ) { - result.allowInlineStartup = false; - buf2.push( - "// This entry module used 'module' so it can't be inlined" - ); - } - if (chunks.length > 0) { - buf2.push( - `${i === 0 ? "var __webpack_exports__ = " : ""}${ - RuntimeGlobals.onChunksLoaded - }(undefined, ${JSON.stringify( - chunks.map(c => c.id) - )}, ${runtimeTemplate.returningFunction( - `__webpack_require__(${moduleIdExpr})` - )})` - ); - } else if (useRequire) { - buf2.push( - `${ - i === 0 ? "var __webpack_exports__ = " : "" - }__webpack_require__(${moduleIdExpr});` - ); - } else { - if (i === 0) buf2.push("var __webpack_exports__ = {};"); - if (requireScopeUsed) { - buf2.push( - `__webpack_modules__[${moduleIdExpr}](0, ${ - i === 0 ? "__webpack_exports__" : "{}" - }, __webpack_require__);` - ); - } else if (entryRuntimeRequirements.has(RuntimeGlobals.exports)) { - buf2.push( - `__webpack_modules__[${moduleIdExpr}](0, ${ - i === 0 ? "__webpack_exports__" : "{}" - });` - ); - } else { - buf2.push(`__webpack_modules__[${moduleIdExpr}]();`); - } - } - } - if (runtimeRequirements.has(RuntimeGlobals.onChunksLoaded)) { - buf2.push( - `__webpack_exports__ = ${RuntimeGlobals.onChunksLoaded}(__webpack_exports__);` - ); - } - if ( - runtimeRequirements.has(RuntimeGlobals.startup) || - (runtimeRequirements.has(RuntimeGlobals.startupOnlyBefore) && - runtimeRequirements.has(RuntimeGlobals.startupOnlyAfter)) - ) { - result.allowInlineStartup = false; - buf.push("// the startup function"); - buf.push( - `${RuntimeGlobals.startup} = ${runtimeTemplate.basicFunction("", [ - ...buf2, - "return __webpack_exports__;" - ])};` - ); - buf.push(""); - startup.push("// run startup"); - startup.push( - `var __webpack_exports__ = ${RuntimeGlobals.startup}();` - ); - } else if (runtimeRequirements.has(RuntimeGlobals.startupOnlyBefore)) { - buf.push("// the startup function"); - buf.push( - `${RuntimeGlobals.startup} = ${runtimeTemplate.emptyFunction()};` - ); - beforeStartup.push("// run runtime startup"); - beforeStartup.push(`${RuntimeGlobals.startup}();`); - startup.push("// startup"); - startup.push(Template.asString(buf2)); - } else if (runtimeRequirements.has(RuntimeGlobals.startupOnlyAfter)) { - buf.push("// the startup function"); - buf.push( - `${RuntimeGlobals.startup} = ${runtimeTemplate.emptyFunction()};` - ); - startup.push("// startup"); - startup.push(Template.asString(buf2)); - afterStartup.push("// run runtime startup"); - afterStartup.push(`${RuntimeGlobals.startup}();`); - } else { - startup.push("// startup"); - startup.push(Template.asString(buf2)); - } + return Template.asString([ + withBaseURI + ? Template.asString([ + `${RuntimeGlobals.baseURI} = new URL(${JSON.stringify( + rootOutputDir + )}, ${importMetaName}.url);` + ]) + : "// no baseURI", + "", + "// object to store loaded and loading chunks", + "// undefined = chunk not loaded, null = chunk preloaded/prefetched", + "// [resolve, reject, Promise] = chunk loading, 0 = chunk loaded", + `var installedChunks = ${ + stateExpression ? `${stateExpression} = ${stateExpression} || ` : "" + }{`, + Template.indent( + Array.from(initialChunkIds, id => `${JSON.stringify(id)}: 0`).join( + ",\n" + ) + ), + "};", + "", + withLoading || withExternalInstallChunk + ? `var installChunk = ${runtimeTemplate.basicFunction("data", [ + runtimeTemplate.destructureObject( + ["ids", "modules", "runtime"], + "data" + ), + '// add "modules" to the modules object,', + '// then flag all "ids" as loaded and fire callback', + "var moduleId, chunkId, i = 0;", + "for(moduleId in modules) {", + Template.indent([ + `if(${RuntimeGlobals.hasOwnProperty}(modules, moduleId)) {`, + Template.indent( + `${RuntimeGlobals.moduleFactories}[moduleId] = modules[moduleId];` + ), + "}" + ]), + "}", + "if(runtime) runtime(__webpack_require__);", + "for(;i < ids.length; i++) {", + Template.indent([ + "chunkId = ids[i];", + `if(${RuntimeGlobals.hasOwnProperty}(installedChunks, chunkId) && installedChunks[chunkId]) {`, + Template.indent("installedChunks[chunkId][0]();"), + "}", + "installedChunks[ids[i]] = 0;" + ]), + "}", + withOnChunkLoad ? `${RuntimeGlobals.onChunksLoaded}();` : "" + ])}` + : "// no install chunk", + "", + withLoading + ? Template.asString([ + `${fn}.j = ${runtimeTemplate.basicFunction( + "chunkId, promises", + hasJsMatcher !== false + ? Template.indent([ + "// import() chunk loading for javascript", + `var installedChunkData = ${RuntimeGlobals.hasOwnProperty}(installedChunks, chunkId) ? installedChunks[chunkId] : undefined;`, + 'if(installedChunkData !== 0) { // 0 means "already installed".', + Template.indent([ + "", + '// a Promise means "currently loading".', + "if(installedChunkData) {", + Template.indent([ + "promises.push(installedChunkData[1]);" + ]), + "} else {", + Template.indent([ + hasJsMatcher === true + ? "if(true) { // all chunks have JS" + : `if(${hasJsMatcher("chunkId")}) {`, + Template.indent([ + "// setup Promise in chunk cache", + `var promise = ${importFunctionName}(${JSON.stringify( + rootOutputDir + )} + ${ + RuntimeGlobals.getChunkScriptFilename + }(chunkId)).then(installChunk, ${runtimeTemplate.basicFunction( + "e", + [ + "if(installedChunks[chunkId] !== 0) installedChunks[chunkId] = undefined;", + "throw e;" + ] + )});`, + `var promise = Promise.race([promise, new Promise(${runtimeTemplate.expressionFunction( + `installedChunkData = installedChunks[chunkId] = [resolve]`, + "resolve" + )})])`, + `promises.push(installedChunkData[1] = promise);` + ]), + "} else installedChunks[chunkId] = 0;" + ]), + "}" + ]), + "}" + ]) + : Template.indent(["installedChunks[chunkId] = 0;"]) + )};` + ]) + : "// no chunk on demand loading", + "", + withExternalInstallChunk + ? Template.asString([ + `${RuntimeGlobals.externalInstallChunk} = installChunk;` + ]) + : "// no external install chunk", + "", + withOnChunkLoad + ? `${ + RuntimeGlobals.onChunksLoaded + }.j = ${runtimeTemplate.returningFunction( + "installedChunks[chunkId] === 0", + "chunkId" + )};` + : "// no on chunks loaded" + ]); + } +} + +module.exports = ModuleChunkLoadingRuntimeModule; + + +/***/ }), + +/***/ 57261: +/***/ (function(module) { + +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ + + + +/** @typedef {import("./Dependency").DependencyLocation} DependencyLocation */ +/** @typedef {import("./Dependency").SourcePosition} SourcePosition */ + +/** + * @param {SourcePosition} pos position + * @returns {string} formatted position + */ +const formatPosition = pos => { + if (pos && typeof pos === "object") { + if ("line" in pos && "column" in pos) { + return `${pos.line}:${pos.column}`; + } else if ("line" in pos) { + return `${pos.line}:?`; + } + } + return ""; +}; + +/** + * @param {DependencyLocation} loc location + * @returns {string} formatted location + */ +const formatLocation = loc => { + if (loc && typeof loc === "object") { + if ("start" in loc && loc.start && "end" in loc && loc.end) { + if ( + typeof loc.start === "object" && + typeof loc.start.line === "number" && + typeof loc.end === "object" && + typeof loc.end.line === "number" && + typeof loc.end.column === "number" && + loc.start.line === loc.end.line + ) { + return `${formatPosition(loc.start)}-${loc.end.column}`; } else if ( - runtimeRequirements.has(RuntimeGlobals.startup) || - runtimeRequirements.has(RuntimeGlobals.startupOnlyBefore) || - runtimeRequirements.has(RuntimeGlobals.startupOnlyAfter) + typeof loc.start === "object" && + typeof loc.start.line === "number" && + typeof loc.start.column !== "number" && + typeof loc.end === "object" && + typeof loc.end.line === "number" && + typeof loc.end.column !== "number" ) { - buf.push( - "// the startup function", - "// It's empty as no entry modules are in this chunk", - `${RuntimeGlobals.startup} = ${runtimeTemplate.emptyFunction()};`, - "" - ); + return `${loc.start.line}-${loc.end.line}`; + } else { + return `${formatPosition(loc.start)}-${formatPosition(loc.end)}`; } - } else if ( - runtimeRequirements.has(RuntimeGlobals.startup) || - runtimeRequirements.has(RuntimeGlobals.startupOnlyBefore) || - runtimeRequirements.has(RuntimeGlobals.startupOnlyAfter) - ) { - result.allowInlineStartup = false; - buf.push( - "// the startup function", - "// It's empty as some runtime module handles the default behavior", - `${RuntimeGlobals.startup} = ${runtimeTemplate.emptyFunction()};` - ); - startup.push("// run startup"); - startup.push(`var __webpack_exports__ = ${RuntimeGlobals.startup}();`); } - return result; + if ("start" in loc && loc.start) { + return formatPosition(loc.start); + } + if ("name" in loc && "index" in loc) { + return `${loc.name}[${loc.index}]`; + } + if ("name" in loc) { + return loc.name; + } } + return ""; +}; + +module.exports = formatLocation; + + +/***/ }), + +/***/ 21978: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ + + + +const RuntimeGlobals = __webpack_require__(49404); +const RuntimeModule = __webpack_require__(61439); +const Template = __webpack_require__(92066); +class HotModuleReplacementRuntimeModule extends RuntimeModule { + constructor() { + super("hot module replacement", RuntimeModule.STAGE_BASIC); + } /** - * @param {RenderBootstrapContext} renderContext options object - * @param {CompilationHooks} hooks hooks - * @returns {string} the generated source of the require function + * @returns {string} runtime code */ - renderRequire(renderContext, hooks) { - const { - chunk, - chunkGraph, - runtimeTemplate: { outputOptions } - } = renderContext; - const runtimeRequirements = chunkGraph.getTreeRuntimeRequirements(chunk); - const moduleExecution = runtimeRequirements.has( - RuntimeGlobals.interceptModuleExecution + generate() { + return Template.getFunctionContent( + require('./HotModuleReplacement.runtime.js') ) - ? Template.asString([ - "var execOptions = { id: moduleId, module: module, factory: __webpack_modules__[moduleId], require: __webpack_require__ };", - `${RuntimeGlobals.interceptModuleExecution}.forEach(function(handler) { handler(execOptions); });`, - "module = execOptions.module;", - "execOptions.factory.call(module.exports, module, module.exports, execOptions.require);" - ]) - : runtimeRequirements.has(RuntimeGlobals.thisAsExports) - ? Template.asString([ - "__webpack_modules__[moduleId].call(module.exports, module, module.exports, __webpack_require__);" - ]) - : Template.asString([ - "__webpack_modules__[moduleId](module, module.exports, __webpack_require__);" - ]); - const needModuleId = runtimeRequirements.has(RuntimeGlobals.moduleId); - const needModuleLoaded = runtimeRequirements.has( - RuntimeGlobals.moduleLoaded - ); - const content = Template.asString([ - "// Check if module is in cache", - "var cachedModule = __webpack_module_cache__[moduleId];", - "if (cachedModule !== undefined) {", - outputOptions.strictModuleErrorHandling - ? Template.indent([ - "if (cachedModule.error !== undefined) throw cachedModule.error;", - "return cachedModule.exports;" - ]) - : Template.indent("return cachedModule.exports;"), - "}", - "// Create a new module (and put it into the cache)", - "var module = __webpack_module_cache__[moduleId] = {", - Template.indent([ - needModuleId ? "id: moduleId," : "// no module.id needed", - needModuleLoaded ? "loaded: false," : "// no module.loaded needed", - "exports: {}" - ]), - "};", - "", - outputOptions.strictModuleExceptionHandling - ? Template.asString([ - "// Execute the module function", - "var threw = true;", - "try {", - Template.indent([moduleExecution, "threw = false;"]), - "} finally {", - Template.indent([ - "if(threw) delete __webpack_module_cache__[moduleId];" - ]), - "}" - ]) - : outputOptions.strictModuleErrorHandling - ? Template.asString([ - "// Execute the module function", - "try {", - Template.indent(moduleExecution), - "} catch(e) {", - Template.indent(["module.error = e;", "throw e;"]), - "}" - ]) - : Template.asString([ - "// Execute the module function", - moduleExecution - ]), - needModuleLoaded - ? Template.asString([ - "", - "// Flag the module as loaded", - "module.loaded = true;", - "" - ]) - : "", - "// Return the exports of the module", - "return module.exports;" - ]); - return tryRunOrWebpackError( - () => hooks.renderRequire.call(content, renderContext), - "JavascriptModulesPlugin.getCompilationHooks().renderRequire" - ); + .replace(/\$getFullHash\$/g, RuntimeGlobals.getFullHash) + .replace( + /\$interceptModuleExecution\$/g, + RuntimeGlobals.interceptModuleExecution + ) + .replace(/\$moduleCache\$/g, RuntimeGlobals.moduleCache) + .replace(/\$hmrModuleData\$/g, RuntimeGlobals.hmrModuleData) + .replace(/\$hmrDownloadManifest\$/g, RuntimeGlobals.hmrDownloadManifest) + .replace( + /\$hmrInvalidateModuleHandlers\$/g, + RuntimeGlobals.hmrInvalidateModuleHandlers + ) + .replace( + /\$hmrDownloadUpdateHandlers\$/g, + RuntimeGlobals.hmrDownloadUpdateHandlers + ); } } -module.exports = JavascriptModulesPlugin; -module.exports.chunkHasJs = chunkHasJs; +module.exports = HotModuleReplacementRuntimeModule; /***/ }), -/***/ 42060: +/***/ 70839: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; @@ -92613,3773 +89487,3080 @@ module.exports.chunkHasJs = chunkHasJs; -const { Parser: AcornParser } = __webpack_require__(29089); -const { importAssertions } = __webpack_require__(10666); -const { SyncBailHook, HookMap } = __webpack_require__(34718); -const vm = __webpack_require__(92184); -const Parser = __webpack_require__(68214); -const StackedMap = __webpack_require__(60798); -const binarySearchBounds = __webpack_require__(44795); -const memoize = __webpack_require__(84297); -const BasicEvaluatedExpression = __webpack_require__(2412); +const { RawSource } = __webpack_require__(96192); +const AsyncDependenciesBlock = __webpack_require__(11315); +const Dependency = __webpack_require__(50384); +const Module = __webpack_require__(85887); +const ModuleFactory = __webpack_require__(61574); +const RuntimeGlobals = __webpack_require__(49404); +const Template = __webpack_require__(92066); +const CommonJsRequireDependency = __webpack_require__(38604); +const { registerNotSerializable } = __webpack_require__(99551); -/** @typedef {import("acorn").Options} AcornOptions */ -/** @typedef {import("estree").ArrayExpression} ArrayExpressionNode */ -/** @typedef {import("estree").BinaryExpression} BinaryExpressionNode */ -/** @typedef {import("estree").BlockStatement} BlockStatementNode */ -/** @typedef {import("estree").SequenceExpression} SequenceExpressionNode */ -/** @typedef {import("estree").CallExpression} CallExpressionNode */ -/** @typedef {import("estree").ClassDeclaration} ClassDeclarationNode */ -/** @typedef {import("estree").ClassExpression} ClassExpressionNode */ -/** @typedef {import("estree").Comment} CommentNode */ -/** @typedef {import("estree").ConditionalExpression} ConditionalExpressionNode */ -/** @typedef {import("estree").Declaration} DeclarationNode */ -/** @typedef {import("estree").PrivateIdentifier} PrivateIdentifierNode */ -/** @typedef {import("estree").PropertyDefinition} PropertyDefinitionNode */ -/** @typedef {import("estree").Expression} ExpressionNode */ -/** @typedef {import("estree").Identifier} IdentifierNode */ -/** @typedef {import("estree").IfStatement} IfStatementNode */ -/** @typedef {import("estree").LabeledStatement} LabeledStatementNode */ -/** @typedef {import("estree").Literal} LiteralNode */ -/** @typedef {import("estree").LogicalExpression} LogicalExpressionNode */ -/** @typedef {import("estree").ChainExpression} ChainExpressionNode */ -/** @typedef {import("estree").MemberExpression} MemberExpressionNode */ -/** @typedef {import("estree").MetaProperty} MetaPropertyNode */ -/** @typedef {import("estree").MethodDefinition} MethodDefinitionNode */ -/** @typedef {import("estree").ModuleDeclaration} ModuleDeclarationNode */ -/** @typedef {import("estree").NewExpression} NewExpressionNode */ -/** @typedef {import("estree").Node} AnyNode */ -/** @typedef {import("estree").Program} ProgramNode */ -/** @typedef {import("estree").Statement} StatementNode */ -/** @typedef {import("estree").ImportDeclaration} ImportDeclarationNode */ -/** @typedef {import("estree").ExportNamedDeclaration} ExportNamedDeclarationNode */ -/** @typedef {import("estree").ExportDefaultDeclaration} ExportDefaultDeclarationNode */ -/** @typedef {import("estree").ExportAllDeclaration} ExportAllDeclarationNode */ -/** @typedef {import("estree").Super} SuperNode */ -/** @typedef {import("estree").TaggedTemplateExpression} TaggedTemplateExpressionNode */ -/** @typedef {import("estree").TemplateLiteral} TemplateLiteralNode */ -/** @typedef {import("estree").ThisExpression} ThisExpressionNode */ -/** @typedef {import("estree").UnaryExpression} UnaryExpressionNode */ -/** @typedef {import("estree").VariableDeclarator} VariableDeclaratorNode */ -/** @template T @typedef {import("tapable").AsArray} AsArray */ -/** @typedef {import("../Parser").ParserState} ParserState */ -/** @typedef {import("../Parser").PreparsedAst} PreparsedAst */ -/** @typedef {{declaredScope: ScopeInfo, freeName: string | true, tagInfo: TagInfo | undefined}} VariableInfoInterface */ -/** @typedef {{ name: string | VariableInfo, rootInfo: string | VariableInfo, getMembers: () => string[] }} GetInfoResult */ +/** @typedef {import("../../declarations/WebpackOptions")} WebpackOptions */ +/** @typedef {import("../Compilation")} Compilation */ +/** @typedef {import("../Compiler")} Compiler */ +/** @typedef {import("../Dependency").UpdateHashContext} UpdateHashContext */ +/** @typedef {import("../Module").BuildMeta} BuildMeta */ +/** @typedef {import("../Module").CodeGenerationContext} CodeGenerationContext */ +/** @typedef {import("../Module").CodeGenerationResult} CodeGenerationResult */ +/** @typedef {import("../Module").LibIdentOptions} LibIdentOptions */ +/** @typedef {import("../Module").NeedBuildContext} NeedBuildContext */ +/** @typedef {import("../ModuleFactory").ModuleFactoryCreateData} ModuleFactoryCreateData */ +/** @typedef {import("../ModuleFactory").ModuleFactoryResult} ModuleFactoryResult */ +/** @typedef {import("../RequestShortener")} RequestShortener */ +/** @typedef {import("../ResolverFactory").ResolverWithOptions} ResolverWithOptions */ +/** @typedef {import("../WebpackError")} WebpackError */ +/** @typedef {import("../util/Hash")} Hash */ +/** @typedef {import("../util/fs").InputFileSystem} InputFileSystem */ -const EMPTY_ARRAY = []; -const ALLOWED_MEMBER_TYPES_CALL_EXPRESSION = 0b01; -const ALLOWED_MEMBER_TYPES_EXPRESSION = 0b10; -const ALLOWED_MEMBER_TYPES_ALL = 0b11; +/** + * @typedef {Object} BackendApi + * @property {function(Error=): void} dispose + * @property {function(Module): { client: string, data: string, active: boolean }} module + */ -// Syntax: https://developer.mozilla.org/en/SpiderMonkey/Parser_API +const IGNORED_DEPENDENCY_TYPES = new Set([ + "import.meta.webpackHot.accept", + "import.meta.webpackHot.decline", + "module.hot.accept", + "module.hot.decline" +]); -const parser = AcornParser.extend(importAssertions); +/** + * @param {undefined|string|RegExp|Function} test test option + * @param {Module} module the module + * @returns {boolean} true, if the module should be selected + */ +const checkTest = (test, module) => { + if (test === undefined) return true; + if (typeof test === "function") { + return test(module); + } + if (typeof test === "string") { + const name = module.nameForCondition(); + return name && name.startsWith(test); + } + if (test instanceof RegExp) { + const name = module.nameForCondition(); + return name && test.test(name); + } + return false; +}; + +const TYPES = new Set(["javascript"]); + +class LazyCompilationDependency extends Dependency { + constructor(proxyModule) { + super(); + this.proxyModule = proxyModule; + } + + get category() { + return "esm"; + } + + get type() { + return "lazy import()"; + } + + /** + * @returns {string | null} an identifier to merge equal requests + */ + getResourceIdentifier() { + return this.proxyModule.originalModule.identifier(); + } +} + +registerNotSerializable(LazyCompilationDependency); + +class LazyCompilationProxyModule extends Module { + constructor(context, originalModule, request, client, data, active) { + super("lazy-compilation-proxy", context, originalModule.layer); + this.originalModule = originalModule; + this.request = request; + this.client = client; + this.data = data; + this.active = active; + } + + /** + * @returns {string} a unique identifier of the module + */ + identifier() { + return `lazy-compilation-proxy|${this.originalModule.identifier()}`; + } + + /** + * @param {RequestShortener} requestShortener the request shortener + * @returns {string} a user readable identifier of the module + */ + readableIdentifier(requestShortener) { + return `lazy-compilation-proxy ${this.originalModule.readableIdentifier( + requestShortener + )}`; + } + + /** + * Assuming this module is in the cache. Update the (cached) module with + * the fresh module from the factory. Usually updates internal references + * and properties. + * @param {Module} module fresh module + * @returns {void} + */ + updateCacheModule(module) { + super.updateCacheModule(module); + const m = /** @type {LazyCompilationProxyModule} */ (module); + this.originalModule = m.originalModule; + this.request = m.request; + this.client = m.client; + this.data = m.data; + this.active = m.active; + } + + /** + * @param {LibIdentOptions} options options + * @returns {string | null} an identifier for library inclusion + */ + libIdent(options) { + return `${this.originalModule.libIdent(options)}!lazy-compilation-proxy`; + } + + /** + * @param {NeedBuildContext} context context info + * @param {function(WebpackError=, boolean=): void} callback callback function, returns true, if the module needs a rebuild + * @returns {void} + */ + needBuild(context, callback) { + callback(null, !this.buildInfo || this.buildInfo.active !== this.active); + } + + /** + * @param {WebpackOptions} options webpack options + * @param {Compilation} compilation the compilation + * @param {ResolverWithOptions} resolver the resolver + * @param {InputFileSystem} fs the file system + * @param {function(WebpackError=): void} callback callback function + * @returns {void} + */ + build(options, compilation, resolver, fs, callback) { + this.buildInfo = { + active: this.active + }; + /** @type {BuildMeta} */ + this.buildMeta = {}; + this.clearDependenciesAndBlocks(); + const dep = new CommonJsRequireDependency(this.client); + this.addDependency(dep); + if (this.active) { + const dep = new LazyCompilationDependency(this); + const block = new AsyncDependenciesBlock({}); + block.addDependency(dep); + this.addBlock(block); + } + callback(); + } + + /** + * @returns {Set} types available (do not mutate) + */ + getSourceTypes() { + return TYPES; + } + + /** + * @param {string=} type the source type for which the size should be estimated + * @returns {number} the estimated size of the module (must be non-zero) + */ + size(type) { + return 200; + } + + /** + * @param {CodeGenerationContext} context context for code generation + * @returns {CodeGenerationResult} result + */ + codeGeneration({ runtimeTemplate, chunkGraph, moduleGraph }) { + const sources = new Map(); + const runtimeRequirements = new Set(); + runtimeRequirements.add(RuntimeGlobals.module); + const clientDep = /** @type {CommonJsRequireDependency} */ ( + this.dependencies[0] + ); + const clientModule = moduleGraph.getModule(clientDep); + const block = this.blocks[0]; + const client = Template.asString([ + `var client = ${runtimeTemplate.moduleExports({ + module: clientModule, + chunkGraph, + request: clientDep.userRequest, + runtimeRequirements + })}`, + `var data = ${JSON.stringify(this.data)};` + ]); + const keepActive = Template.asString([ + `var dispose = client.keepAlive({ data: data, active: ${JSON.stringify( + !!block + )}, module: module, onError: onError });` + ]); + let source; + if (block) { + const dep = block.dependencies[0]; + const module = moduleGraph.getModule(dep); + source = Template.asString([ + client, + `module.exports = ${runtimeTemplate.moduleNamespacePromise({ + chunkGraph, + block, + module, + request: this.request, + strict: false, // TODO this should be inherited from the original module + message: "import()", + runtimeRequirements + })};`, + "if (module.hot) {", + Template.indent([ + "module.hot.accept();", + `module.hot.accept(${JSON.stringify( + chunkGraph.getModuleId(module) + )}, function() { module.hot.invalidate(); });`, + "module.hot.dispose(function(data) { delete data.resolveSelf; dispose(data); });", + "if (module.hot.data && module.hot.data.resolveSelf) module.hot.data.resolveSelf(module.exports);" + ]), + "}", + "function onError() { /* ignore */ }", + keepActive + ]); + } else { + source = Template.asString([ + client, + "var resolveSelf, onError;", + `module.exports = new Promise(function(resolve, reject) { resolveSelf = resolve; onError = reject; });`, + "if (module.hot) {", + Template.indent([ + "module.hot.accept();", + "if (module.hot.data && module.hot.data.resolveSelf) module.hot.data.resolveSelf(module.exports);", + "module.hot.dispose(function(data) { data.resolveSelf = resolveSelf; dispose(data); });" + ]), + "}", + keepActive + ]); + } + sources.set("javascript", new RawSource(source)); + return { + sources, + runtimeRequirements + }; + } -class VariableInfo { /** - * @param {ScopeInfo} declaredScope scope in which the variable is declared - * @param {string | true} freeName which free name the variable aliases, or true when none - * @param {TagInfo | undefined} tagInfo info about tags + * @param {Hash} hash the hash used to track dependencies + * @param {UpdateHashContext} context context + * @returns {void} */ - constructor(declaredScope, freeName, tagInfo) { - this.declaredScope = declaredScope; - this.freeName = freeName; - this.tagInfo = tagInfo; + updateHash(hash, context) { + super.updateHash(hash, context); + hash.update(this.active ? "active" : ""); + hash.update(JSON.stringify(this.data)); } } -/** @typedef {string | ScopeInfo | VariableInfo} ExportedVariableInfo */ -/** @typedef {LiteralNode | string | null | undefined} ImportSource */ -/** @typedef {Omit & { sourceType: "module" | "script" | "auto", ecmaVersion?: AcornOptions["ecmaVersion"] }} ParseOptions */ - -/** - * @typedef {Object} TagInfo - * @property {any} tag - * @property {any} data - * @property {TagInfo | undefined} next - */ - -/** - * @typedef {Object} ScopeInfo - * @property {StackedMap} definitions - * @property {boolean | "arrow"} topLevelScope - * @property {boolean} inShorthand - * @property {boolean} isStrict - * @property {boolean} isAsmJs - * @property {boolean} inTry - */ - -const joinRanges = (startRange, endRange) => { - if (!endRange) return startRange; - if (!startRange) return endRange; - return [startRange[0], endRange[1]]; -}; - -const objectAndMembersToName = (object, membersReversed) => { - let name = object; - for (let i = membersReversed.length - 1; i >= 0; i--) { - name = name + "." + membersReversed[i]; - } - return name; -}; +registerNotSerializable(LazyCompilationProxyModule); -const getRootName = expression => { - switch (expression.type) { - case "Identifier": - return expression.name; - case "ThisExpression": - return "this"; - case "MetaProperty": - return `${expression.meta.name}.${expression.property.name}`; - default: - return undefined; +class LazyCompilationDependencyFactory extends ModuleFactory { + constructor(factory) { + super(); + this._factory = factory; } -}; - -/** @type {AcornOptions} */ -const defaultParserOptions = { - ranges: true, - locations: true, - ecmaVersion: "latest", - sourceType: "module", - // https://github.com/tc39/proposal-hashbang - allowHashBang: true, - onComment: null -}; - -// regexp to match at least one "magic comment" -const webpackCommentRegExp = new RegExp(/(^|\W)webpack[A-Z]{1,}[A-Za-z]{1,}:/); - -const EMPTY_COMMENT_OPTIONS = { - options: null, - errors: null -}; -class JavascriptParser extends Parser { /** - * @param {"module" | "script" | "auto"} sourceType default source type + * @param {ModuleFactoryCreateData} data data object + * @param {function(Error=, ModuleFactoryResult=): void} callback callback + * @returns {void} */ - constructor(sourceType = "auto") { - super(); - this.hooks = Object.freeze({ - /** @type {HookMap>} */ - evaluateTypeof: new HookMap(() => new SyncBailHook(["expression"])), - /** @type {HookMap>} */ - evaluate: new HookMap(() => new SyncBailHook(["expression"])), - /** @type {HookMap>} */ - evaluateIdentifier: new HookMap(() => new SyncBailHook(["expression"])), - /** @type {HookMap>} */ - evaluateDefinedIdentifier: new HookMap( - () => new SyncBailHook(["expression"]) - ), - /** @type {HookMap>} */ - evaluateCallExpressionMember: new HookMap( - () => new SyncBailHook(["expression", "param"]) - ), - /** @type {HookMap>} */ - isPure: new HookMap( - () => new SyncBailHook(["expression", "commentsStartPosition"]) - ), - /** @type {SyncBailHook<[StatementNode | ModuleDeclarationNode], boolean | void>} */ - preStatement: new SyncBailHook(["statement"]), - - /** @type {SyncBailHook<[StatementNode | ModuleDeclarationNode], boolean | void>} */ - blockPreStatement: new SyncBailHook(["declaration"]), - /** @type {SyncBailHook<[StatementNode | ModuleDeclarationNode], boolean | void>} */ - statement: new SyncBailHook(["statement"]), - /** @type {SyncBailHook<[IfStatementNode], boolean | void>} */ - statementIf: new SyncBailHook(["statement"]), - /** @type {SyncBailHook<[ExpressionNode, ClassExpressionNode | ClassDeclarationNode], boolean | void>} */ - classExtendsExpression: new SyncBailHook([ - "expression", - "classDefinition" - ]), - /** @type {SyncBailHook<[MethodDefinitionNode | PropertyDefinitionNode, ClassExpressionNode | ClassDeclarationNode], boolean | void>} */ - classBodyElement: new SyncBailHook(["element", "classDefinition"]), - /** @type {SyncBailHook<[ExpressionNode, MethodDefinitionNode | PropertyDefinitionNode, ClassExpressionNode | ClassDeclarationNode], boolean | void>} */ - classBodyValue: new SyncBailHook([ - "expression", - "element", - "classDefinition" - ]), - /** @type {HookMap>} */ - label: new HookMap(() => new SyncBailHook(["statement"])), - /** @type {SyncBailHook<[ImportDeclarationNode, ImportSource], boolean | void>} */ - import: new SyncBailHook(["statement", "source"]), - /** @type {SyncBailHook<[ImportDeclarationNode, ImportSource, string, string], boolean | void>} */ - importSpecifier: new SyncBailHook([ - "statement", - "source", - "exportName", - "identifierName" - ]), - /** @type {SyncBailHook<[ExportNamedDeclarationNode | ExportAllDeclarationNode], boolean | void>} */ - export: new SyncBailHook(["statement"]), - /** @type {SyncBailHook<[ExportNamedDeclarationNode | ExportAllDeclarationNode, ImportSource], boolean | void>} */ - exportImport: new SyncBailHook(["statement", "source"]), - /** @type {SyncBailHook<[ExportNamedDeclarationNode | ExportAllDeclarationNode, DeclarationNode], boolean | void>} */ - exportDeclaration: new SyncBailHook(["statement", "declaration"]), - /** @type {SyncBailHook<[ExportDefaultDeclarationNode, DeclarationNode], boolean | void>} */ - exportExpression: new SyncBailHook(["statement", "declaration"]), - /** @type {SyncBailHook<[ExportNamedDeclarationNode | ExportAllDeclarationNode, string, string, number | undefined], boolean | void>} */ - exportSpecifier: new SyncBailHook([ - "statement", - "identifierName", - "exportName", - "index" - ]), - /** @type {SyncBailHook<[ExportNamedDeclarationNode | ExportAllDeclarationNode, ImportSource, string, string, number | undefined], boolean | void>} */ - exportImportSpecifier: new SyncBailHook([ - "statement", - "source", - "identifierName", - "exportName", - "index" - ]), - /** @type {SyncBailHook<[VariableDeclaratorNode, StatementNode], boolean | void>} */ - preDeclarator: new SyncBailHook(["declarator", "statement"]), - /** @type {SyncBailHook<[VariableDeclaratorNode, StatementNode], boolean | void>} */ - declarator: new SyncBailHook(["declarator", "statement"]), - /** @type {HookMap>} */ - varDeclaration: new HookMap(() => new SyncBailHook(["declaration"])), - /** @type {HookMap>} */ - varDeclarationLet: new HookMap(() => new SyncBailHook(["declaration"])), - /** @type {HookMap>} */ - varDeclarationConst: new HookMap(() => new SyncBailHook(["declaration"])), - /** @type {HookMap>} */ - varDeclarationVar: new HookMap(() => new SyncBailHook(["declaration"])), - /** @type {HookMap>} */ - pattern: new HookMap(() => new SyncBailHook(["pattern"])), - /** @type {HookMap>} */ - canRename: new HookMap(() => new SyncBailHook(["initExpression"])), - /** @type {HookMap>} */ - rename: new HookMap(() => new SyncBailHook(["initExpression"])), - /** @type {HookMap>} */ - assign: new HookMap(() => new SyncBailHook(["expression"])), - /** @type {HookMap>} */ - assignMemberChain: new HookMap( - () => new SyncBailHook(["expression", "members"]) - ), - /** @type {HookMap>} */ - typeof: new HookMap(() => new SyncBailHook(["expression"])), - /** @type {SyncBailHook<[ExpressionNode], boolean | void>} */ - importCall: new SyncBailHook(["expression"]), - /** @type {SyncBailHook<[ExpressionNode], boolean | void>} */ - topLevelAwait: new SyncBailHook(["expression"]), - /** @type {HookMap>} */ - call: new HookMap(() => new SyncBailHook(["expression"])), - /** Something like "a.b()" */ - /** @type {HookMap>} */ - callMemberChain: new HookMap( - () => new SyncBailHook(["expression", "members"]) - ), - /** Something like "a.b().c.d" */ - /** @type {HookMap>} */ - memberChainOfCallMemberChain: new HookMap( - () => - new SyncBailHook([ - "expression", - "calleeMembers", - "callExpression", - "members" - ]) - ), - /** Something like "a.b().c.d()"" */ - /** @type {HookMap>} */ - callMemberChainOfCallMemberChain: new HookMap( - () => - new SyncBailHook([ - "expression", - "calleeMembers", - "innerCallExpression", - "members" - ]) - ), - /** @type {SyncBailHook<[ChainExpressionNode], boolean | void>} */ - optionalChaining: new SyncBailHook(["optionalChaining"]), - /** @type {HookMap>} */ - new: new HookMap(() => new SyncBailHook(["expression"])), - /** @type {HookMap>} */ - expression: new HookMap(() => new SyncBailHook(["expression"])), - /** @type {HookMap>} */ - expressionMemberChain: new HookMap( - () => new SyncBailHook(["expression", "members"]) - ), - /** @type {HookMap>} */ - unhandledExpressionMemberChain: new HookMap( - () => new SyncBailHook(["expression", "members"]) - ), - /** @type {SyncBailHook<[ExpressionNode], boolean | void>} */ - expressionConditionalOperator: new SyncBailHook(["expression"]), - /** @type {SyncBailHook<[ExpressionNode], boolean | void>} */ - expressionLogicalOperator: new SyncBailHook(["expression"]), - /** @type {SyncBailHook<[ProgramNode, CommentNode[]], boolean | void>} */ - program: new SyncBailHook(["ast", "comments"]), - /** @type {SyncBailHook<[ProgramNode, CommentNode[]], boolean | void>} */ - finish: new SyncBailHook(["ast", "comments"]) + create(data, callback) { + const dependency = /** @type {LazyCompilationDependency} */ ( + data.dependencies[0] + ); + callback(null, { + module: dependency.proxyModule.originalModule }); - this.sourceType = sourceType; - /** @type {ScopeInfo} */ - this.scope = undefined; - /** @type {ParserState} */ - this.state = undefined; - this.comments = undefined; - this.semicolons = undefined; - /** @type {(StatementNode|ExpressionNode)[]} */ - this.statementPath = undefined; - this.prevStatement = undefined; - this.currentTagData = undefined; - this._initializeEvaluating(); } +} - _initializeEvaluating() { - this.hooks.evaluate.for("Literal").tap("JavascriptParser", _expr => { - const expr = /** @type {LiteralNode} */ (_expr); - - switch (typeof expr.value) { - case "number": - return new BasicEvaluatedExpression() - .setNumber(expr.value) - .setRange(expr.range); - case "bigint": - return new BasicEvaluatedExpression() - .setBigInt(expr.value) - .setRange(expr.range); - case "string": - return new BasicEvaluatedExpression() - .setString(expr.value) - .setRange(expr.range); - case "boolean": - return new BasicEvaluatedExpression() - .setBoolean(expr.value) - .setRange(expr.range); - } - if (expr.value === null) { - return new BasicEvaluatedExpression().setNull().setRange(expr.range); - } - if (expr.value instanceof RegExp) { - return new BasicEvaluatedExpression() - .setRegExp(expr.value) - .setRange(expr.range); +class LazyCompilationPlugin { + /** + * @param {Object} options options + * @param {(function(Compiler, function(Error?, BackendApi?): void): void) | function(Compiler): Promise} options.backend the backend + * @param {boolean} options.entries true, when entries are lazy compiled + * @param {boolean} options.imports true, when import() modules are lazy compiled + * @param {RegExp | string | (function(Module): boolean)} options.test additional filter for lazy compiled entrypoint modules + */ + constructor({ backend, entries, imports, test }) { + this.backend = backend; + this.entries = entries; + this.imports = imports; + this.test = test; + } + /** + * Apply the plugin + * @param {Compiler} compiler the compiler instance + * @returns {void} + */ + apply(compiler) { + let backend; + compiler.hooks.beforeCompile.tapAsync( + "LazyCompilationPlugin", + (params, callback) => { + if (backend !== undefined) return callback(); + const promise = this.backend(compiler, (err, result) => { + if (err) return callback(err); + backend = result; + callback(); + }); + if (promise && promise.then) { + promise.then(b => { + backend = b; + callback(); + }, callback); + } } - }); - this.hooks.evaluate.for("NewExpression").tap("JavascriptParser", _expr => { - const expr = /** @type {NewExpressionNode} */ (_expr); - const callee = expr.callee; - if ( - callee.type !== "Identifier" || - callee.name !== "RegExp" || - expr.arguments.length > 2 || - this.getVariableInfo("RegExp") !== "RegExp" - ) - return; - - let regExp, flags; - const arg1 = expr.arguments[0]; - - if (arg1) { - if (arg1.type === "SpreadElement") return; - - const evaluatedRegExp = this.evaluateExpression(arg1); - - if (!evaluatedRegExp) return; - - regExp = evaluatedRegExp.asString(); + ); + compiler.hooks.thisCompilation.tap( + "LazyCompilationPlugin", + (compilation, { normalModuleFactory }) => { + normalModuleFactory.hooks.module.tap( + "LazyCompilationPlugin", + (originalModule, createData, resolveData) => { + if ( + resolveData.dependencies.every( + dep => + IGNORED_DEPENDENCY_TYPES.has(dep.type) || + (this.imports && + (dep.type === "import()" || + dep.type === "import() context element")) || + (this.entries && dep.type === "entry") + ) && + !/webpack[/\\]hot[/\\]|webpack-dev-server[/\\]client/.test( + resolveData.request + ) && + checkTest(this.test, originalModule) + ) { + const moduleInfo = backend.module(originalModule); + if (!moduleInfo) return; + const { client, data, active } = moduleInfo; - if (!regExp) return; - } else { - return new BasicEvaluatedExpression() - .setRegExp(new RegExp("")) - .setRange(expr.range); + return new LazyCompilationProxyModule( + compiler.context, + originalModule, + resolveData.request, + client, + data, + active + ); + } + } + ); + compilation.dependencyFactories.set( + LazyCompilationDependency, + new LazyCompilationDependencyFactory() + ); } + ); + compiler.hooks.shutdown.tapAsync("LazyCompilationPlugin", callback => { + backend.dispose(callback); + }); + } +} - const arg2 = expr.arguments[1]; - - if (arg2) { - if (arg2.type === "SpreadElement") return; - - const evaluatedFlags = this.evaluateExpression(arg2); - - if (!evaluatedFlags) return; - - if (!evaluatedFlags.isUndefined()) { - flags = evaluatedFlags.asString(); +module.exports = LazyCompilationPlugin; - if ( - flags === undefined || - !BasicEvaluatedExpression.isValidRegExpFlags(flags) - ) - return; - } - } - return new BasicEvaluatedExpression() - .setRegExp(flags ? new RegExp(regExp, flags) : new RegExp(regExp)) - .setRange(expr.range); - }); - this.hooks.evaluate - .for("LogicalExpression") - .tap("JavascriptParser", _expr => { - const expr = /** @type {LogicalExpressionNode} */ (_expr); +/***/ }), - const left = this.evaluateExpression(expr.left); - if (!left) return; - let returnRight = false; - /** @type {boolean|undefined} */ - let allowedRight; - if (expr.operator === "&&") { - const leftAsBool = left.asBool(); - if (leftAsBool === false) return left.setRange(expr.range); - returnRight = leftAsBool === true; - allowedRight = false; - } else if (expr.operator === "||") { - const leftAsBool = left.asBool(); - if (leftAsBool === true) return left.setRange(expr.range); - returnRight = leftAsBool === false; - allowedRight = true; - } else if (expr.operator === "??") { - const leftAsNullish = left.asNullish(); - if (leftAsNullish === false) return left.setRange(expr.range); - if (leftAsNullish !== true) return; - returnRight = true; - } else return; - const right = this.evaluateExpression(expr.right); - if (!right) return; - if (returnRight) { - if (left.couldHaveSideEffects()) right.setSideEffects(); - return right.setRange(expr.range); - } +/***/ 46574: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - const asBool = right.asBool(); +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ - if (allowedRight === true && asBool === true) { - return new BasicEvaluatedExpression() - .setRange(expr.range) - .setTruthy(); - } else if (allowedRight === false && asBool === false) { - return new BasicEvaluatedExpression().setRange(expr.range).setFalsy(); - } - }); - const valueAsExpression = (value, expr, sideEffects) => { - switch (typeof value) { - case "boolean": - return new BasicEvaluatedExpression() - .setBoolean(value) - .setSideEffects(sideEffects) - .setRange(expr.range); - case "number": - return new BasicEvaluatedExpression() - .setNumber(value) - .setSideEffects(sideEffects) - .setRange(expr.range); - case "bigint": - return new BasicEvaluatedExpression() - .setBigInt(value) - .setSideEffects(sideEffects) - .setRange(expr.range); - case "string": - return new BasicEvaluatedExpression() - .setString(value) - .setSideEffects(sideEffects) - .setRange(expr.range); - } - }; - this.hooks.evaluate - .for("BinaryExpression") - .tap("JavascriptParser", _expr => { - const expr = /** @type {BinaryExpressionNode} */ (_expr); +/** @typedef {import("http").ServerOptions} HttpServerOptions */ +/** @typedef {import("https").ServerOptions} HttpsServerOptions */ +/** @typedef {import("../../declarations/WebpackOptions").LazyCompilationDefaultBackendOptions} LazyCompilationDefaultBackendOptions */ +/** @typedef {import("../Compiler")} Compiler */ - const handleConstOperation = fn => { - const left = this.evaluateExpression(expr.left); - if (!left || !left.isCompileTimeValue()) return; +/** + * @callback BackendHandler + * @param {Compiler} compiler compiler + * @param {function(Error?, any?): void} callback callback + * @returns {void} + */ - const right = this.evaluateExpression(expr.right); - if (!right || !right.isCompileTimeValue()) return; +/** + * @param {Omit & { client: NonNullable}} options additional options for the backend + * @returns {BackendHandler} backend + */ +module.exports = options => (compiler, callback) => { + const logger = compiler.getInfrastructureLogger("LazyCompilationBackend"); + const activeModules = new Map(); + const prefix = "/lazy-compilation-using-"; - const result = fn( - left.asCompileTimeValue(), - right.asCompileTimeValue() - ); - return valueAsExpression( - result, - expr, - left.couldHaveSideEffects() || right.couldHaveSideEffects() - ); - }; + const isHttps = + options.protocol === "https" || + (typeof options.server === "object" && + ("key" in options.server || "pfx" in options.server)); - const isAlwaysDifferent = (a, b) => - (a === true && b === false) || (a === false && b === true); + const createServer = + typeof options.server === "function" + ? options.server + : (() => { + const http = isHttps ? __webpack_require__(57211) : __webpack_require__(98605); + return http.createServer.bind(http, options.server); + })(); + const listen = + typeof options.listen === "function" + ? options.listen + : server => { + let listen = options.listen; + if (typeof listen === "object" && !("port" in listen)) + listen = { ...listen, port: undefined }; + server.listen(listen); + }; - const handleTemplateStringCompare = (left, right, res, eql) => { - const getPrefix = parts => { - let value = ""; - for (const p of parts) { - const v = p.asString(); - if (v !== undefined) value += v; - else break; - } - return value; - }; - const getSuffix = parts => { - let value = ""; - for (let i = parts.length - 1; i >= 0; i--) { - const v = parts[i].asString(); - if (v !== undefined) value = v + value; - else break; - } - return value; - }; - const leftPrefix = getPrefix(left.parts); - const rightPrefix = getPrefix(right.parts); - const leftSuffix = getSuffix(left.parts); - const rightSuffix = getSuffix(right.parts); - const lenPrefix = Math.min(leftPrefix.length, rightPrefix.length); - const lenSuffix = Math.min(leftSuffix.length, rightSuffix.length); - if ( - leftPrefix.slice(0, lenPrefix) !== - rightPrefix.slice(0, lenPrefix) || - leftSuffix.slice(-lenSuffix) !== rightSuffix.slice(-lenSuffix) - ) { - return res - .setBoolean(!eql) - .setSideEffects( - left.couldHaveSideEffects() || right.couldHaveSideEffects() - ); + const protocol = options.protocol || (isHttps ? "https" : "http"); + + const requestListener = (req, res) => { + const keys = req.url.slice(prefix.length).split("@"); + req.socket.on("close", () => { + setTimeout(() => { + for (const key of keys) { + const oldValue = activeModules.get(key) || 0; + activeModules.set(key, oldValue - 1); + if (oldValue === 1) { + logger.log( + `${key} is no longer in use. Next compilation will skip this module.` + ); } - }; + } + }, 120000); + }); + req.socket.setNoDelay(true); + res.writeHead(200, { + "content-type": "text/event-stream", + "Access-Control-Allow-Origin": "*" + }); + res.write("\n"); + let moduleActivated = false; + for (const key of keys) { + const oldValue = activeModules.get(key) || 0; + activeModules.set(key, oldValue + 1); + if (oldValue === 0) { + logger.log(`${key} is now in use and will be compiled.`); + moduleActivated = true; + } + } + if (moduleActivated && compiler.watching) compiler.watching.invalidate(); + }; - const handleStrictEqualityComparison = eql => { - const left = this.evaluateExpression(expr.left); - if (!left) return; - const right = this.evaluateExpression(expr.right); - if (!right) return; - const res = new BasicEvaluatedExpression(); - res.setRange(expr.range); + const server = /** @type {import("net").Server} */ (createServer()); + server.on("request", requestListener); - const leftConst = left.isCompileTimeValue(); - const rightConst = right.isCompileTimeValue(); + let isClosing = false; + /** @type {Set} */ + const sockets = new Set(); + server.on("connection", socket => { + sockets.add(socket); + socket.on("close", () => { + sockets.delete(socket); + }); + if (isClosing) socket.destroy(); + }); + server.on("clientError", e => { + if (e.message !== "Server is disposing") logger.warn(e); + }); + server.on("listening", err => { + if (err) return callback(err); + const addr = server.address(); + if (typeof addr === "string") throw new Error("addr must not be a string"); + const urlBase = + addr.address === "::" || addr.address === "0.0.0.0" + ? `${protocol}://localhost:${addr.port}` + : addr.family === "IPv6" + ? `${protocol}://[${addr.address}]:${addr.port}` + : `${protocol}://${addr.address}:${addr.port}`; + logger.log( + `Server-Sent-Events server for lazy compilation open at ${urlBase}.` + ); + callback(null, { + dispose(callback) { + isClosing = true; + // Removing the listener is a workaround for a memory leak in node.js + server.off("request", requestListener); + server.close(err => { + callback(err); + }); + for (const socket of sockets) { + socket.destroy(new Error("Server is disposing")); + } + }, + module(originalModule) { + const key = `${encodeURIComponent( + originalModule.identifier().replace(/\\/g, "/").replace(/@/g, "_") + ).replace(/%(2F|3A|24|26|2B|2C|3B|3D|3A)/g, decodeURIComponent)}`; + const active = activeModules.get(key) > 0; + return { + client: `${options.client}?${encodeURIComponent(urlBase + prefix)}`, + data: key, + active + }; + } + }); + }); + listen(server); +}; - if (leftConst && rightConst) { - return res - .setBoolean( - eql === - (left.asCompileTimeValue() === right.asCompileTimeValue()) - ) - .setSideEffects( - left.couldHaveSideEffects() || right.couldHaveSideEffects() - ); - } - if (left.isArray() && right.isArray()) { - return res - .setBoolean(!eql) - .setSideEffects( - left.couldHaveSideEffects() || right.couldHaveSideEffects() - ); - } - if (left.isTemplateString() && right.isTemplateString()) { - return handleTemplateStringCompare(left, right, res, eql); - } +/***/ }), - const leftPrimitive = left.isPrimitiveType(); - const rightPrimitive = right.isPrimitiveType(); +/***/ 7047: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - if ( - // Primitive !== Object or - // compile-time object types are never equal to something at runtime - (leftPrimitive === false && - (leftConst || rightPrimitive === true)) || - (rightPrimitive === false && - (rightConst || leftPrimitive === true)) || - // Different nullish or boolish status also means not equal - isAlwaysDifferent(left.asBool(), right.asBool()) || - isAlwaysDifferent(left.asNullish(), right.asNullish()) - ) { - return res - .setBoolean(!eql) - .setSideEffects( - left.couldHaveSideEffects() || right.couldHaveSideEffects() - ); - } - }; +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ - const handleAbstractEqualityComparison = eql => { - const left = this.evaluateExpression(expr.left); - if (!left) return; - const right = this.evaluateExpression(expr.right); - if (!right) return; - const res = new BasicEvaluatedExpression(); - res.setRange(expr.range); - const leftConst = left.isCompileTimeValue(); - const rightConst = right.isCompileTimeValue(); - if (leftConst && rightConst) { - return res - .setBoolean( - eql === - // eslint-disable-next-line eqeqeq - (left.asCompileTimeValue() == right.asCompileTimeValue()) - ) - .setSideEffects( - left.couldHaveSideEffects() || right.couldHaveSideEffects() - ); - } +const { find } = __webpack_require__(34715); +const { + compareModulesByPreOrderIndexOrIdentifier, + compareModulesByPostOrderIndexOrIdentifier +} = __webpack_require__(26296); - if (left.isArray() && right.isArray()) { - return res - .setBoolean(!eql) - .setSideEffects( - left.couldHaveSideEffects() || right.couldHaveSideEffects() - ); - } - if (left.isTemplateString() && right.isTemplateString()) { - return handleTemplateStringCompare(left, right, res, eql); - } - }; +/** @typedef {import("../Compiler")} Compiler */ - if (expr.operator === "+") { - const left = this.evaluateExpression(expr.left); - if (!left) return; - const right = this.evaluateExpression(expr.right); - if (!right) return; - const res = new BasicEvaluatedExpression(); - if (left.isString()) { - if (right.isString()) { - res.setString(left.string + right.string); - } else if (right.isNumber()) { - res.setString(left.string + right.number); - } else if ( - right.isWrapped() && - right.prefix && - right.prefix.isString() - ) { - // "left" + ("prefix" + inner + "postfix") - // => ("leftPrefix" + inner + "postfix") - res.setWrapped( - new BasicEvaluatedExpression() - .setString(left.string + right.prefix.string) - .setRange(joinRanges(left.range, right.prefix.range)), - right.postfix, - right.wrappedInnerExpressions - ); - } else if (right.isWrapped()) { - // "left" + ([null] + inner + "postfix") - // => ("left" + inner + "postfix") - res.setWrapped( - left, - right.postfix, - right.wrappedInnerExpressions - ); - } else { - // "left" + expr - // => ("left" + expr + "") - res.setWrapped(left, null, [right]); - } - } else if (left.isNumber()) { - if (right.isString()) { - res.setString(left.number + right.string); - } else if (right.isNumber()) { - res.setNumber(left.number + right.number); - } else { - return; - } - } else if (left.isBigInt()) { - if (right.isBigInt()) { - res.setBigInt(left.bigint + right.bigint); - } - } else if (left.isWrapped()) { - if (left.postfix && left.postfix.isString() && right.isString()) { - // ("prefix" + inner + "postfix") + "right" - // => ("prefix" + inner + "postfixRight") - res.setWrapped( - left.prefix, - new BasicEvaluatedExpression() - .setString(left.postfix.string + right.string) - .setRange(joinRanges(left.postfix.range, right.range)), - left.wrappedInnerExpressions - ); - } else if ( - left.postfix && - left.postfix.isString() && - right.isNumber() - ) { - // ("prefix" + inner + "postfix") + 123 - // => ("prefix" + inner + "postfix123") - res.setWrapped( - left.prefix, - new BasicEvaluatedExpression() - .setString(left.postfix.string + right.number) - .setRange(joinRanges(left.postfix.range, right.range)), - left.wrappedInnerExpressions - ); - } else if (right.isString()) { - // ("prefix" + inner + [null]) + "right" - // => ("prefix" + inner + "right") - res.setWrapped(left.prefix, right, left.wrappedInnerExpressions); - } else if (right.isNumber()) { - // ("prefix" + inner + [null]) + 123 - // => ("prefix" + inner + "123") - res.setWrapped( - left.prefix, - new BasicEvaluatedExpression() - .setString(right.number + "") - .setRange(right.range), - left.wrappedInnerExpressions - ); - } else if (right.isWrapped()) { - // ("prefix1" + inner1 + "postfix1") + ("prefix2" + inner2 + "postfix2") - // ("prefix1" + inner1 + "postfix1" + "prefix2" + inner2 + "postfix2") - res.setWrapped( - left.prefix, - right.postfix, - left.wrappedInnerExpressions && - right.wrappedInnerExpressions && - left.wrappedInnerExpressions - .concat(left.postfix ? [left.postfix] : []) - .concat(right.prefix ? [right.prefix] : []) - .concat(right.wrappedInnerExpressions) - ); - } else { - // ("prefix" + inner + postfix) + expr - // => ("prefix" + inner + postfix + expr + [null]) - res.setWrapped( - left.prefix, - null, - left.wrappedInnerExpressions && - left.wrappedInnerExpressions.concat( - left.postfix ? [left.postfix, right] : [right] - ) - ); - } - } else { - if (right.isString()) { - // left + "right" - // => ([null] + left + "right") - res.setWrapped(null, right, [left]); - } else if (right.isWrapped()) { - // left + (prefix + inner + "postfix") - // => ([null] + left + prefix + inner + "postfix") - res.setWrapped( - null, - right.postfix, - right.wrappedInnerExpressions && - (right.prefix ? [left, right.prefix] : [left]).concat( - right.wrappedInnerExpressions - ) - ); - } else { - return; - } - } - if (left.couldHaveSideEffects() || right.couldHaveSideEffects()) - res.setSideEffects(); - res.setRange(expr.range); - return res; - } else if (expr.operator === "-") { - return handleConstOperation((l, r) => l - r); - } else if (expr.operator === "*") { - return handleConstOperation((l, r) => l * r); - } else if (expr.operator === "/") { - return handleConstOperation((l, r) => l / r); - } else if (expr.operator === "**") { - return handleConstOperation((l, r) => l ** r); - } else if (expr.operator === "===") { - return handleStrictEqualityComparison(true); - } else if (expr.operator === "==") { - return handleAbstractEqualityComparison(true); - } else if (expr.operator === "!==") { - return handleStrictEqualityComparison(false); - } else if (expr.operator === "!=") { - return handleAbstractEqualityComparison(false); - } else if (expr.operator === "&") { - return handleConstOperation((l, r) => l & r); - } else if (expr.operator === "|") { - return handleConstOperation((l, r) => l | r); - } else if (expr.operator === "^") { - return handleConstOperation((l, r) => l ^ r); - } else if (expr.operator === ">>>") { - return handleConstOperation((l, r) => l >>> r); - } else if (expr.operator === ">>") { - return handleConstOperation((l, r) => l >> r); - } else if (expr.operator === "<<") { - return handleConstOperation((l, r) => l << r); - } else if (expr.operator === "<") { - return handleConstOperation((l, r) => l < r); - } else if (expr.operator === ">") { - return handleConstOperation((l, r) => l > r); - } else if (expr.operator === "<=") { - return handleConstOperation((l, r) => l <= r); - } else if (expr.operator === ">=") { - return handleConstOperation((l, r) => l >= r); - } - }); - this.hooks.evaluate - .for("UnaryExpression") - .tap("JavascriptParser", _expr => { - const expr = /** @type {UnaryExpressionNode} */ (_expr); +class ChunkModuleIdRangePlugin { + constructor(options) { + this.options = options; + } - const handleConstOperation = fn => { - const argument = this.evaluateExpression(expr.argument); - if (!argument || !argument.isCompileTimeValue()) return; - const result = fn(argument.asCompileTimeValue()); - return valueAsExpression( - result, - expr, - argument.couldHaveSideEffects() + /** + * Apply the plugin + * @param {Compiler} compiler the compiler instance + * @returns {void} + */ + apply(compiler) { + const options = this.options; + compiler.hooks.compilation.tap("ChunkModuleIdRangePlugin", compilation => { + const moduleGraph = compilation.moduleGraph; + compilation.hooks.moduleIds.tap("ChunkModuleIdRangePlugin", modules => { + const chunkGraph = compilation.chunkGraph; + const chunk = find( + compilation.chunks, + chunk => chunk.name === options.name + ); + if (!chunk) { + throw new Error( + `ChunkModuleIdRangePlugin: Chunk with name '${options.name}"' was not found` ); - }; + } - if (expr.operator === "typeof") { - switch (expr.argument.type) { - case "Identifier": { - const res = this.callHooksForName( - this.hooks.evaluateTypeof, - expr.argument.name, - expr - ); - if (res !== undefined) return res; - break; - } - case "MetaProperty": { - const res = this.callHooksForName( - this.hooks.evaluateTypeof, - getRootName(expr.argument), - expr - ); - if (res !== undefined) return res; + let chunkModules; + if (options.order) { + let cmpFn; + switch (options.order) { + case "index": + case "preOrderIndex": + cmpFn = compareModulesByPreOrderIndexOrIdentifier(moduleGraph); break; - } - case "MemberExpression": { - const res = this.callHooksForExpression( - this.hooks.evaluateTypeof, - expr.argument, - expr - ); - if (res !== undefined) return res; + case "index2": + case "postOrderIndex": + cmpFn = compareModulesByPostOrderIndexOrIdentifier(moduleGraph); break; - } - case "ChainExpression": { - const res = this.callHooksForExpression( - this.hooks.evaluateTypeof, - expr.argument.expression, - expr + default: + throw new Error( + "ChunkModuleIdRangePlugin: unexpected value of order" ); - if (res !== undefined) return res; - break; - } - case "FunctionExpression": { - return new BasicEvaluatedExpression() - .setString("function") - .setRange(expr.range); - } - } - const arg = this.evaluateExpression(expr.argument); - if (arg.isUnknown()) return; - if (arg.isString()) { - return new BasicEvaluatedExpression() - .setString("string") - .setRange(expr.range); - } - if (arg.isWrapped()) { - return new BasicEvaluatedExpression() - .setString("string") - .setSideEffects() - .setRange(expr.range); - } - if (arg.isUndefined()) { - return new BasicEvaluatedExpression() - .setString("undefined") - .setRange(expr.range); - } - if (arg.isNumber()) { - return new BasicEvaluatedExpression() - .setString("number") - .setRange(expr.range); - } - if (arg.isBigInt()) { - return new BasicEvaluatedExpression() - .setString("bigint") - .setRange(expr.range); - } - if (arg.isBoolean()) { - return new BasicEvaluatedExpression() - .setString("boolean") - .setRange(expr.range); - } - if (arg.isConstArray() || arg.isRegExp() || arg.isNull()) { - return new BasicEvaluatedExpression() - .setString("object") - .setRange(expr.range); } - if (arg.isArray()) { - return new BasicEvaluatedExpression() - .setString("object") - .setSideEffects(arg.couldHaveSideEffects()) - .setRange(expr.range); + chunkModules = chunkGraph.getOrderedChunkModules(chunk, cmpFn); + } else { + chunkModules = Array.from(modules) + .filter(m => { + return chunkGraph.isModuleInChunk(m, chunk); + }) + .sort(compareModulesByPreOrderIndexOrIdentifier(moduleGraph)); + } + + let currentId = options.start || 0; + for (let i = 0; i < chunkModules.length; i++) { + const m = chunkModules[i]; + if (m.needId && chunkGraph.getModuleId(m) === null) { + chunkGraph.setModuleId(m, currentId++); } - } else if (expr.operator === "!") { - const argument = this.evaluateExpression(expr.argument); - if (!argument) return; - const bool = argument.asBool(); - if (typeof bool !== "boolean") return; - return new BasicEvaluatedExpression() - .setBoolean(!bool) - .setSideEffects(argument.couldHaveSideEffects()) - .setRange(expr.range); - } else if (expr.operator === "~") { - return handleConstOperation(v => ~v); - } else if (expr.operator === "+") { - return handleConstOperation(v => +v); - } else if (expr.operator === "-") { - return handleConstOperation(v => -v); + if (options.end && currentId > options.end) break; } }); - this.hooks.evaluateTypeof.for("undefined").tap("JavascriptParser", expr => { - return new BasicEvaluatedExpression() - .setString("undefined") - .setRange(expr.range); }); - /** - * @param {string} exprType expression type name - * @param {function(ExpressionNode): GetInfoResult | undefined} getInfo get info - * @returns {void} - */ - const tapEvaluateWithVariableInfo = (exprType, getInfo) => { - /** @type {ExpressionNode | undefined} */ - let cachedExpression = undefined; - /** @type {GetInfoResult | undefined} */ - let cachedInfo = undefined; - this.hooks.evaluate.for(exprType).tap("JavascriptParser", expr => { - const expression = /** @type {MemberExpressionNode} */ (expr); + } +} +module.exports = ChunkModuleIdRangePlugin; - const info = getInfo(expr); - if (info !== undefined) { - return this.callHooksForInfoWithFallback( - this.hooks.evaluateIdentifier, - info.name, - name => { - cachedExpression = expression; - cachedInfo = info; - }, - name => { - const hook = this.hooks.evaluateDefinedIdentifier.get(name); - if (hook !== undefined) { - return hook.call(expression); - } - }, - expression - ); - } - }); - this.hooks.evaluate - .for(exprType) - .tap({ name: "JavascriptParser", stage: 100 }, expr => { - const info = cachedExpression === expr ? cachedInfo : getInfo(expr); - if (info !== undefined) { - return new BasicEvaluatedExpression() - .setIdentifier(info.name, info.rootInfo, info.getMembers) - .setRange(expr.range); + +/***/ }), + +/***/ 64801: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Florent Cailhol @ooflorent +*/ + + + +const { compareChunksNatural } = __webpack_require__(26296); +const { + getFullChunkName, + getUsedChunkIds, + assignDeterministicIds +} = __webpack_require__(72922); + +/** @typedef {import("../Compiler")} Compiler */ +/** @typedef {import("../Module")} Module */ + +class DeterministicChunkIdsPlugin { + constructor(options) { + this.options = options || {}; + } + + /** + * Apply the plugin + * @param {Compiler} compiler the compiler instance + * @returns {void} + */ + apply(compiler) { + compiler.hooks.compilation.tap( + "DeterministicChunkIdsPlugin", + compilation => { + compilation.hooks.chunkIds.tap( + "DeterministicChunkIdsPlugin", + chunks => { + const chunkGraph = compilation.chunkGraph; + const context = this.options.context + ? this.options.context + : compiler.context; + const maxLength = this.options.maxLength || 3; + + const compareNatural = compareChunksNatural(chunkGraph); + + const usedIds = getUsedChunkIds(compilation); + assignDeterministicIds( + Array.from(chunks).filter(chunk => { + return chunk.id === null; + }), + chunk => + getFullChunkName(chunk, chunkGraph, context, compiler.root), + compareNatural, + (chunk, id) => { + const size = usedIds.size; + usedIds.add(`${id}`); + if (size === usedIds.size) return false; + chunk.id = id; + chunk.ids = [id]; + return true; + }, + [Math.pow(10, maxLength)], + 10, + usedIds.size + ); } - }); - this.hooks.finish.tap("JavascriptParser", () => { - // Cleanup for GC - cachedExpression = cachedInfo = undefined; - }); - }; - tapEvaluateWithVariableInfo("Identifier", expr => { - const info = this.getVariableInfo( - /** @type {IdentifierNode} */ (expr).name - ); - if ( - typeof info === "string" || - (info instanceof VariableInfo && typeof info.freeName === "string") - ) { - return { name: info, rootInfo: info, getMembers: () => [] }; - } - }); - tapEvaluateWithVariableInfo("ThisExpression", expr => { - const info = this.getVariableInfo("this"); - if ( - typeof info === "string" || - (info instanceof VariableInfo && typeof info.freeName === "string") - ) { - return { name: info, rootInfo: info, getMembers: () => [] }; + ); } - }); - this.hooks.evaluate.for("MetaProperty").tap("JavascriptParser", expr => { - const metaProperty = /** @type {MetaPropertyNode} */ (expr); - - return this.callHooksForName( - this.hooks.evaluateIdentifier, - getRootName(expr), - metaProperty - ); - }); - tapEvaluateWithVariableInfo("MemberExpression", expr => - this.getMemberExpressionInfo( - /** @type {MemberExpressionNode} */ (expr), - ALLOWED_MEMBER_TYPES_EXPRESSION - ) ); + } +} - this.hooks.evaluate.for("CallExpression").tap("JavascriptParser", _expr => { - const expr = /** @type {CallExpressionNode} */ (_expr); - if ( - expr.callee.type !== "MemberExpression" || - expr.callee.property.type !== - (expr.callee.computed ? "Literal" : "Identifier") - ) { - return; - } +module.exports = DeterministicChunkIdsPlugin; - // type Super also possible here - const param = this.evaluateExpression( - /** @type {ExpressionNode} */ (expr.callee.object) - ); - if (!param) return; - const property = - expr.callee.property.type === "Literal" - ? `${expr.callee.property.value}` - : expr.callee.property.name; - const hook = this.hooks.evaluateCallExpressionMember.get(property); - if (hook !== undefined) { - return hook.call(expr, param); + +/***/ }), + +/***/ 84965: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Florent Cailhol @ooflorent +*/ + + + +const { + compareModulesByPreOrderIndexOrIdentifier +} = __webpack_require__(26296); +const { + getUsedModuleIds, + getFullModuleName, + assignDeterministicIds +} = __webpack_require__(72922); + +/** @typedef {import("../Compiler")} Compiler */ +/** @typedef {import("../Module")} Module */ + +class DeterministicModuleIdsPlugin { + constructor(options) { + this.options = options || {}; + } + + /** + * Apply the plugin + * @param {Compiler} compiler the compiler instance + * @returns {void} + */ + apply(compiler) { + compiler.hooks.compilation.tap( + "DeterministicModuleIdsPlugin", + compilation => { + compilation.hooks.moduleIds.tap( + "DeterministicModuleIdsPlugin", + modules => { + const chunkGraph = compilation.chunkGraph; + const context = this.options.context + ? this.options.context + : compiler.context; + const maxLength = this.options.maxLength || 3; + + const usedIds = getUsedModuleIds(compilation); + assignDeterministicIds( + Array.from(modules).filter(module => { + if (!module.needId) return false; + if (chunkGraph.getNumberOfModuleChunks(module) === 0) + return false; + return chunkGraph.getModuleId(module) === null; + }), + module => getFullModuleName(module, context, compiler.root), + compareModulesByPreOrderIndexOrIdentifier( + compilation.moduleGraph + ), + (module, id) => { + const size = usedIds.size; + usedIds.add(`${id}`); + if (size === usedIds.size) return false; + chunkGraph.setModuleId(module, id); + return true; + }, + [Math.pow(10, maxLength)], + 10, + usedIds.size + ); + } + ); } - }); - this.hooks.evaluateCallExpressionMember - .for("indexOf") - .tap("JavascriptParser", (expr, param) => { - if (!param.isString()) return; - if (expr.arguments.length === 0) return; - const [arg1, arg2] = expr.arguments; - if (arg1.type === "SpreadElement") return; - const arg1Eval = this.evaluateExpression(arg1); - if (!arg1Eval.isString()) return; - const arg1Value = arg1Eval.string; + ); + } +} - let result; - if (arg2) { - if (arg2.type === "SpreadElement") return; - const arg2Eval = this.evaluateExpression(arg2); - if (!arg2Eval.isNumber()) return; - result = param.string.indexOf(arg1Value, arg2Eval.number); - } else { - result = param.string.indexOf(arg1Value); - } - return new BasicEvaluatedExpression() - .setNumber(result) - .setSideEffects(param.couldHaveSideEffects()) - .setRange(expr.range); - }); - this.hooks.evaluateCallExpressionMember - .for("replace") - .tap("JavascriptParser", (expr, param) => { - if (!param.isString()) return; - if (expr.arguments.length !== 2) return; - if (expr.arguments[0].type === "SpreadElement") return; - if (expr.arguments[1].type === "SpreadElement") return; - let arg1 = this.evaluateExpression(expr.arguments[0]); - let arg2 = this.evaluateExpression(expr.arguments[1]); - if (!arg1.isString() && !arg1.isRegExp()) return; - const arg1Value = arg1.regExp || arg1.string; - if (!arg2.isString()) return; - const arg2Value = arg2.string; - return new BasicEvaluatedExpression() - .setString(param.string.replace(arg1Value, arg2Value)) - .setSideEffects(param.couldHaveSideEffects()) - .setRange(expr.range); +module.exports = DeterministicModuleIdsPlugin; + + +/***/ }), + +/***/ 83635: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + +"use strict"; +/* module decorator */ module = __webpack_require__.nmd(module); +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ + + + +const { + compareModulesByPreOrderIndexOrIdentifier +} = __webpack_require__(26296); +const createSchemaValidation = __webpack_require__(77695); +const createHash = __webpack_require__(24123); +const { getUsedModuleIds, getFullModuleName } = __webpack_require__(72922); + +/** @typedef {import("../../declarations/plugins/HashedModuleIdsPlugin").HashedModuleIdsPluginOptions} HashedModuleIdsPluginOptions */ + +const validate = createSchemaValidation( + __webpack_require__(168), + () => __webpack_require__(72864), + { + name: "Hashed Module Ids Plugin", + baseDataPath: "options" + } +); + +class HashedModuleIdsPlugin { + /** + * @param {HashedModuleIdsPluginOptions=} options options object + */ + constructor(options = {}) { + validate(options); + + /** @type {HashedModuleIdsPluginOptions} */ + this.options = { + context: null, + hashFunction: "md4", + hashDigest: "base64", + hashDigestLength: 4, + ...options + }; + } + + apply(compiler) { + const options = this.options; + compiler.hooks.compilation.tap("HashedModuleIdsPlugin", compilation => { + compilation.hooks.moduleIds.tap("HashedModuleIdsPlugin", modules => { + const chunkGraph = compilation.chunkGraph; + const context = this.options.context + ? this.options.context + : compiler.context; + + const usedIds = getUsedModuleIds(compilation); + const modulesInNaturalOrder = Array.from(modules) + .filter(m => { + if (!m.needId) return false; + if (chunkGraph.getNumberOfModuleChunks(m) === 0) return false; + return chunkGraph.getModuleId(module) === null; + }) + .sort( + compareModulesByPreOrderIndexOrIdentifier(compilation.moduleGraph) + ); + for (const module of modulesInNaturalOrder) { + const ident = getFullModuleName(module, context, compiler.root); + const hash = createHash(options.hashFunction); + hash.update(ident || ""); + const hashId = /** @type {string} */ ( + hash.digest(options.hashDigest) + ); + let len = options.hashDigestLength; + while (usedIds.has(hashId.substr(0, len))) len++; + const moduleId = hashId.substr(0, len); + chunkGraph.setModuleId(module, moduleId); + usedIds.add(moduleId); + } }); - ["substr", "substring", "slice"].forEach(fn => { - this.hooks.evaluateCallExpressionMember - .for(fn) - .tap("JavascriptParser", (expr, param) => { - if (!param.isString()) return; - let arg1; - let result, - str = param.string; - switch (expr.arguments.length) { - case 1: - if (expr.arguments[0].type === "SpreadElement") return; - arg1 = this.evaluateExpression(expr.arguments[0]); - if (!arg1.isNumber()) return; - result = str[fn](arg1.number); - break; - case 2: { - if (expr.arguments[0].type === "SpreadElement") return; - if (expr.arguments[1].type === "SpreadElement") return; - arg1 = this.evaluateExpression(expr.arguments[0]); - const arg2 = this.evaluateExpression(expr.arguments[1]); - if (!arg1.isNumber()) return; - if (!arg2.isNumber()) return; - result = str[fn](arg1.number, arg2.number); - break; - } - default: - return; - } - return new BasicEvaluatedExpression() - .setString(result) - .setSideEffects(param.couldHaveSideEffects()) - .setRange(expr.range); - }); }); + } +} - /** - * @param {"cooked" | "raw"} kind kind of values to get - * @param {TemplateLiteralNode} templateLiteralExpr TemplateLiteral expr - * @returns {{quasis: BasicEvaluatedExpression[], parts: BasicEvaluatedExpression[]}} Simplified template - */ - const getSimplifiedTemplateResult = (kind, templateLiteralExpr) => { - /** @type {BasicEvaluatedExpression[]} */ - const quasis = []; - /** @type {BasicEvaluatedExpression[]} */ - const parts = []; +module.exports = HashedModuleIdsPlugin; - for (let i = 0; i < templateLiteralExpr.quasis.length; i++) { - const quasiExpr = templateLiteralExpr.quasis[i]; - const quasi = quasiExpr.value[kind]; - if (i > 0) { - const prevExpr = parts[parts.length - 1]; - const expr = this.evaluateExpression( - templateLiteralExpr.expressions[i - 1] - ); - const exprAsString = expr.asString(); - if ( - typeof exprAsString === "string" && - !expr.couldHaveSideEffects() - ) { - // We can merge quasi + expr + quasi when expr - // is a const string +/***/ }), - prevExpr.setString(prevExpr.string + exprAsString + quasi); - prevExpr.setRange([prevExpr.range[0], quasiExpr.range[1]]); - // We unset the expression as it doesn't match to a single expression - prevExpr.setExpression(undefined); - continue; - } - parts.push(expr); - } +/***/ 72922: +/***/ (function(__unused_webpack_module, exports, __webpack_require__) { - const part = new BasicEvaluatedExpression() - .setString(quasi) - .setRange(quasiExpr.range) - .setExpression(quasiExpr); - quasis.push(part); - parts.push(part); - } - return { - quasis, - parts - }; - }; +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ - this.hooks.evaluate - .for("TemplateLiteral") - .tap("JavascriptParser", _node => { - const node = /** @type {TemplateLiteralNode} */ (_node); - const { quasis, parts } = getSimplifiedTemplateResult("cooked", node); - if (parts.length === 1) { - return parts[0].setRange(node.range); - } - return new BasicEvaluatedExpression() - .setTemplateString(quasis, parts, "cooked") - .setRange(node.range); - }); - this.hooks.evaluate - .for("TaggedTemplateExpression") - .tap("JavascriptParser", _node => { - const node = /** @type {TaggedTemplateExpressionNode} */ (_node); - const tag = this.evaluateExpression(node.tag); - if (tag.isIdentifier() && tag.identifier !== "String.raw") return; - const { quasis, parts } = getSimplifiedTemplateResult( - "raw", - node.quasi - ); - return new BasicEvaluatedExpression() - .setTemplateString(quasis, parts, "raw") - .setRange(node.range); - }); +const createHash = __webpack_require__(24123); +const { makePathsRelative } = __webpack_require__(96236); +const numberHash = __webpack_require__(91679); - this.hooks.evaluateCallExpressionMember - .for("concat") - .tap("JavascriptParser", (expr, param) => { - if (!param.isString() && !param.isWrapped()) return; +/** @typedef {import("../Chunk")} Chunk */ +/** @typedef {import("../ChunkGraph")} ChunkGraph */ +/** @typedef {import("../Compilation")} Compilation */ +/** @typedef {import("../Module")} Module */ +/** @typedef {typeof import("../util/Hash")} Hash */ - let stringSuffix = null; - let hasUnknownParams = false; - const innerExpressions = []; - for (let i = expr.arguments.length - 1; i >= 0; i--) { - const arg = expr.arguments[i]; - if (arg.type === "SpreadElement") return; - const argExpr = this.evaluateExpression(arg); - if ( - hasUnknownParams || - (!argExpr.isString() && !argExpr.isNumber()) - ) { - hasUnknownParams = true; - innerExpressions.push(argExpr); - continue; - } +/** + * @param {string} str string to hash + * @param {number} len max length of the hash + * @param {string | Hash} hashFunction hash function to use + * @returns {string} hash + */ +const getHash = (str, len, hashFunction) => { + const hash = createHash(hashFunction); + hash.update(str); + const digest = /** @type {string} */ (hash.digest("hex")); + return digest.substr(0, len); +}; - const value = argExpr.isString() - ? argExpr.string - : "" + argExpr.number; +/** + * @param {string} str the string + * @returns {string} string prefixed by an underscore if it is a number + */ +const avoidNumber = str => { + // max length of a number is 21 chars, bigger numbers a written as "...e+xx" + if (str.length > 21) return str; + const firstChar = str.charCodeAt(0); + // skip everything that doesn't look like a number + // charCodes: "-": 45, "1": 49, "9": 57 + if (firstChar < 49) { + if (firstChar !== 45) return str; + } else if (firstChar > 57) { + return str; + } + if (str === +str + "") { + return `_${str}`; + } + return str; +}; - const newString = value + (stringSuffix ? stringSuffix.string : ""); - const newRange = [ - argExpr.range[0], - (stringSuffix || argExpr).range[1] - ]; - stringSuffix = new BasicEvaluatedExpression() - .setString(newString) - .setSideEffects( - (stringSuffix && stringSuffix.couldHaveSideEffects()) || - argExpr.couldHaveSideEffects() - ) - .setRange(newRange); - } +/** + * @param {string} request the request + * @returns {string} id representation + */ +const requestToId = request => { + return request + .replace(/^(\.\.?\/)+/, "") + .replace(/(^[.-]|[^a-zA-Z0-9_-])+/g, "_"); +}; +exports.requestToId = requestToId; - if (hasUnknownParams) { - const prefix = param.isString() ? param : param.prefix; - const inner = - param.isWrapped() && param.wrappedInnerExpressions - ? param.wrappedInnerExpressions.concat(innerExpressions.reverse()) - : innerExpressions.reverse(); - return new BasicEvaluatedExpression() - .setWrapped(prefix, stringSuffix, inner) - .setRange(expr.range); - } else if (param.isWrapped()) { - const postfix = stringSuffix || param.postfix; - const inner = param.wrappedInnerExpressions - ? param.wrappedInnerExpressions.concat(innerExpressions.reverse()) - : innerExpressions.reverse(); - return new BasicEvaluatedExpression() - .setWrapped(param.prefix, postfix, inner) - .setRange(expr.range); - } else { - const newString = - param.string + (stringSuffix ? stringSuffix.string : ""); - return new BasicEvaluatedExpression() - .setString(newString) - .setSideEffects( - (stringSuffix && stringSuffix.couldHaveSideEffects()) || - param.couldHaveSideEffects() - ) - .setRange(expr.range); - } - }); - this.hooks.evaluateCallExpressionMember - .for("split") - .tap("JavascriptParser", (expr, param) => { - if (!param.isString()) return; - if (expr.arguments.length !== 1) return; - if (expr.arguments[0].type === "SpreadElement") return; - let result; - const arg = this.evaluateExpression(expr.arguments[0]); - if (arg.isString()) { - result = param.string.split(arg.string); - } else if (arg.isRegExp()) { - result = param.string.split(arg.regExp); - } else { - return; - } - return new BasicEvaluatedExpression() - .setArray(result) - .setSideEffects(param.couldHaveSideEffects()) - .setRange(expr.range); - }); - this.hooks.evaluate - .for("ConditionalExpression") - .tap("JavascriptParser", _expr => { - const expr = /** @type {ConditionalExpressionNode} */ (_expr); +/** + * @param {string} string the string + * @param {string} delimiter separator for string and hash + * @param {string | Hash} hashFunction hash function to use + * @returns {string} string with limited max length to 100 chars + */ +const shortenLongString = (string, delimiter, hashFunction) => { + if (string.length < 100) return string; + return ( + string.slice(0, 100 - 6 - delimiter.length) + + delimiter + + getHash(string, 6, hashFunction) + ); +}; - const condition = this.evaluateExpression(expr.test); - const conditionValue = condition.asBool(); - let res; - if (conditionValue === undefined) { - const consequent = this.evaluateExpression(expr.consequent); - const alternate = this.evaluateExpression(expr.alternate); - if (!consequent || !alternate) return; - res = new BasicEvaluatedExpression(); - if (consequent.isConditional()) { - res.setOptions(consequent.options); - } else { - res.setOptions([consequent]); - } - if (alternate.isConditional()) { - res.addOptions(alternate.options); - } else { - res.addOptions([alternate]); - } - } else { - res = this.evaluateExpression( - conditionValue ? expr.consequent : expr.alternate - ); - if (condition.couldHaveSideEffects()) res.setSideEffects(); - } - res.setRange(expr.range); - return res; - }); - this.hooks.evaluate - .for("ArrayExpression") - .tap("JavascriptParser", _expr => { - const expr = /** @type {ArrayExpressionNode} */ (_expr); +/** + * @param {Module} module the module + * @param {string} context context directory + * @param {Object=} associatedObjectForCache an object to which the cache will be attached + * @returns {string} short module name + */ +const getShortModuleName = (module, context, associatedObjectForCache) => { + const libIdent = module.libIdent({ context, associatedObjectForCache }); + if (libIdent) return avoidNumber(libIdent); + const nameForCondition = module.nameForCondition(); + if (nameForCondition) + return avoidNumber( + makePathsRelative(context, nameForCondition, associatedObjectForCache) + ); + return ""; +}; +exports.getShortModuleName = getShortModuleName; - const items = expr.elements.map(element => { - return ( - element !== null && - element.type !== "SpreadElement" && - this.evaluateExpression(element) - ); - }); - if (!items.every(Boolean)) return; - return new BasicEvaluatedExpression() - .setItems(items) - .setRange(expr.range); - }); - this.hooks.evaluate - .for("ChainExpression") - .tap("JavascriptParser", _expr => { - const expr = /** @type {ChainExpressionNode} */ (_expr); - /** @type {ExpressionNode[]} */ - const optionalExpressionsStack = []; - /** @type {ExpressionNode|SuperNode} */ - let next = expr.expression; +/** + * @param {string} shortName the short name + * @param {Module} module the module + * @param {string} context context directory + * @param {string | Hash} hashFunction hash function to use + * @param {Object=} associatedObjectForCache an object to which the cache will be attached + * @returns {string} long module name + */ +const getLongModuleName = ( + shortName, + module, + context, + hashFunction, + associatedObjectForCache +) => { + const fullName = getFullModuleName(module, context, associatedObjectForCache); + return `${shortName}?${getHash(fullName, 4, hashFunction)}`; +}; +exports.getLongModuleName = getLongModuleName; - while ( - next.type === "MemberExpression" || - next.type === "CallExpression" - ) { - if (next.type === "MemberExpression") { - if (next.optional) { - // SuperNode can not be optional - optionalExpressionsStack.push( - /** @type {ExpressionNode} */ (next.object) - ); - } - next = next.object; - } else { - if (next.optional) { - // SuperNode can not be optional - optionalExpressionsStack.push( - /** @type {ExpressionNode} */ (next.callee) - ); - } - next = next.callee; - } - } +/** + * @param {Module} module the module + * @param {string} context context directory + * @param {Object=} associatedObjectForCache an object to which the cache will be attached + * @returns {string} full module name + */ +const getFullModuleName = (module, context, associatedObjectForCache) => { + return makePathsRelative( + context, + module.identifier(), + associatedObjectForCache + ); +}; +exports.getFullModuleName = getFullModuleName; + +/** + * @param {Chunk} chunk the chunk + * @param {ChunkGraph} chunkGraph the chunk graph + * @param {string} context context directory + * @param {string} delimiter delimiter for names + * @param {string | Hash} hashFunction hash function to use + * @param {Object=} associatedObjectForCache an object to which the cache will be attached + * @returns {string} short chunk name + */ +const getShortChunkName = ( + chunk, + chunkGraph, + context, + delimiter, + hashFunction, + associatedObjectForCache +) => { + const modules = chunkGraph.getChunkRootModules(chunk); + const shortModuleNames = modules.map(m => + requestToId(getShortModuleName(m, context, associatedObjectForCache)) + ); + chunk.idNameHints.sort(); + const chunkName = Array.from(chunk.idNameHints) + .concat(shortModuleNames) + .filter(Boolean) + .join(delimiter); + return shortenLongString(chunkName, delimiter, hashFunction); +}; +exports.getShortChunkName = getShortChunkName; + +/** + * @param {Chunk} chunk the chunk + * @param {ChunkGraph} chunkGraph the chunk graph + * @param {string} context context directory + * @param {string} delimiter delimiter for names + * @param {string | Hash} hashFunction hash function to use + * @param {Object=} associatedObjectForCache an object to which the cache will be attached + * @returns {string} short chunk name + */ +const getLongChunkName = ( + chunk, + chunkGraph, + context, + delimiter, + hashFunction, + associatedObjectForCache +) => { + const modules = chunkGraph.getChunkRootModules(chunk); + const shortModuleNames = modules.map(m => + requestToId(getShortModuleName(m, context, associatedObjectForCache)) + ); + const longModuleNames = modules.map(m => + requestToId( + getLongModuleName("", m, context, hashFunction, associatedObjectForCache) + ) + ); + chunk.idNameHints.sort(); + const chunkName = Array.from(chunk.idNameHints) + .concat(shortModuleNames, longModuleNames) + .filter(Boolean) + .join(delimiter); + return shortenLongString(chunkName, delimiter, hashFunction); +}; +exports.getLongChunkName = getLongChunkName; + +/** + * @param {Chunk} chunk the chunk + * @param {ChunkGraph} chunkGraph the chunk graph + * @param {string} context context directory + * @param {Object=} associatedObjectForCache an object to which the cache will be attached + * @returns {string} full chunk name + */ +const getFullChunkName = ( + chunk, + chunkGraph, + context, + associatedObjectForCache +) => { + if (chunk.name) return chunk.name; + const modules = chunkGraph.getChunkRootModules(chunk); + const fullModuleNames = modules.map(m => + makePathsRelative(context, m.identifier(), associatedObjectForCache) + ); + return fullModuleNames.join(); +}; +exports.getFullChunkName = getFullChunkName; + +/** + * @template K + * @template V + * @param {Map} map a map from key to values + * @param {K} key key + * @param {V} value value + * @returns {void} + */ +const addToMapOfItems = (map, key, value) => { + let array = map.get(key); + if (array === undefined) { + array = []; + map.set(key, array); + } + array.push(value); +}; + +/** + * @param {Compilation} compilation the compilation + * @returns {Set} used module ids as strings + */ +const getUsedModuleIds = compilation => { + const chunkGraph = compilation.chunkGraph; - while (optionalExpressionsStack.length > 0) { - const expression = optionalExpressionsStack.pop(); - const evaluated = this.evaluateExpression(expression); + /** @type {Set} */ + const usedIds = new Set(); + if (compilation.usedModuleIds) { + for (const id of compilation.usedModuleIds) { + usedIds.add(id + ""); + } + } - if (evaluated && evaluated.asNullish()) { - return evaluated.setRange(_expr.range); - } - } - return this.evaluateExpression(expr.expression); - }); + for (const module of compilation.modules) { + const moduleId = chunkGraph.getModuleId(module); + if (moduleId !== null) { + usedIds.add(moduleId + ""); + } } - getRenameIdentifier(expr) { - const result = this.evaluateExpression(expr); - if (result && result.isIdentifier()) { - return result.identifier; + return usedIds; +}; +exports.getUsedModuleIds = getUsedModuleIds; + +/** + * @param {Compilation} compilation the compilation + * @returns {Set} used chunk ids as strings + */ +const getUsedChunkIds = compilation => { + /** @type {Set} */ + const usedIds = new Set(); + if (compilation.usedChunkIds) { + for (const id of compilation.usedChunkIds) { + usedIds.add(id + ""); } } - /** - * @param {ClassExpressionNode | ClassDeclarationNode} classy a class node - * @returns {void} - */ - walkClass(classy) { - if (classy.superClass) { - if (!this.hooks.classExtendsExpression.call(classy.superClass, classy)) { - this.walkExpression(classy.superClass); - } + for (const chunk of compilation.chunks) { + const chunkId = chunk.id; + if (chunkId !== null) { + usedIds.add(chunkId + ""); } - if (classy.body && classy.body.type === "ClassBody") { - for (const classElement of /** @type {TODO} */ (classy.body.body)) { - if (!this.hooks.classBodyElement.call(classElement, classy)) { - if (classElement.computed && classElement.key) { - this.walkExpression(classElement.key); - } - if (classElement.value) { - if ( - !this.hooks.classBodyValue.call( - classElement.value, - classElement, - classy - ) - ) { - const wasTopLevel = this.scope.topLevelScope; - this.scope.topLevelScope = false; - this.walkExpression(classElement.value); - this.scope.topLevelScope = wasTopLevel; - } - } - } + } + + return usedIds; +}; +exports.getUsedChunkIds = getUsedChunkIds; + +/** + * @template T + * @param {Iterable} items list of items to be named + * @param {function(T): string} getShortName get a short name for an item + * @param {function(T, string): string} getLongName get a long name for an item + * @param {function(T, T): -1|0|1} comparator order of items + * @param {Set} usedIds already used ids, will not be assigned + * @param {function(T, string): void} assignName assign a name to an item + * @returns {T[]} list of items without a name + */ +const assignNames = ( + items, + getShortName, + getLongName, + comparator, + usedIds, + assignName +) => { + /** @type {Map} */ + const nameToItems = new Map(); + + for (const item of items) { + const name = getShortName(item); + addToMapOfItems(nameToItems, name, item); + } + + /** @type {Map} */ + const nameToItems2 = new Map(); + + for (const [name, items] of nameToItems) { + if (items.length > 1 || !name) { + for (const item of items) { + const longName = getLongName(item, name); + addToMapOfItems(nameToItems2, longName, item); } + } else { + addToMapOfItems(nameToItems2, name, items[0]); } } - // Pre walking iterates the scope for variable declarations - preWalkStatements(statements) { - for (let index = 0, len = statements.length; index < len; index++) { - const statement = statements[index]; - this.preWalkStatement(statement); + /** @type {T[]} */ + const unnamedItems = []; + + for (const [name, items] of nameToItems2) { + if (!name) { + for (const item of items) { + unnamedItems.push(item); + } + } else if (items.length === 1 && !usedIds.has(name)) { + assignName(items[0], name); + usedIds.add(name); + } else { + items.sort(comparator); + let i = 0; + for (const item of items) { + while (nameToItems2.has(name + i) && usedIds.has(name + i)) i++; + assignName(item, name + i); + usedIds.add(name + i); + i++; + } } } - // Block pre walking iterates the scope for block variable declarations - blockPreWalkStatements(statements) { - for (let index = 0, len = statements.length; index < len; index++) { - const statement = statements[index]; - this.blockPreWalkStatement(statement); + unnamedItems.sort(comparator); + return unnamedItems; +}; +exports.assignNames = assignNames; + +/** + * @template T + * @param {T[]} items list of items to be named + * @param {function(T): string} getName get a name for an item + * @param {function(T, T): -1|0|1} comparator order of items + * @param {function(T, number): boolean} assignId assign an id to an item + * @param {number[]} ranges usable ranges for ids + * @param {number} expandFactor factor to create more ranges + * @param {number} extraSpace extra space to allocate, i. e. when some ids are already used + * @returns {void} + */ +const assignDeterministicIds = ( + items, + getName, + comparator, + assignId, + ranges = [10], + expandFactor = 10, + extraSpace = 0 +) => { + items.sort(comparator); + + // max 5% fill rate + const optimalRange = Math.min( + Math.ceil(items.length * 20) + extraSpace, + Number.MAX_SAFE_INTEGER + ); + + let i = 0; + let range = ranges[i]; + while (range < optimalRange) { + i++; + if (i < ranges.length) { + range = Math.min(ranges[i], Number.MAX_SAFE_INTEGER); + } else { + range = Math.min(range * expandFactor, Number.MAX_SAFE_INTEGER); } } - // Walking iterates the statements and expressions and processes them - walkStatements(statements) { - for (let index = 0, len = statements.length; index < len; index++) { - const statement = statements[index]; - this.walkStatement(statement); - } + for (const item of items) { + const ident = getName(item); + let id; + let i = 0; + do { + id = numberHash(ident + i++, range); + } while (!assignId(item, id)); } +}; +exports.assignDeterministicIds = assignDeterministicIds; - preWalkStatement(statement) { - this.statementPath.push(statement); - if (this.hooks.preStatement.call(statement)) { - this.prevStatement = this.statementPath.pop(); - return; - } - switch (statement.type) { - case "BlockStatement": - this.preWalkBlockStatement(statement); - break; - case "DoWhileStatement": - this.preWalkDoWhileStatement(statement); - break; - case "ForInStatement": - this.preWalkForInStatement(statement); - break; - case "ForOfStatement": - this.preWalkForOfStatement(statement); - break; - case "ForStatement": - this.preWalkForStatement(statement); - break; - case "FunctionDeclaration": - this.preWalkFunctionDeclaration(statement); - break; - case "IfStatement": - this.preWalkIfStatement(statement); - break; - case "LabeledStatement": - this.preWalkLabeledStatement(statement); - break; - case "SwitchStatement": - this.preWalkSwitchStatement(statement); - break; - case "TryStatement": - this.preWalkTryStatement(statement); - break; - case "VariableDeclaration": - this.preWalkVariableDeclaration(statement); - break; - case "WhileStatement": - this.preWalkWhileStatement(statement); - break; - case "WithStatement": - this.preWalkWithStatement(statement); - break; - } - this.prevStatement = this.statementPath.pop(); +/** + * @param {Iterable} modules the modules + * @param {Compilation} compilation the compilation + * @returns {void} + */ +const assignAscendingModuleIds = (modules, compilation) => { + const chunkGraph = compilation.chunkGraph; + + const usedIds = getUsedModuleIds(compilation); + + let nextId = 0; + let assignId; + if (usedIds.size > 0) { + assignId = module => { + if (chunkGraph.getModuleId(module) === null) { + while (usedIds.has(nextId + "")) nextId++; + chunkGraph.setModuleId(module, nextId++); + } + }; + } else { + assignId = module => { + if (chunkGraph.getModuleId(module) === null) { + chunkGraph.setModuleId(module, nextId++); + } + }; } + for (const module of modules) { + assignId(module); + } +}; +exports.assignAscendingModuleIds = assignAscendingModuleIds; - blockPreWalkStatement(statement) { - this.statementPath.push(statement); - if (this.hooks.blockPreStatement.call(statement)) { - this.prevStatement = this.statementPath.pop(); - return; +/** + * @param {Iterable} chunks the chunks + * @param {Compilation} compilation the compilation + * @returns {void} + */ +const assignAscendingChunkIds = (chunks, compilation) => { + const usedIds = getUsedChunkIds(compilation); + + let nextId = 0; + if (usedIds.size > 0) { + for (const chunk of chunks) { + if (chunk.id === null) { + while (usedIds.has(nextId + "")) nextId++; + chunk.id = nextId; + chunk.ids = [nextId]; + nextId++; + } } - switch (statement.type) { - case "ImportDeclaration": - this.blockPreWalkImportDeclaration(statement); - break; - case "ExportAllDeclaration": - this.blockPreWalkExportAllDeclaration(statement); - break; - case "ExportDefaultDeclaration": - this.blockPreWalkExportDefaultDeclaration(statement); - break; - case "ExportNamedDeclaration": - this.blockPreWalkExportNamedDeclaration(statement); - break; - case "VariableDeclaration": - this.blockPreWalkVariableDeclaration(statement); - break; - case "ClassDeclaration": - this.blockPreWalkClassDeclaration(statement); - break; + } else { + for (const chunk of chunks) { + if (chunk.id === null) { + chunk.id = nextId; + chunk.ids = [nextId]; + nextId++; + } } - this.prevStatement = this.statementPath.pop(); } +}; +exports.assignAscendingChunkIds = assignAscendingChunkIds; - walkStatement(statement) { - this.statementPath.push(statement); - if (this.hooks.statement.call(statement) !== undefined) { - this.prevStatement = this.statementPath.pop(); - return; - } - switch (statement.type) { - case "BlockStatement": - this.walkBlockStatement(statement); - break; - case "ClassDeclaration": - this.walkClassDeclaration(statement); - break; - case "DoWhileStatement": - this.walkDoWhileStatement(statement); - break; - case "ExportDefaultDeclaration": - this.walkExportDefaultDeclaration(statement); - break; - case "ExportNamedDeclaration": - this.walkExportNamedDeclaration(statement); - break; - case "ExpressionStatement": - this.walkExpressionStatement(statement); - break; - case "ForInStatement": - this.walkForInStatement(statement); - break; - case "ForOfStatement": - this.walkForOfStatement(statement); - break; - case "ForStatement": - this.walkForStatement(statement); - break; - case "FunctionDeclaration": - this.walkFunctionDeclaration(statement); - break; - case "IfStatement": - this.walkIfStatement(statement); - break; - case "LabeledStatement": - this.walkLabeledStatement(statement); - break; - case "ReturnStatement": - this.walkReturnStatement(statement); - break; - case "SwitchStatement": - this.walkSwitchStatement(statement); - break; - case "ThrowStatement": - this.walkThrowStatement(statement); - break; - case "TryStatement": - this.walkTryStatement(statement); - break; - case "VariableDeclaration": - this.walkVariableDeclaration(statement); - break; - case "WhileStatement": - this.walkWhileStatement(statement); - break; - case "WithStatement": - this.walkWithStatement(statement); - break; - } - this.prevStatement = this.statementPath.pop(); + +/***/ }), + +/***/ 30483: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ + + + +const { compareChunksNatural } = __webpack_require__(26296); +const { + getShortChunkName, + getLongChunkName, + assignNames, + getUsedChunkIds, + assignAscendingChunkIds +} = __webpack_require__(72922); + +/** @typedef {import("../Chunk")} Chunk */ +/** @typedef {import("../Compiler")} Compiler */ +/** @typedef {import("../Module")} Module */ + +class NamedChunkIdsPlugin { + constructor(options) { + this.delimiter = (options && options.delimiter) || "-"; + this.context = options && options.context; + } + + /** + * Apply the plugin + * @param {Compiler} compiler the compiler instance + * @returns {void} + */ + apply(compiler) { + compiler.hooks.compilation.tap("NamedChunkIdsPlugin", compilation => { + const { hashFunction } = compilation.outputOptions; + compilation.hooks.chunkIds.tap("NamedChunkIdsPlugin", chunks => { + const chunkGraph = compilation.chunkGraph; + const context = this.context ? this.context : compiler.context; + const delimiter = this.delimiter; + + const unnamedChunks = assignNames( + Array.from(chunks).filter(chunk => { + if (chunk.name) { + chunk.id = chunk.name; + chunk.ids = [chunk.name]; + } + return chunk.id === null; + }), + chunk => + getShortChunkName( + chunk, + chunkGraph, + context, + delimiter, + hashFunction, + compiler.root + ), + chunk => + getLongChunkName( + chunk, + chunkGraph, + context, + delimiter, + hashFunction, + compiler.root + ), + compareChunksNatural(chunkGraph), + getUsedChunkIds(compilation), + (chunk, name) => { + chunk.id = name; + chunk.ids = [name]; + } + ); + if (unnamedChunks.length > 0) { + assignAscendingChunkIds(unnamedChunks, compilation); + } + }); + }); + } +} + +module.exports = NamedChunkIdsPlugin; + + +/***/ }), + +/***/ 88514: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ + + + +const { compareModulesByIdentifier } = __webpack_require__(26296); +const { + getShortModuleName, + getLongModuleName, + assignNames, + getUsedModuleIds, + assignAscendingModuleIds +} = __webpack_require__(72922); + +/** @typedef {import("../Compiler")} Compiler */ +/** @typedef {import("../Module")} Module */ + +class NamedModuleIdsPlugin { + constructor(options) { + this.options = options || {}; } /** - * Walks a statements that is nested within a parent statement - * and can potentially be a non-block statement. - * This enforces the nested statement to never be in ASI position. - * @param {StatementNode} statement the nested statement + * Apply the plugin + * @param {Compiler} compiler the compiler instance * @returns {void} */ - walkNestedStatement(statement) { - this.prevStatement = undefined; - this.walkStatement(statement); - } - - // Real Statements - preWalkBlockStatement(statement) { - this.preWalkStatements(statement.body); - } + apply(compiler) { + const { root } = compiler; + compiler.hooks.compilation.tap("NamedModuleIdsPlugin", compilation => { + const { hashFunction } = compilation.outputOptions; + compilation.hooks.moduleIds.tap("NamedModuleIdsPlugin", modules => { + const chunkGraph = compilation.chunkGraph; + const context = this.options.context + ? this.options.context + : compiler.context; - walkBlockStatement(statement) { - this.inBlockScope(() => { - const body = statement.body; - const prev = this.prevStatement; - this.blockPreWalkStatements(body); - this.prevStatement = prev; - this.walkStatements(body); + const unnamedModules = assignNames( + Array.from(modules).filter(module => { + if (!module.needId) return false; + if (chunkGraph.getNumberOfModuleChunks(module) === 0) return false; + return chunkGraph.getModuleId(module) === null; + }), + m => getShortModuleName(m, context, root), + (m, shortName) => + getLongModuleName(shortName, m, context, hashFunction, root), + compareModulesByIdentifier, + getUsedModuleIds(compilation), + (m, name) => chunkGraph.setModuleId(m, name) + ); + if (unnamedModules.length > 0) { + assignAscendingModuleIds(unnamedModules, compilation); + } + }); }); } +} - walkExpressionStatement(statement) { - this.walkExpression(statement.expression); - } - - preWalkIfStatement(statement) { - this.preWalkStatement(statement.consequent); - if (statement.alternate) { - this.preWalkStatement(statement.alternate); - } - } - - walkIfStatement(statement) { - const result = this.hooks.statementIf.call(statement); - if (result === undefined) { - this.walkExpression(statement.test); - this.walkNestedStatement(statement.consequent); - if (statement.alternate) { - this.walkNestedStatement(statement.alternate); - } - } else { - if (result) { - this.walkNestedStatement(statement.consequent); - } else if (statement.alternate) { - this.walkNestedStatement(statement.alternate); - } - } - } +module.exports = NamedModuleIdsPlugin; - preWalkLabeledStatement(statement) { - this.preWalkStatement(statement.body); - } - walkLabeledStatement(statement) { - const hook = this.hooks.label.get(statement.label.name); - if (hook !== undefined) { - const result = hook.call(statement); - if (result === true) return; - } - this.walkNestedStatement(statement.body); - } +/***/ }), - preWalkWithStatement(statement) { - this.preWalkStatement(statement.body); - } +/***/ 18326: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - walkWithStatement(statement) { - this.walkExpression(statement.object); - this.walkNestedStatement(statement.body); - } +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ - preWalkSwitchStatement(statement) { - this.preWalkSwitchCases(statement.cases); - } - walkSwitchStatement(statement) { - this.walkExpression(statement.discriminant); - this.walkSwitchCases(statement.cases); - } - walkTerminatingStatement(statement) { - if (statement.argument) this.walkExpression(statement.argument); - } +const { compareChunksNatural } = __webpack_require__(26296); +const { assignAscendingChunkIds } = __webpack_require__(72922); - walkReturnStatement(statement) { - this.walkTerminatingStatement(statement); - } +/** @typedef {import("../Chunk")} Chunk */ +/** @typedef {import("../Compiler")} Compiler */ +/** @typedef {import("../Module")} Module */ - walkThrowStatement(statement) { - this.walkTerminatingStatement(statement); +class NaturalChunkIdsPlugin { + /** + * Apply the plugin + * @param {Compiler} compiler the compiler instance + * @returns {void} + */ + apply(compiler) { + compiler.hooks.compilation.tap("NaturalChunkIdsPlugin", compilation => { + compilation.hooks.chunkIds.tap("NaturalChunkIdsPlugin", chunks => { + const chunkGraph = compilation.chunkGraph; + const compareNatural = compareChunksNatural(chunkGraph); + const chunksInNaturalOrder = Array.from(chunks).sort(compareNatural); + assignAscendingChunkIds(chunksInNaturalOrder, compilation); + }); + }); } +} - preWalkTryStatement(statement) { - this.preWalkStatement(statement.block); - if (statement.handler) this.preWalkCatchClause(statement.handler); - if (statement.finializer) this.preWalkStatement(statement.finializer); - } +module.exports = NaturalChunkIdsPlugin; - walkTryStatement(statement) { - if (this.scope.inTry) { - this.walkStatement(statement.block); - } else { - this.scope.inTry = true; - this.walkStatement(statement.block); - this.scope.inTry = false; - } - if (statement.handler) this.walkCatchClause(statement.handler); - if (statement.finalizer) this.walkStatement(statement.finalizer); - } - preWalkWhileStatement(statement) { - this.preWalkStatement(statement.body); - } +/***/ }), - walkWhileStatement(statement) { - this.walkExpression(statement.test); - this.walkNestedStatement(statement.body); - } +/***/ 96338: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - preWalkDoWhileStatement(statement) { - this.preWalkStatement(statement.body); - } +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Florent Cailhol @ooflorent +*/ - walkDoWhileStatement(statement) { - this.walkNestedStatement(statement.body); - this.walkExpression(statement.test); - } - preWalkForStatement(statement) { - if (statement.init) { - if (statement.init.type === "VariableDeclaration") { - this.preWalkStatement(statement.init); - } - } - this.preWalkStatement(statement.body); - } - walkForStatement(statement) { - this.inBlockScope(() => { - if (statement.init) { - if (statement.init.type === "VariableDeclaration") { - this.blockPreWalkVariableDeclaration(statement.init); - this.prevStatement = undefined; - this.walkStatement(statement.init); - } else { - this.walkExpression(statement.init); - } - } - if (statement.test) { - this.walkExpression(statement.test); - } - if (statement.update) { - this.walkExpression(statement.update); - } - const body = statement.body; - if (body.type === "BlockStatement") { - // no need to add additional scope - const prev = this.prevStatement; - this.blockPreWalkStatements(body.body); - this.prevStatement = prev; - this.walkStatements(body.body); - } else { - this.walkNestedStatement(body); - } - }); - } +const { + compareModulesByPreOrderIndexOrIdentifier +} = __webpack_require__(26296); +const { assignAscendingModuleIds } = __webpack_require__(72922); - preWalkForInStatement(statement) { - if (statement.left.type === "VariableDeclaration") { - this.preWalkVariableDeclaration(statement.left); - } - this.preWalkStatement(statement.body); - } +/** @typedef {import("../Compiler")} Compiler */ +/** @typedef {import("../Module")} Module */ - walkForInStatement(statement) { - this.inBlockScope(() => { - if (statement.left.type === "VariableDeclaration") { - this.blockPreWalkVariableDeclaration(statement.left); - this.walkVariableDeclaration(statement.left); - } else { - this.walkPattern(statement.left); - } - this.walkExpression(statement.right); - const body = statement.body; - if (body.type === "BlockStatement") { - // no need to add additional scope - const prev = this.prevStatement; - this.blockPreWalkStatements(body.body); - this.prevStatement = prev; - this.walkStatements(body.body); - } else { - this.walkNestedStatement(body); - } +class NaturalModuleIdsPlugin { + /** + * Apply the plugin + * @param {Compiler} compiler the compiler instance + * @returns {void} + */ + apply(compiler) { + compiler.hooks.compilation.tap("NaturalModuleIdsPlugin", compilation => { + compilation.hooks.moduleIds.tap("NaturalModuleIdsPlugin", modules => { + const chunkGraph = compilation.chunkGraph; + const modulesInNaturalOrder = Array.from(modules) + .filter( + m => + m.needId && + chunkGraph.getNumberOfModuleChunks(m) > 0 && + chunkGraph.getModuleId(m) === null + ) + .sort( + compareModulesByPreOrderIndexOrIdentifier(compilation.moduleGraph) + ); + assignAscendingModuleIds(modulesInNaturalOrder, compilation); + }); }); } +} - preWalkForOfStatement(statement) { - if (statement.await && this.scope.topLevelScope === true) { - this.hooks.topLevelAwait.call(statement); - } - if (statement.left.type === "VariableDeclaration") { - this.preWalkVariableDeclaration(statement.left); - } - this.preWalkStatement(statement.body); - } +module.exports = NaturalModuleIdsPlugin; - walkForOfStatement(statement) { - this.inBlockScope(() => { - if (statement.left.type === "VariableDeclaration") { - this.blockPreWalkVariableDeclaration(statement.left); - this.walkVariableDeclaration(statement.left); - } else { - this.walkPattern(statement.left); - } - this.walkExpression(statement.right); - const body = statement.body; - if (body.type === "BlockStatement") { - // no need to add additional scope - const prev = this.prevStatement; - this.blockPreWalkStatements(body.body); - this.prevStatement = prev; - this.walkStatements(body.body); - } else { - this.walkNestedStatement(body); - } - }); - } - // Declarations - preWalkFunctionDeclaration(statement) { - if (statement.id) { - this.defineVariable(statement.id.name); - } - } +/***/ }), - walkFunctionDeclaration(statement) { - const wasTopLevel = this.scope.topLevelScope; - this.scope.topLevelScope = false; - this.inFunctionScope(true, statement.params, () => { - for (const param of statement.params) { - this.walkPattern(param); - } - if (statement.body.type === "BlockStatement") { - this.detectMode(statement.body.body); - const prev = this.prevStatement; - this.preWalkStatement(statement.body); - this.prevStatement = prev; - this.walkStatement(statement.body); - } else { - this.walkExpression(statement.body); - } - }); - this.scope.topLevelScope = wasTopLevel; - } +/***/ 98702: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - blockPreWalkImportDeclaration(statement) { - const source = statement.source.value; - this.hooks.import.call(statement, source); - for (const specifier of statement.specifiers) { - const name = specifier.local.name; - switch (specifier.type) { - case "ImportDefaultSpecifier": - if ( - !this.hooks.importSpecifier.call(statement, source, "default", name) - ) { - this.defineVariable(name); - } - break; - case "ImportSpecifier": - if ( - !this.hooks.importSpecifier.call( - statement, - source, - specifier.imported.name, - name - ) - ) { - this.defineVariable(name); - } - break; - case "ImportNamespaceSpecifier": - if (!this.hooks.importSpecifier.call(statement, source, null, name)) { - this.defineVariable(name); - } - break; - default: - this.defineVariable(name); - } - } - } +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ - enterDeclaration(declaration, onIdent) { - switch (declaration.type) { - case "VariableDeclaration": - for (const declarator of declaration.declarations) { - switch (declarator.type) { - case "VariableDeclarator": { - this.enterPattern(declarator.id, onIdent); - break; - } - } - } - break; - case "FunctionDeclaration": - this.enterPattern(declaration.id, onIdent); - break; - case "ClassDeclaration": - this.enterPattern(declaration.id, onIdent); - break; - } - } - blockPreWalkExportNamedDeclaration(statement) { - let source; - if (statement.source) { - source = statement.source.value; - this.hooks.exportImport.call(statement, source); - } else { - this.hooks.export.call(statement); - } - if (statement.declaration) { - if ( - !this.hooks.exportDeclaration.call(statement, statement.declaration) - ) { - const prev = this.prevStatement; - this.preWalkStatement(statement.declaration); - this.prevStatement = prev; - this.blockPreWalkStatement(statement.declaration); - let index = 0; - this.enterDeclaration(statement.declaration, def => { - this.hooks.exportSpecifier.call(statement, def, def, index++); - }); - } - } - if (statement.specifiers) { - for ( - let specifierIndex = 0; - specifierIndex < statement.specifiers.length; - specifierIndex++ - ) { - const specifier = statement.specifiers[specifierIndex]; - switch (specifier.type) { - case "ExportSpecifier": { - const name = specifier.exported.name; - if (source) { - this.hooks.exportImportSpecifier.call( - statement, - source, - specifier.local.name, - name, - specifierIndex - ); - } else { - this.hooks.exportSpecifier.call( - statement, - specifier.local.name, - name, - specifierIndex - ); - } - break; - } - } - } - } - } - walkExportNamedDeclaration(statement) { - if (statement.declaration) { - this.walkStatement(statement.declaration); - } - } +const { compareChunksNatural } = __webpack_require__(26296); +const createSchemaValidation = __webpack_require__(77695); +const { assignAscendingChunkIds } = __webpack_require__(72922); - blockPreWalkExportDefaultDeclaration(statement) { - const prev = this.prevStatement; - this.preWalkStatement(statement.declaration); - this.prevStatement = prev; - this.blockPreWalkStatement(statement.declaration); - if ( - statement.declaration.id && - statement.declaration.type !== "FunctionExpression" && - statement.declaration.type !== "ClassExpression" - ) { - this.hooks.exportSpecifier.call( - statement, - statement.declaration.id.name, - "default", - undefined - ); - } - } +/** @typedef {import("../../declarations/plugins/ids/OccurrenceChunkIdsPlugin").OccurrenceChunkIdsPluginOptions} OccurrenceChunkIdsPluginOptions */ +/** @typedef {import("../Chunk")} Chunk */ +/** @typedef {import("../Compiler")} Compiler */ +/** @typedef {import("../Module")} Module */ - walkExportDefaultDeclaration(statement) { - this.hooks.export.call(statement); - if ( - statement.declaration.id && - statement.declaration.type !== "FunctionExpression" && - statement.declaration.type !== "ClassExpression" - ) { - if ( - !this.hooks.exportDeclaration.call(statement, statement.declaration) - ) { - this.walkStatement(statement.declaration); - } - } else { - // Acorn parses `export default function() {}` as `FunctionDeclaration` and - // `export default class {}` as `ClassDeclaration`, both with `id = null`. - // These nodes must be treated as expressions. - if ( - statement.declaration.type === "FunctionDeclaration" || - statement.declaration.type === "ClassDeclaration" - ) { - this.walkStatement(statement.declaration); - } else { - this.walkExpression(statement.declaration); - } - if (!this.hooks.exportExpression.call(statement, statement.declaration)) { - this.hooks.exportSpecifier.call( - statement, - statement.declaration, - "default", - undefined - ); - } - } +const validate = createSchemaValidation( + __webpack_require__(19311), + () => __webpack_require__(7435), + { + name: "Occurrence Order Chunk Ids Plugin", + baseDataPath: "options" } +); - blockPreWalkExportAllDeclaration(statement) { - const source = statement.source.value; - const name = statement.exported ? statement.exported.name : null; - this.hooks.exportImport.call(statement, source); - this.hooks.exportImportSpecifier.call(statement, source, null, name, 0); +class OccurrenceChunkIdsPlugin { + /** + * @param {OccurrenceChunkIdsPluginOptions=} options options object + */ + constructor(options = {}) { + validate(options); + this.options = options; } - preWalkVariableDeclaration(statement) { - if (statement.kind !== "var") return; - this._preWalkVariableDeclaration(statement, this.hooks.varDeclarationVar); - } + /** + * Apply the plugin + * @param {Compiler} compiler the compiler instance + * @returns {void} + */ + apply(compiler) { + const prioritiseInitial = this.options.prioritiseInitial; + compiler.hooks.compilation.tap("OccurrenceChunkIdsPlugin", compilation => { + compilation.hooks.chunkIds.tap("OccurrenceChunkIdsPlugin", chunks => { + const chunkGraph = compilation.chunkGraph; - blockPreWalkVariableDeclaration(statement) { - if (statement.kind === "var") return; - const hookMap = - statement.kind === "const" - ? this.hooks.varDeclarationConst - : this.hooks.varDeclarationLet; - this._preWalkVariableDeclaration(statement, hookMap); - } + /** @type {Map} */ + const occursInInitialChunksMap = new Map(); - _preWalkVariableDeclaration(statement, hookMap) { - for (const declarator of statement.declarations) { - switch (declarator.type) { - case "VariableDeclarator": { - if (!this.hooks.preDeclarator.call(declarator, statement)) { - this.enterPattern(declarator.id, (name, decl) => { - let hook = hookMap.get(name); - if (hook === undefined || !hook.call(decl)) { - hook = this.hooks.varDeclaration.get(name); - if (hook === undefined || !hook.call(decl)) { - this.defineVariable(name); - } - } - }); - } - break; - } - } - } - } + const compareNatural = compareChunksNatural(chunkGraph); - walkVariableDeclaration(statement) { - for (const declarator of statement.declarations) { - switch (declarator.type) { - case "VariableDeclarator": { - const renameIdentifier = - declarator.init && this.getRenameIdentifier(declarator.init); - if (renameIdentifier && declarator.id.type === "Identifier") { - const hook = this.hooks.canRename.get(renameIdentifier); - if (hook !== undefined && hook.call(declarator.init)) { - // renaming with "var a = b;" - const hook = this.hooks.rename.get(renameIdentifier); - if (hook === undefined || !hook.call(declarator.init)) { - this.setVariable(declarator.id.name, renameIdentifier); - } - break; + for (const c of chunks) { + let occurs = 0; + for (const chunkGroup of c.groupsIterable) { + for (const parent of chunkGroup.parentsIterable) { + if (parent.isInitial()) occurs++; } } - if (!this.hooks.declarator.call(declarator, statement)) { - this.walkPattern(declarator.id); - if (declarator.init) this.walkExpression(declarator.init); - } - break; + occursInInitialChunksMap.set(c, occurs); } - } - } - } - - blockPreWalkClassDeclaration(statement) { - if (statement.id) { - this.defineVariable(statement.id.name); - } - } - walkClassDeclaration(statement) { - this.walkClass(statement); - } - - preWalkSwitchCases(switchCases) { - for (let index = 0, len = switchCases.length; index < len; index++) { - const switchCase = switchCases[index]; - this.preWalkStatements(switchCase.consequent); - } + const chunksInOccurrenceOrder = Array.from(chunks).sort((a, b) => { + if (prioritiseInitial) { + const aEntryOccurs = occursInInitialChunksMap.get(a); + const bEntryOccurs = occursInInitialChunksMap.get(b); + if (aEntryOccurs > bEntryOccurs) return -1; + if (aEntryOccurs < bEntryOccurs) return 1; + } + const aOccurs = a.getNumberOfGroups(); + const bOccurs = b.getNumberOfGroups(); + if (aOccurs > bOccurs) return -1; + if (aOccurs < bOccurs) return 1; + return compareNatural(a, b); + }); + assignAscendingChunkIds(chunksInOccurrenceOrder, compilation); + }); + }); } +} - walkSwitchCases(switchCases) { - this.inBlockScope(() => { - const len = switchCases.length; +module.exports = OccurrenceChunkIdsPlugin; - // we need to pre walk all statements first since we can have invalid code - // import A from "module"; - // switch(1) { - // case 1: - // console.log(A); // should fail at runtime - // case 2: - // const A = 1; - // } - for (let index = 0; index < len; index++) { - const switchCase = switchCases[index]; - if (switchCase.consequent.length > 0) { - const prev = this.prevStatement; - this.blockPreWalkStatements(switchCase.consequent); - this.prevStatement = prev; - } - } +/***/ }), - for (let index = 0; index < len; index++) { - const switchCase = switchCases[index]; +/***/ 128: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - if (switchCase.test) { - this.walkExpression(switchCase.test); - } - if (switchCase.consequent.length > 0) { - this.walkStatements(switchCase.consequent); - } - } - }); - } +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ - preWalkCatchClause(catchClause) { - this.preWalkStatement(catchClause.body); - } - walkCatchClause(catchClause) { - this.inBlockScope(() => { - // Error binding is optional in catch clause since ECMAScript 2019 - if (catchClause.param !== null) { - this.enterPattern(catchClause.param, ident => { - this.defineVariable(ident); - }); - this.walkPattern(catchClause.param); - } - const prev = this.prevStatement; - this.blockPreWalkStatement(catchClause.body); - this.prevStatement = prev; - this.walkStatement(catchClause.body); - }); - } - walkPattern(pattern) { - switch (pattern.type) { - case "ArrayPattern": - this.walkArrayPattern(pattern); - break; - case "AssignmentPattern": - this.walkAssignmentPattern(pattern); - break; - case "MemberExpression": - this.walkMemberExpression(pattern); - break; - case "ObjectPattern": - this.walkObjectPattern(pattern); - break; - case "RestElement": - this.walkRestElement(pattern); - break; - } - } +const { + compareModulesByPreOrderIndexOrIdentifier +} = __webpack_require__(26296); +const createSchemaValidation = __webpack_require__(77695); +const { assignAscendingModuleIds } = __webpack_require__(72922); - walkAssignmentPattern(pattern) { - this.walkExpression(pattern.right); - this.walkPattern(pattern.left); - } +/** @typedef {import("../../declarations/plugins/ids/OccurrenceModuleIdsPlugin").OccurrenceModuleIdsPluginOptions} OccurrenceModuleIdsPluginOptions */ +/** @typedef {import("../Compiler")} Compiler */ +/** @typedef {import("../Module")} Module */ +/** @typedef {import("../ModuleGraphConnection")} ModuleGraphConnection */ - walkObjectPattern(pattern) { - for (let i = 0, len = pattern.properties.length; i < len; i++) { - const prop = pattern.properties[i]; - if (prop) { - if (prop.computed) this.walkExpression(prop.key); - if (prop.value) this.walkPattern(prop.value); - } - } +const validate = createSchemaValidation( + __webpack_require__(4650), + () => __webpack_require__(88570), + { + name: "Occurrence Order Module Ids Plugin", + baseDataPath: "options" } +); - walkArrayPattern(pattern) { - for (let i = 0, len = pattern.elements.length; i < len; i++) { - const element = pattern.elements[i]; - if (element) this.walkPattern(element); - } +class OccurrenceModuleIdsPlugin { + /** + * @param {OccurrenceModuleIdsPluginOptions=} options options object + */ + constructor(options = {}) { + validate(options); + this.options = options; } - walkRestElement(pattern) { - this.walkPattern(pattern.argument); - } + /** + * Apply the plugin + * @param {Compiler} compiler the compiler instance + * @returns {void} + */ + apply(compiler) { + const prioritiseInitial = this.options.prioritiseInitial; + compiler.hooks.compilation.tap("OccurrenceModuleIdsPlugin", compilation => { + const moduleGraph = compilation.moduleGraph; - walkExpressions(expressions) { - for (const expression of expressions) { - if (expression) { - this.walkExpression(expression); - } - } - } + compilation.hooks.moduleIds.tap("OccurrenceModuleIdsPlugin", modules => { + const chunkGraph = compilation.chunkGraph; - walkExpression(expression) { - switch (expression.type) { - case "ArrayExpression": - this.walkArrayExpression(expression); - break; - case "ArrowFunctionExpression": - this.walkArrowFunctionExpression(expression); - break; - case "AssignmentExpression": - this.walkAssignmentExpression(expression); - break; - case "AwaitExpression": - this.walkAwaitExpression(expression); - break; - case "BinaryExpression": - this.walkBinaryExpression(expression); - break; - case "CallExpression": - this.walkCallExpression(expression); - break; - case "ChainExpression": - this.walkChainExpression(expression); - break; - case "ClassExpression": - this.walkClassExpression(expression); - break; - case "ConditionalExpression": - this.walkConditionalExpression(expression); - break; - case "FunctionExpression": - this.walkFunctionExpression(expression); - break; - case "Identifier": - this.walkIdentifier(expression); - break; - case "ImportExpression": - this.walkImportExpression(expression); - break; - case "LogicalExpression": - this.walkLogicalExpression(expression); - break; - case "MetaProperty": - this.walkMetaProperty(expression); - break; - case "MemberExpression": - this.walkMemberExpression(expression); - break; - case "NewExpression": - this.walkNewExpression(expression); - break; - case "ObjectExpression": - this.walkObjectExpression(expression); - break; - case "SequenceExpression": - this.walkSequenceExpression(expression); - break; - case "SpreadElement": - this.walkSpreadElement(expression); - break; - case "TaggedTemplateExpression": - this.walkTaggedTemplateExpression(expression); - break; - case "TemplateLiteral": - this.walkTemplateLiteral(expression); - break; - case "ThisExpression": - this.walkThisExpression(expression); - break; - case "UnaryExpression": - this.walkUnaryExpression(expression); - break; - case "UpdateExpression": - this.walkUpdateExpression(expression); - break; - case "YieldExpression": - this.walkYieldExpression(expression); - break; - } - } + const modulesInOccurrenceOrder = Array.from(modules).filter( + m => + m.needId && + chunkGraph.getNumberOfModuleChunks(m) > 0 && + chunkGraph.getModuleId(m) === null + ); - walkAwaitExpression(expression) { - if (this.scope.topLevelScope === true) - this.hooks.topLevelAwait.call(expression); - this.walkExpression(expression.argument); - } + const occursInInitialChunksMap = new Map(); + const occursInAllChunksMap = new Map(); - walkArrayExpression(expression) { - if (expression.elements) { - this.walkExpressions(expression.elements); - } - } + const initialChunkChunkMap = new Map(); + const entryCountMap = new Map(); + for (const m of modulesInOccurrenceOrder) { + let initial = 0; + let entry = 0; + for (const c of chunkGraph.getModuleChunksIterable(m)) { + if (c.canBeInitial()) initial++; + if (chunkGraph.isEntryModuleInChunk(m, c)) entry++; + } + initialChunkChunkMap.set(m, initial); + entryCountMap.set(m, entry); + } - walkSpreadElement(expression) { - if (expression.argument) { - this.walkExpression(expression.argument); - } - } + /** + * @param {Module} module module + * @returns {number} count of occurs + */ + const countOccursInEntry = module => { + let sum = 0; + for (const [ + originModule, + connections + ] of moduleGraph.getIncomingConnectionsByOriginModule(module)) { + if (!originModule) continue; + if (!connections.some(c => c.isTargetActive(undefined))) continue; + sum += initialChunkChunkMap.get(originModule); + } + return sum; + }; - walkObjectExpression(expression) { - for ( - let propIndex = 0, len = expression.properties.length; - propIndex < len; - propIndex++ - ) { - const prop = expression.properties[propIndex]; - this.walkProperty(prop); - } - } + /** + * @param {Module} module module + * @returns {number} count of occurs + */ + const countOccurs = module => { + let sum = 0; + for (const [ + originModule, + connections + ] of moduleGraph.getIncomingConnectionsByOriginModule(module)) { + if (!originModule) continue; + const chunkModules = + chunkGraph.getNumberOfModuleChunks(originModule); + for (const c of connections) { + if (!c.isTargetActive(undefined)) continue; + if (!c.dependency) continue; + const factor = c.dependency.getNumberOfIdOccurrences(); + if (factor === 0) continue; + sum += factor * chunkModules; + } + } + return sum; + }; - walkProperty(prop) { - if (prop.type === "SpreadElement") { - this.walkExpression(prop.argument); - return; - } - if (prop.computed) { - this.walkExpression(prop.key); - } - if (prop.shorthand && prop.value && prop.value.type === "Identifier") { - this.scope.inShorthand = prop.value.name; - this.walkIdentifier(prop.value); - this.scope.inShorthand = false; - } else { - this.walkExpression(prop.value); - } - } + if (prioritiseInitial) { + for (const m of modulesInOccurrenceOrder) { + const result = + countOccursInEntry(m) + + initialChunkChunkMap.get(m) + + entryCountMap.get(m); + occursInInitialChunksMap.set(m, result); + } + } - walkFunctionExpression(expression) { - const wasTopLevel = this.scope.topLevelScope; - this.scope.topLevelScope = false; - const scopeParams = expression.params; + for (const m of modules) { + const result = + countOccurs(m) + + chunkGraph.getNumberOfModuleChunks(m) + + entryCountMap.get(m); + occursInAllChunksMap.set(m, result); + } - // Add function name in scope for recursive calls - if (expression.id) { - scopeParams.push(expression.id.name); - } + const naturalCompare = compareModulesByPreOrderIndexOrIdentifier( + compilation.moduleGraph + ); - this.inFunctionScope(true, scopeParams, () => { - for (const param of expression.params) { - this.walkPattern(param); - } - if (expression.body.type === "BlockStatement") { - this.detectMode(expression.body.body); - const prev = this.prevStatement; - this.preWalkStatement(expression.body); - this.prevStatement = prev; - this.walkStatement(expression.body); - } else { - this.walkExpression(expression.body); - } - }); - this.scope.topLevelScope = wasTopLevel; - } + modulesInOccurrenceOrder.sort((a, b) => { + if (prioritiseInitial) { + const aEntryOccurs = occursInInitialChunksMap.get(a); + const bEntryOccurs = occursInInitialChunksMap.get(b); + if (aEntryOccurs > bEntryOccurs) return -1; + if (aEntryOccurs < bEntryOccurs) return 1; + } + const aOccurs = occursInAllChunksMap.get(a); + const bOccurs = occursInAllChunksMap.get(b); + if (aOccurs > bOccurs) return -1; + if (aOccurs < bOccurs) return 1; + return naturalCompare(a, b); + }); - walkArrowFunctionExpression(expression) { - const wasTopLevel = this.scope.topLevelScope; - this.scope.topLevelScope = wasTopLevel ? "arrow" : false; - this.inFunctionScope(false, expression.params, () => { - for (const param of expression.params) { - this.walkPattern(param); - } - if (expression.body.type === "BlockStatement") { - this.detectMode(expression.body.body); - const prev = this.prevStatement; - this.preWalkStatement(expression.body); - this.prevStatement = prev; - this.walkStatement(expression.body); - } else { - this.walkExpression(expression.body); - } + assignAscendingModuleIds(modulesInOccurrenceOrder, compilation); + }); }); - this.scope.topLevelScope = wasTopLevel; } +} - /** - * @param {SequenceExpressionNode} expression the sequence - */ - walkSequenceExpression(expression) { - if (!expression.expressions) return; - // We treat sequence expressions like statements when they are one statement level - // This has some benefits for optimizations that only work on statement level - const currentStatement = this.statementPath[this.statementPath.length - 1]; - if ( - currentStatement === expression || - (currentStatement.type === "ExpressionStatement" && - currentStatement.expression === expression) - ) { - const old = this.statementPath.pop(); - for (const expr of expression.expressions) { - this.statementPath.push(expr); - this.walkExpression(expr); - this.statementPath.pop(); - } - this.statementPath.push(old); - } else { - this.walkExpressions(expression.expressions); - } - } +module.exports = OccurrenceModuleIdsPlugin; - walkUpdateExpression(expression) { - this.walkExpression(expression.argument); - } - walkUnaryExpression(expression) { - if (expression.operator === "typeof") { - const result = this.callHooksForExpression( - this.hooks.typeof, - expression.argument, - expression - ); - if (result === true) return; - if (expression.argument.type === "ChainExpression") { - const result = this.callHooksForExpression( - this.hooks.typeof, - expression.argument.expression, - expression - ); - if (result === true) return; - } - } - this.walkExpression(expression.argument); - } +/***/ }), - walkLeftRightExpression(expression) { - this.walkExpression(expression.left); - this.walkExpression(expression.right); - } +/***/ 48169: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - walkBinaryExpression(expression) { - this.walkLeftRightExpression(expression); - } +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ - walkLogicalExpression(expression) { - const result = this.hooks.expressionLogicalOperator.call(expression); - if (result === undefined) { - this.walkLeftRightExpression(expression); - } else { - if (result) { - this.walkExpression(expression.right); - } + + +const util = __webpack_require__(31669); +const memoize = __webpack_require__(84297); + +/** @typedef {import("../declarations/WebpackOptions").Entry} Entry */ +/** @typedef {import("../declarations/WebpackOptions").EntryNormalized} EntryNormalized */ +/** @typedef {import("../declarations/WebpackOptions").EntryObject} EntryObject */ +/** @typedef {import("../declarations/WebpackOptions").LibraryOptions} LibraryOptions */ +/** @typedef {import("../declarations/WebpackOptions").ModuleOptions} ModuleOptions */ +/** @typedef {import("../declarations/WebpackOptions").ResolveOptions} ResolveOptions */ +/** @typedef {import("../declarations/WebpackOptions").RuleSetCondition} RuleSetCondition */ +/** @typedef {import("../declarations/WebpackOptions").RuleSetConditionAbsolute} RuleSetConditionAbsolute */ +/** @typedef {import("../declarations/WebpackOptions").RuleSetRule} RuleSetRule */ +/** @typedef {import("../declarations/WebpackOptions").RuleSetUse} RuleSetUse */ +/** @typedef {import("../declarations/WebpackOptions").RuleSetUseItem} RuleSetUseItem */ +/** @typedef {import("../declarations/WebpackOptions").WebpackOptions} Configuration */ +/** @typedef {import("../declarations/WebpackOptions").WebpackOptionsNormalized} WebpackOptionsNormalized */ +/** @typedef {import("../declarations/WebpackOptions").WebpackPluginFunction} WebpackPluginFunction */ +/** @typedef {import("../declarations/WebpackOptions").WebpackPluginInstance} WebpackPluginInstance */ +/** @typedef {import("./Compilation").Asset} Asset */ +/** @typedef {import("./Compilation").AssetInfo} AssetInfo */ +/** @typedef {import("./MultiStats")} MultiStats */ +/** @typedef {import("./Parser").ParserState} ParserState */ +/** @typedef {import("./Watching")} Watching */ +/** @typedef {import("./stats/DefaultStatsFactoryPlugin").StatsAsset} StatsAsset */ +/** @typedef {import("./stats/DefaultStatsFactoryPlugin").StatsChunk} StatsChunk */ +/** @typedef {import("./stats/DefaultStatsFactoryPlugin").StatsChunkGroup} StatsChunkGroup */ +/** @typedef {import("./stats/DefaultStatsFactoryPlugin").StatsChunkOrigin} StatsChunkOrigin */ +/** @typedef {import("./stats/DefaultStatsFactoryPlugin").StatsCompilation} StatsCompilation */ +/** @typedef {import("./stats/DefaultStatsFactoryPlugin").StatsError} StatsError */ +/** @typedef {import("./stats/DefaultStatsFactoryPlugin").StatsLogging} StatsLogging */ +/** @typedef {import("./stats/DefaultStatsFactoryPlugin").StatsLoggingEntry} StatsLoggingEntry */ +/** @typedef {import("./stats/DefaultStatsFactoryPlugin").StatsModule} StatsModule */ +/** @typedef {import("./stats/DefaultStatsFactoryPlugin").StatsModuleIssuer} StatsModuleIssuer */ +/** @typedef {import("./stats/DefaultStatsFactoryPlugin").StatsModuleReason} StatsModuleReason */ +/** @typedef {import("./stats/DefaultStatsFactoryPlugin").StatsModuleTraceDependency} StatsModuleTraceDependency */ +/** @typedef {import("./stats/DefaultStatsFactoryPlugin").StatsModuleTraceItem} StatsModuleTraceItem */ +/** @typedef {import("./stats/DefaultStatsFactoryPlugin").StatsProfile} StatsProfile */ + +/** + * @template {Function} T + * @param {function(): T} factory factory function + * @returns {T} function + */ +const lazyFunction = factory => { + const fac = memoize(factory); + const f = /** @type {any} */ ( + (...args) => { + return fac()(...args); } - } + ); + return /** @type {T} */ (f); +}; - walkAssignmentExpression(expression) { - if (expression.left.type === "Identifier") { - const renameIdentifier = this.getRenameIdentifier(expression.right); - if (renameIdentifier) { - if ( - this.callHooksForInfo( - this.hooks.canRename, - renameIdentifier, - expression.right - ) - ) { - // renaming "a = b;" - if ( - !this.callHooksForInfo( - this.hooks.rename, - renameIdentifier, - expression.right - ) - ) { - this.setVariable( - expression.left.name, - this.getVariableInfo(renameIdentifier) - ); - } - return; - } - } - this.walkExpression(expression.right); - this.enterPattern(expression.left, (name, decl) => { - if (!this.callHooksForName(this.hooks.assign, name, expression)) { - this.walkExpression(expression.left); - } +/** + * @template A + * @template B + * @param {A} obj input a + * @param {B} exports input b + * @returns {A & B} merged + */ +const mergeExports = (obj, exports) => { + const descriptors = Object.getOwnPropertyDescriptors(exports); + for (const name of Object.keys(descriptors)) { + const descriptor = descriptors[name]; + if (descriptor.get) { + const fn = descriptor.get; + Object.defineProperty(obj, name, { + configurable: false, + enumerable: true, + get: memoize(fn) }); - return; - } - if (expression.left.type.endsWith("Pattern")) { - this.walkExpression(expression.right); - this.enterPattern(expression.left, (name, decl) => { - if (!this.callHooksForName(this.hooks.assign, name, expression)) { - this.defineVariable(name); - } + } else if (typeof descriptor.value === "object") { + Object.defineProperty(obj, name, { + configurable: false, + enumerable: true, + writable: false, + value: mergeExports({}, descriptor.value) }); - this.walkPattern(expression.left); - } else if (expression.left.type === "MemberExpression") { - const exprName = this.getMemberExpressionInfo( - expression.left, - ALLOWED_MEMBER_TYPES_EXPRESSION - ); - if (exprName) { - if ( - this.callHooksForInfo( - this.hooks.assignMemberChain, - exprName.rootInfo, - expression, - exprName.getMembers() - ) - ) { - return; - } - } - this.walkExpression(expression.right); - this.walkExpression(expression.left); } else { - this.walkExpression(expression.right); - this.walkExpression(expression.left); + throw new Error( + "Exposed values must be either a getter or an nested object" + ); } } + return /** @type {A & B} */ (Object.freeze(obj)); +}; - walkConditionalExpression(expression) { - const result = this.hooks.expressionConditionalOperator.call(expression); - if (result === undefined) { - this.walkExpression(expression.test); - this.walkExpression(expression.consequent); - if (expression.alternate) { - this.walkExpression(expression.alternate); - } - } else { - if (result) { - this.walkExpression(expression.consequent); - } else if (expression.alternate) { - this.walkExpression(expression.alternate); - } +const fn = lazyFunction(() => __webpack_require__(86128)); +module.exports = mergeExports(fn, { + get webpack() { + return __webpack_require__(86128); + }, + get validate() { + const webpackOptionsSchemaCheck = __webpack_require__(97220); + const getRealValidate = memoize(() => { + const validateSchema = __webpack_require__(55959); + const webpackOptionsSchema = __webpack_require__(1863); + return options => validateSchema(webpackOptionsSchema, options); + }); + return options => { + if (!webpackOptionsSchemaCheck(options)) getRealValidate()(options); + }; + }, + get validateSchema() { + const validateSchema = __webpack_require__(55959); + return validateSchema; + }, + get version() { + return /** @type {string} */ (__webpack_require__(87168)/* .version */ .i8); + }, + + get cli() { + return __webpack_require__(26040); + }, + get AutomaticPrefetchPlugin() { + return __webpack_require__(51714); + }, + get AsyncDependenciesBlock() { + return __webpack_require__(11315); + }, + get BannerPlugin() { + return __webpack_require__(45480); + }, + get Cache() { + return __webpack_require__(99453); + }, + get Chunk() { + return __webpack_require__(65574); + }, + get ChunkGraph() { + return __webpack_require__(97860); + }, + get CleanPlugin() { + return __webpack_require__(49129); + }, + get Compilation() { + return __webpack_require__(59622); + }, + get Compiler() { + return __webpack_require__(11777); + }, + get ConcatenationScope() { + return __webpack_require__(14067); + }, + get ContextExclusionPlugin() { + return __webpack_require__(30480); + }, + get ContextReplacementPlugin() { + return __webpack_require__(21542); + }, + get DefinePlugin() { + return __webpack_require__(46754); + }, + get DelegatedPlugin() { + return __webpack_require__(48248); + }, + get Dependency() { + return __webpack_require__(50384); + }, + get DllPlugin() { + return __webpack_require__(15232); + }, + get DllReferencePlugin() { + return __webpack_require__(8904); + }, + get DynamicEntryPlugin() { + return __webpack_require__(60670); + }, + get EntryOptionPlugin() { + return __webpack_require__(59526); + }, + get EntryPlugin() { + return __webpack_require__(82430); + }, + get EnvironmentPlugin() { + return __webpack_require__(43755); + }, + get EvalDevToolModulePlugin() { + return __webpack_require__(4125); + }, + get EvalSourceMapDevToolPlugin() { + return __webpack_require__(42053); + }, + get ExternalModule() { + return __webpack_require__(89805); + }, + get ExternalsPlugin() { + return __webpack_require__(361); + }, + get Generator() { + return __webpack_require__(1826); + }, + get HotUpdateChunk() { + return __webpack_require__(39222); + }, + get HotModuleReplacementPlugin() { + return __webpack_require__(616); + }, + get IgnorePlugin() { + return __webpack_require__(8098); + }, + get JavascriptModulesPlugin() { + return util.deprecate( + () => __webpack_require__(76767), + "webpack.JavascriptModulesPlugin has moved to webpack.javascript.JavascriptModulesPlugin", + "DEP_WEBPACK_JAVASCRIPT_MODULES_PLUGIN" + )(); + }, + get LibManifestPlugin() { + return __webpack_require__(30711); + }, + get LibraryTemplatePlugin() { + return util.deprecate( + () => __webpack_require__(81735), + "webpack.LibraryTemplatePlugin is deprecated and has been replaced by compilation.outputOptions.library or compilation.addEntry + passing a library option", + "DEP_WEBPACK_LIBRARY_TEMPLATE_PLUGIN" + )(); + }, + get LoaderOptionsPlugin() { + return __webpack_require__(73047); + }, + get LoaderTargetPlugin() { + return __webpack_require__(94834); + }, + get Module() { + return __webpack_require__(85887); + }, + get ModuleFilenameHelpers() { + return __webpack_require__(80295); + }, + get ModuleGraph() { + return __webpack_require__(20258); + }, + get ModuleGraphConnection() { + return __webpack_require__(94144); + }, + get NoEmitOnErrorsPlugin() { + return __webpack_require__(70760); + }, + get NormalModule() { + return __webpack_require__(11026); + }, + get NormalModuleReplacementPlugin() { + return __webpack_require__(12747); + }, + get MultiCompiler() { + return __webpack_require__(73663); + }, + get Parser() { + return __webpack_require__(68214); + }, + get PrefetchPlugin() { + return __webpack_require__(34652); + }, + get ProgressPlugin() { + return __webpack_require__(41306); + }, + get ProvidePlugin() { + return __webpack_require__(18067); + }, + get RuntimeGlobals() { + return __webpack_require__(49404); + }, + get RuntimeModule() { + return __webpack_require__(61439); + }, + get SingleEntryPlugin() { + return util.deprecate( + () => __webpack_require__(82430), + "SingleEntryPlugin was renamed to EntryPlugin", + "DEP_WEBPACK_SINGLE_ENTRY_PLUGIN" + )(); + }, + get SourceMapDevToolPlugin() { + return __webpack_require__(79917); + }, + get Stats() { + return __webpack_require__(87797); + }, + get Template() { + return __webpack_require__(92066); + }, + get UsageState() { + return __webpack_require__(4295).UsageState; + }, + get WatchIgnorePlugin() { + return __webpack_require__(90187); + }, + get WebpackError() { + return __webpack_require__(68422); + }, + get WebpackOptionsApply() { + return __webpack_require__(44137); + }, + get WebpackOptionsDefaulter() { + return util.deprecate( + () => __webpack_require__(547), + "webpack.WebpackOptionsDefaulter is deprecated and has been replaced by webpack.config.getNormalizedWebpackOptions and webpack.config.applyWebpackOptionsDefaults", + "DEP_WEBPACK_OPTIONS_DEFAULTER" + )(); + }, + // TODO webpack 6 deprecate + get WebpackOptionsValidationError() { + return __webpack_require__(79286).ValidationError; + }, + get ValidationError() { + return __webpack_require__(79286).ValidationError; + }, + + cache: { + get MemoryCachePlugin() { + return __webpack_require__(4045); } - } + }, - walkNewExpression(expression) { - const result = this.callHooksForExpression( - this.hooks.new, - expression.callee, - expression - ); - if (result === true) return; - this.walkExpression(expression.callee); - if (expression.arguments) { - this.walkExpressions(expression.arguments); + config: { + get getNormalizedWebpackOptions() { + return __webpack_require__(52975).getNormalizedWebpackOptions; + }, + get applyWebpackOptionsDefaults() { + return __webpack_require__(27057).applyWebpackOptionsDefaults; + } + }, + + dependencies: { + get ModuleDependency() { + return __webpack_require__(80944); + }, + get ConstDependency() { + return __webpack_require__(60864); + }, + get NullDependency() { + return __webpack_require__(65845); + } + }, + + ids: { + get ChunkModuleIdRangePlugin() { + return __webpack_require__(7047); + }, + get NaturalModuleIdsPlugin() { + return __webpack_require__(96338); + }, + get OccurrenceModuleIdsPlugin() { + return __webpack_require__(128); + }, + get NamedModuleIdsPlugin() { + return __webpack_require__(88514); + }, + get DeterministicChunkIdsPlugin() { + return __webpack_require__(64801); + }, + get DeterministicModuleIdsPlugin() { + return __webpack_require__(84965); + }, + get NamedChunkIdsPlugin() { + return __webpack_require__(30483); + }, + get OccurrenceChunkIdsPlugin() { + return __webpack_require__(98702); + }, + get HashedModuleIdsPlugin() { + return __webpack_require__(83635); } - } + }, - walkYieldExpression(expression) { - if (expression.argument) { - this.walkExpression(expression.argument); + javascript: { + get EnableChunkLoadingPlugin() { + return __webpack_require__(34726); + }, + get JavascriptModulesPlugin() { + return __webpack_require__(76767); + }, + get JavascriptParser() { + return __webpack_require__(42060); } - } + }, - walkTemplateLiteral(expression) { - if (expression.expressions) { - this.walkExpressions(expression.expressions); + optimize: { + get AggressiveMergingPlugin() { + return __webpack_require__(8239); + }, + get AggressiveSplittingPlugin() { + return util.deprecate( + () => __webpack_require__(10055), + "AggressiveSplittingPlugin is deprecated in favor of SplitChunksPlugin", + "DEP_WEBPACK_AGGRESSIVE_SPLITTING_PLUGIN" + )(); + }, + get InnerGraph() { + return __webpack_require__(92886); + }, + get LimitChunkCountPlugin() { + return __webpack_require__(22119); + }, + get MinChunkSizePlugin() { + return __webpack_require__(85813); + }, + get ModuleConcatenationPlugin() { + return __webpack_require__(29585); + }, + get RealContentHashPlugin() { + return __webpack_require__(6669); + }, + get RuntimeChunkPlugin() { + return __webpack_require__(23821); + }, + get SideEffectsFlagPlugin() { + return __webpack_require__(47844); + }, + get SplitChunksPlugin() { + return __webpack_require__(57073); } - } + }, - walkTaggedTemplateExpression(expression) { - if (expression.tag) { - this.walkExpression(expression.tag); - } - if (expression.quasi && expression.quasi.expressions) { - this.walkExpressions(expression.quasi.expressions); + runtime: { + get GetChunkFilenameRuntimeModule() { + return __webpack_require__(53288); + }, + get LoadScriptRuntimeModule() { + return __webpack_require__(80647); } - } - - walkClassExpression(expression) { - this.walkClass(expression); - } - - /** - * @param {ChainExpressionNode} expression expression - */ - walkChainExpression(expression) { - const result = this.hooks.optionalChaining.call(expression); + }, - if (result === undefined) { - if (expression.expression.type === "CallExpression") { - this.walkCallExpression(expression.expression); - } else { - this.walkMemberExpression(expression.expression); - } + prefetch: { + get ChunkPrefetchPreloadPlugin() { + return __webpack_require__(17839); } - } - - _walkIIFE(functionExpression, options, currentThis) { - const getVarInfo = argOrThis => { - const renameIdentifier = this.getRenameIdentifier(argOrThis); - if (renameIdentifier) { - if ( - this.callHooksForInfo( - this.hooks.canRename, - renameIdentifier, - argOrThis - ) - ) { - if ( - !this.callHooksForInfo( - this.hooks.rename, - renameIdentifier, - argOrThis - ) - ) { - return this.getVariableInfo(renameIdentifier); - } - } - } - this.walkExpression(argOrThis); - }; - const { params, type } = functionExpression; - const arrow = type === "ArrowFunctionExpression"; - const renameThis = currentThis ? getVarInfo(currentThis) : null; - const varInfoForArgs = options.map(getVarInfo); - const wasTopLevel = this.scope.topLevelScope; - this.scope.topLevelScope = wasTopLevel && arrow ? "arrow" : false; - const scopeParams = params.filter( - (identifier, idx) => !varInfoForArgs[idx] - ); + }, - // Add function name in scope for recursive calls - if (functionExpression.id) { - scopeParams.push(functionExpression.id.name); + web: { + get FetchCompileAsyncWasmPlugin() { + return __webpack_require__(37118); + }, + get FetchCompileWasmPlugin() { + return __webpack_require__(89728); + }, + get JsonpChunkLoadingRuntimeModule() { + return __webpack_require__(66032); + }, + get JsonpTemplatePlugin() { + return __webpack_require__(45968); } + }, - this.inFunctionScope(true, scopeParams, () => { - if (renameThis && !arrow) { - this.setVariable("this", renameThis); - } - for (let i = 0; i < varInfoForArgs.length; i++) { - const varInfo = varInfoForArgs[i]; - if (!varInfo) continue; - if (!params[i] || params[i].type !== "Identifier") continue; - this.setVariable(params[i].name, varInfo); - } - if (functionExpression.body.type === "BlockStatement") { - this.detectMode(functionExpression.body.body); - const prev = this.prevStatement; - this.preWalkStatement(functionExpression.body); - this.prevStatement = prev; - this.walkStatement(functionExpression.body); - } else { - this.walkExpression(functionExpression.body); - } - }); - this.scope.topLevelScope = wasTopLevel; - } - - walkImportExpression(expression) { - let result = this.hooks.importCall.call(expression); - if (result === true) return; - - this.walkExpression(expression.source); - } - - walkCallExpression(expression) { - const isSimpleFunction = fn => { - return fn.params.every(p => p.type === "Identifier"); - }; - if ( - expression.callee.type === "MemberExpression" && - expression.callee.object.type.endsWith("FunctionExpression") && - !expression.callee.computed && - (expression.callee.property.name === "call" || - expression.callee.property.name === "bind") && - expression.arguments.length > 0 && - isSimpleFunction(expression.callee.object) - ) { - // (function(…) { }.call/bind(?, …)) - this._walkIIFE( - expression.callee.object, - expression.arguments.slice(1), - expression.arguments[0] - ); - } else if ( - expression.callee.type.endsWith("FunctionExpression") && - isSimpleFunction(expression.callee) - ) { - // (function(…) { }(…)) - this._walkIIFE(expression.callee, expression.arguments, null); - } else { - if (expression.callee.type === "MemberExpression") { - const exprInfo = this.getMemberExpressionInfo( - expression.callee, - ALLOWED_MEMBER_TYPES_CALL_EXPRESSION - ); - if (exprInfo && exprInfo.type === "call") { - const result = this.callHooksForInfo( - this.hooks.callMemberChainOfCallMemberChain, - exprInfo.rootInfo, - expression, - exprInfo.getCalleeMembers(), - exprInfo.call, - exprInfo.getMembers() - ); - if (result === true) return; - } - } - const callee = this.evaluateExpression(expression.callee); - if (callee.isIdentifier()) { - const result1 = this.callHooksForInfo( - this.hooks.callMemberChain, - callee.rootInfo, - expression, - callee.getMembers() - ); - if (result1 === true) return; - const result2 = this.callHooksForInfo( - this.hooks.call, - callee.identifier, - expression - ); - if (result2 === true) return; - } - - if (expression.callee) { - if (expression.callee.type === "MemberExpression") { - // because of call context we need to walk the call context as expression - this.walkExpression(expression.callee.object); - if (expression.callee.computed === true) - this.walkExpression(expression.callee.property); - } else { - this.walkExpression(expression.callee); - } - } - if (expression.arguments) this.walkExpressions(expression.arguments); + webworker: { + get WebWorkerTemplatePlugin() { + return __webpack_require__(9460); } - } + }, - walkMemberExpression(expression) { - const exprInfo = this.getMemberExpressionInfo( - expression, - ALLOWED_MEMBER_TYPES_ALL - ); - if (exprInfo) { - switch (exprInfo.type) { - case "expression": { - const result1 = this.callHooksForInfo( - this.hooks.expression, - exprInfo.name, - expression - ); - if (result1 === true) return; - const members = exprInfo.getMembers(); - const result2 = this.callHooksForInfo( - this.hooks.expressionMemberChain, - exprInfo.rootInfo, - expression, - members - ); - if (result2 === true) return; - this.walkMemberExpressionWithExpressionName( - expression, - exprInfo.name, - exprInfo.rootInfo, - members.slice(), - () => - this.callHooksForInfo( - this.hooks.unhandledExpressionMemberChain, - exprInfo.rootInfo, - expression, - members - ) - ); - return; - } - case "call": { - const result = this.callHooksForInfo( - this.hooks.memberChainOfCallMemberChain, - exprInfo.rootInfo, - expression, - exprInfo.getCalleeMembers(), - exprInfo.call, - exprInfo.getMembers() - ); - if (result === true) return; - // Fast skip over the member chain as we already called memberChainOfCallMemberChain - // and call computed property are literals anyway - this.walkExpression(exprInfo.call); - return; - } - } + node: { + get NodeEnvironmentPlugin() { + return __webpack_require__(38857); + }, + get NodeSourcePlugin() { + return __webpack_require__(13313); + }, + get NodeTargetPlugin() { + return __webpack_require__(28037); + }, + get NodeTemplatePlugin() { + return __webpack_require__(47087); + }, + get ReadFileCompileWasmPlugin() { + return __webpack_require__(98724); } - this.walkExpression(expression.object); - if (expression.computed === true) this.walkExpression(expression.property); - } + }, - walkMemberExpressionWithExpressionName( - expression, - name, - rootInfo, - members, - onUnhandled - ) { - if (expression.object.type === "MemberExpression") { - // optimize the case where expression.object is a MemberExpression too. - // we can keep info here when calling walkMemberExpression directly - const property = - expression.property.name || `${expression.property.value}`; - name = name.slice(0, -property.length - 1); - members.pop(); - const result = this.callHooksForInfo( - this.hooks.expression, - name, - expression.object - ); - if (result === true) return; - this.walkMemberExpressionWithExpressionName( - expression.object, - name, - rootInfo, - members, - onUnhandled - ); - } else if (!onUnhandled || !onUnhandled()) { - this.walkExpression(expression.object); + electron: { + get ElectronTargetPlugin() { + return __webpack_require__(88362); } - if (expression.computed === true) this.walkExpression(expression.property); - } - - walkThisExpression(expression) { - this.callHooksForName(this.hooks.expression, "this", expression); - } - - walkIdentifier(expression) { - this.callHooksForName(this.hooks.expression, expression.name, expression); - } - - /** - * @param {MetaPropertyNode} metaProperty meta property - */ - walkMetaProperty(metaProperty) { - this.hooks.expression.for(getRootName(metaProperty)).call(metaProperty); - } - - callHooksForExpression(hookMap, expr, ...args) { - return this.callHooksForExpressionWithFallback( - hookMap, - expr, - undefined, - undefined, - ...args - ); - } + }, - /** - * @template T - * @template R - * @param {HookMap>} hookMap hooks the should be called - * @param {MemberExpressionNode} expr expression info - * @param {function(string, string | ScopeInfo | VariableInfo, function(): string[]): any} fallback callback when variable in not handled by hooks - * @param {function(string): any} defined callback when variable is defined - * @param {AsArray} args args for the hook - * @returns {R} result of hook - */ - callHooksForExpressionWithFallback( - hookMap, - expr, - fallback, - defined, - ...args - ) { - const exprName = this.getMemberExpressionInfo( - expr, - ALLOWED_MEMBER_TYPES_EXPRESSION - ); - if (exprName !== undefined) { - const members = exprName.getMembers(); - return this.callHooksForInfoWithFallback( - hookMap, - members.length === 0 ? exprName.rootInfo : exprName.name, - fallback && - (name => fallback(name, exprName.rootInfo, exprName.getMembers)), - defined && (() => defined(exprName.name)), - ...args - ); + wasm: { + get AsyncWebAssemblyModulesPlugin() { + return __webpack_require__(13804); } - } + }, - /** - * @template T - * @template R - * @param {HookMap>} hookMap hooks the should be called - * @param {string} name key in map - * @param {AsArray} args args for the hook - * @returns {R} result of hook - */ - callHooksForName(hookMap, name, ...args) { - return this.callHooksForNameWithFallback( - hookMap, - name, - undefined, - undefined, - ...args - ); - } + library: { + get AbstractLibraryPlugin() { + return __webpack_require__(94051); + }, + get EnableLibraryPlugin() { + return __webpack_require__(35613); + } + }, - /** - * @template T - * @template R - * @param {HookMap>} hookMap hooks that should be called - * @param {ExportedVariableInfo} info variable info - * @param {AsArray} args args for the hook - * @returns {R} result of hook - */ - callHooksForInfo(hookMap, info, ...args) { - return this.callHooksForInfoWithFallback( - hookMap, - info, - undefined, - undefined, - ...args - ); - } + container: { + get ContainerPlugin() { + return __webpack_require__(20962); + }, + get ContainerReferencePlugin() { + return __webpack_require__(17813); + }, + get ModuleFederationPlugin() { + return __webpack_require__(22814); + }, + get scope() { + return __webpack_require__(56084).scope; + } + }, - /** - * @template T - * @template R - * @param {HookMap>} hookMap hooks the should be called - * @param {ExportedVariableInfo} info variable info - * @param {function(string): any} fallback callback when variable in not handled by hooks - * @param {function(): any} defined callback when variable is defined - * @param {AsArray} args args for the hook - * @returns {R} result of hook - */ - callHooksForInfoWithFallback(hookMap, info, fallback, defined, ...args) { - let name; - if (typeof info === "string") { - name = info; - } else { - if (!(info instanceof VariableInfo)) { - if (defined !== undefined) { - return defined(); - } - return; - } - let tagInfo = info.tagInfo; - while (tagInfo !== undefined) { - const hook = hookMap.get(tagInfo.tag); - if (hook !== undefined) { - this.currentTagData = tagInfo.data; - const result = hook.call(...args); - this.currentTagData = undefined; - if (result !== undefined) return result; - } - tagInfo = tagInfo.next; - } - if (info.freeName === true) { - if (defined !== undefined) { - return defined(); - } - return; - } - name = info.freeName; + sharing: { + get ConsumeSharedPlugin() { + return __webpack_require__(19984); + }, + get ProvideSharedPlugin() { + return __webpack_require__(42672); + }, + get SharePlugin() { + return __webpack_require__(25790); + }, + get scope() { + return __webpack_require__(56084).scope; } - const hook = hookMap.get(name); - if (hook !== undefined) { - const result = hook.call(...args); - if (result !== undefined) return result; + }, + + debug: { + get ProfilingPlugin() { + return __webpack_require__(52034); } - if (fallback !== undefined) { - return fallback(name); + }, + + util: { + get createHash() { + return __webpack_require__(24123); + }, + get comparators() { + return __webpack_require__(26296); + }, + get runtime() { + return __webpack_require__(19655); + }, + get serialization() { + return __webpack_require__(99551); + }, + get cleverMerge() { + return __webpack_require__(11217).cachedCleverMerge; + }, + get LazySet() { + return __webpack_require__(59534); + } + }, + + get sources() { + return __webpack_require__(96192); + }, + + experiments: { + schemes: { + get HttpUriPlugin() { + return __webpack_require__(34747); + } } } +}); + + +/***/ }), + +/***/ 86189: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ + + + +const { ConcatSource, PrefixSource, RawSource } = __webpack_require__(96192); +const { RuntimeGlobals } = __webpack_require__(48169); +const HotUpdateChunk = __webpack_require__(39222); +const Template = __webpack_require__(92066); +const { getCompilationHooks } = __webpack_require__(76767); +const { + generateEntryStartup, + updateHashForEntryStartup +} = __webpack_require__(30951); +/** @typedef {import("../Compiler")} Compiler */ + +class ArrayPushCallbackChunkFormatPlugin { /** - * @template T - * @template R - * @param {HookMap>} hookMap hooks the should be called - * @param {string} name key in map - * @param {function(string): any} fallback callback when variable in not handled by hooks - * @param {function(): any} defined callback when variable is defined - * @param {AsArray} args args for the hook - * @returns {R} result of hook + * Apply the plugin + * @param {Compiler} compiler the compiler instance + * @returns {void} */ - callHooksForNameWithFallback(hookMap, name, fallback, defined, ...args) { - return this.callHooksForInfoWithFallback( - hookMap, - this.getVariableInfo(name), - fallback, - defined, - ...args + apply(compiler) { + compiler.hooks.thisCompilation.tap( + "ArrayPushCallbackChunkFormatPlugin", + compilation => { + compilation.hooks.additionalChunkRuntimeRequirements.tap( + "ArrayPushCallbackChunkFormatPlugin", + (chunk, set, { chunkGraph }) => { + if (chunk.hasRuntime()) return; + if (chunkGraph.getNumberOfEntryModules(chunk) > 0) { + set.add(RuntimeGlobals.onChunksLoaded); + set.add(RuntimeGlobals.require); + } + set.add(RuntimeGlobals.chunkCallback); + } + ); + const hooks = getCompilationHooks(compilation); + hooks.renderChunk.tap( + "ArrayPushCallbackChunkFormatPlugin", + (modules, renderContext) => { + const { chunk, chunkGraph, runtimeTemplate } = renderContext; + const hotUpdateChunk = + chunk instanceof HotUpdateChunk ? chunk : null; + const globalObject = runtimeTemplate.outputOptions.globalObject; + const source = new ConcatSource(); + const runtimeModules = + chunkGraph.getChunkRuntimeModulesInOrder(chunk); + if (hotUpdateChunk) { + const hotUpdateGlobal = + runtimeTemplate.outputOptions.hotUpdateGlobal; + source.add( + `${globalObject}[${JSON.stringify(hotUpdateGlobal)}](` + ); + source.add(`${JSON.stringify(chunk.id)},`); + source.add(modules); + if (runtimeModules.length > 0) { + source.add(",\n"); + const runtimePart = Template.renderChunkRuntimeModules( + runtimeModules, + renderContext + ); + source.add(runtimePart); + } + source.add(")"); + } else { + const chunkLoadingGlobal = + runtimeTemplate.outputOptions.chunkLoadingGlobal; + source.add( + `(${globalObject}[${JSON.stringify( + chunkLoadingGlobal + )}] = ${globalObject}[${JSON.stringify( + chunkLoadingGlobal + )}] || []).push([` + ); + source.add(`${JSON.stringify(chunk.ids)},`); + source.add(modules); + const entries = Array.from( + chunkGraph.getChunkEntryModulesWithChunkGroupIterable(chunk) + ); + if (runtimeModules.length > 0 || entries.length > 0) { + const runtime = new ConcatSource( + (runtimeTemplate.supportsArrowFunction() + ? "__webpack_require__ =>" + : "function(__webpack_require__)") + + " { // webpackRuntimeModules\n" + ); + if (runtimeModules.length > 0) { + runtime.add( + Template.renderRuntimeModules(runtimeModules, { + ...renderContext, + codeGenerationResults: compilation.codeGenerationResults + }) + ); + } + if (entries.length > 0) { + const startupSource = new RawSource( + generateEntryStartup( + chunkGraph, + runtimeTemplate, + entries, + chunk, + true + ) + ); + runtime.add( + hooks.renderStartup.call( + startupSource, + entries[entries.length - 1][0], + { + ...renderContext, + inlined: false + } + ) + ); + if ( + chunkGraph + .getChunkRuntimeRequirements(chunk) + .has(RuntimeGlobals.returnExportsFromRuntime) + ) { + runtime.add("return __webpack_exports__;\n"); + } + } + runtime.add("}\n"); + source.add(",\n"); + source.add(new PrefixSource("/******/ ", runtime)); + } + source.add("])"); + } + return source; + } + ); + hooks.chunkHash.tap( + "ArrayPushCallbackChunkFormatPlugin", + (chunk, hash, { chunkGraph, runtimeTemplate }) => { + if (chunk.hasRuntime()) return; + hash.update( + `ArrayPushCallbackChunkFormatPlugin1${runtimeTemplate.outputOptions.chunkLoadingGlobal}${runtimeTemplate.outputOptions.hotUpdateGlobal}${runtimeTemplate.outputOptions.globalObject}` + ); + const entries = Array.from( + chunkGraph.getChunkEntryModulesWithChunkGroupIterable(chunk) + ); + updateHashForEntryStartup(hash, chunkGraph, entries, chunk); + } + ); + } ); } +} - /** - * @deprecated - * @param {any} params scope params - * @param {function(): void} fn inner function - * @returns {void} - */ - inScope(params, fn) { - const oldScope = this.scope; - this.scope = { - topLevelScope: oldScope.topLevelScope, - inTry: false, - inShorthand: false, - isStrict: oldScope.isStrict, - isAsmJs: oldScope.isAsmJs, - definitions: oldScope.definitions.createChild() - }; +module.exports = ArrayPushCallbackChunkFormatPlugin; - this.undefineVariable("this"); - this.enterPatterns(params, (ident, pattern) => { - this.defineVariable(ident); - }); +/***/ }), - fn(); +/***/ 2412: +/***/ (function(module) { - this.scope = oldScope; - } +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ - inFunctionScope(hasThis, params, fn) { - const oldScope = this.scope; - this.scope = { - topLevelScope: oldScope.topLevelScope, - inTry: false, - inShorthand: false, - isStrict: oldScope.isStrict, - isAsmJs: oldScope.isAsmJs, - definitions: oldScope.definitions.createChild() - }; - if (hasThis) { - this.undefineVariable("this"); - } - this.enterPatterns(params, (ident, pattern) => { - this.defineVariable(ident); - }); +/** @typedef {import("estree").Node} EsTreeNode */ +/** @typedef {import("./JavascriptParser").VariableInfoInterface} VariableInfoInterface */ - fn(); +const TypeUnknown = 0; +const TypeUndefined = 1; +const TypeNull = 2; +const TypeString = 3; +const TypeNumber = 4; +const TypeBoolean = 5; +const TypeRegExp = 6; +const TypeConditional = 7; +const TypeArray = 8; +const TypeConstArray = 9; +const TypeIdentifier = 10; +const TypeWrapped = 11; +const TypeTemplateString = 12; +const TypeBigInt = 13; - this.scope = oldScope; +class BasicEvaluatedExpression { + constructor() { + this.type = TypeUnknown; + /** @type {[number, number]} */ + this.range = undefined; + /** @type {boolean} */ + this.falsy = false; + /** @type {boolean} */ + this.truthy = false; + /** @type {boolean | undefined} */ + this.nullish = undefined; + /** @type {boolean} */ + this.sideEffects = true; + /** @type {boolean | undefined} */ + this.bool = undefined; + /** @type {number | undefined} */ + this.number = undefined; + /** @type {bigint | undefined} */ + this.bigint = undefined; + /** @type {RegExp | undefined} */ + this.regExp = undefined; + /** @type {string | undefined} */ + this.string = undefined; + /** @type {BasicEvaluatedExpression[] | undefined} */ + this.quasis = undefined; + /** @type {BasicEvaluatedExpression[] | undefined} */ + this.parts = undefined; + /** @type {any[] | undefined} */ + this.array = undefined; + /** @type {BasicEvaluatedExpression[] | undefined} */ + this.items = undefined; + /** @type {BasicEvaluatedExpression[] | undefined} */ + this.options = undefined; + /** @type {BasicEvaluatedExpression | undefined} */ + this.prefix = undefined; + /** @type {BasicEvaluatedExpression | undefined} */ + this.postfix = undefined; + this.wrappedInnerExpressions = undefined; + /** @type {string | undefined} */ + this.identifier = undefined; + /** @type {VariableInfoInterface} */ + this.rootInfo = undefined; + /** @type {() => string[]} */ + this.getMembers = undefined; + /** @type {EsTreeNode} */ + this.expression = undefined; } - inBlockScope(fn) { - const oldScope = this.scope; - this.scope = { - topLevelScope: oldScope.topLevelScope, - inTry: oldScope.inTry, - inShorthand: false, - isStrict: oldScope.isStrict, - isAsmJs: oldScope.isAsmJs, - definitions: oldScope.definitions.createChild() - }; + isUnknown() { + return this.type === TypeUnknown; + } - fn(); + isNull() { + return this.type === TypeNull; + } - this.scope = oldScope; + isUndefined() { + return this.type === TypeUndefined; } - detectMode(statements) { - const isLiteral = - statements.length >= 1 && - statements[0].type === "ExpressionStatement" && - statements[0].expression.type === "Literal"; - if (isLiteral && statements[0].expression.value === "use strict") { - this.scope.isStrict = true; - } - if (isLiteral && statements[0].expression.value === "use asm") { - this.scope.isAsmJs = true; - } + isString() { + return this.type === TypeString; } - enterPatterns(patterns, onIdent) { - for (const pattern of patterns) { - if (typeof pattern !== "string") { - this.enterPattern(pattern, onIdent); - } else if (pattern) { - onIdent(pattern); - } - } + isNumber() { + return this.type === TypeNumber; } - enterPattern(pattern, onIdent) { - if (!pattern) return; - switch (pattern.type) { - case "ArrayPattern": - this.enterArrayPattern(pattern, onIdent); - break; - case "AssignmentPattern": - this.enterAssignmentPattern(pattern, onIdent); - break; - case "Identifier": - this.enterIdentifier(pattern, onIdent); - break; - case "ObjectPattern": - this.enterObjectPattern(pattern, onIdent); - break; - case "RestElement": - this.enterRestElement(pattern, onIdent); - break; - case "Property": - if (pattern.shorthand && pattern.value.type === "Identifier") { - this.scope.inShorthand = pattern.value.name; - this.enterIdentifier(pattern.value, onIdent); - this.scope.inShorthand = false; - } else { - this.enterPattern(pattern.value, onIdent); - } - break; - } + isBigInt() { + return this.type === TypeBigInt; } - enterIdentifier(pattern, onIdent) { - if (!this.callHooksForName(this.hooks.pattern, pattern.name, pattern)) { - onIdent(pattern.name, pattern); - } + isBoolean() { + return this.type === TypeBoolean; } - enterObjectPattern(pattern, onIdent) { - for ( - let propIndex = 0, len = pattern.properties.length; - propIndex < len; - propIndex++ - ) { - const prop = pattern.properties[propIndex]; - this.enterPattern(prop, onIdent); - } + isRegExp() { + return this.type === TypeRegExp; } - enterArrayPattern(pattern, onIdent) { - for ( - let elementIndex = 0, len = pattern.elements.length; - elementIndex < len; - elementIndex++ - ) { - const element = pattern.elements[elementIndex]; - this.enterPattern(element, onIdent); - } + isConditional() { + return this.type === TypeConditional; } - enterRestElement(pattern, onIdent) { - this.enterPattern(pattern.argument, onIdent); + isArray() { + return this.type === TypeArray; } - enterAssignmentPattern(pattern, onIdent) { - this.enterPattern(pattern.left, onIdent); + isConstArray() { + return this.type === TypeConstArray; } - /** - * @param {ExpressionNode} expression expression node - * @returns {BasicEvaluatedExpression | undefined} evaluation result - */ - evaluateExpression(expression) { - try { - const hook = this.hooks.evaluate.get(expression.type); - if (hook !== undefined) { - const result = hook.call(expression); - if (result !== undefined) { - if (result) { - result.setExpression(expression); - } - return result; - } - } - } catch (e) { - console.warn(e); - // ignore error - } - return new BasicEvaluatedExpression() - .setRange(expression.range) - .setExpression(expression); + isIdentifier() { + return this.type === TypeIdentifier; } - parseString(expression) { - switch (expression.type) { - case "BinaryExpression": - if (expression.operator === "+") { - return ( - this.parseString(expression.left) + - this.parseString(expression.right) - ); - } - break; - case "Literal": - return expression.value + ""; + isWrapped() { + return this.type === TypeWrapped; + } + + isTemplateString() { + return this.type === TypeTemplateString; + } + + /** + * Is expression a primitive or an object type value? + * @returns {boolean | undefined} true: primitive type, false: object type, undefined: unknown/runtime-defined + */ + isPrimitiveType() { + switch (this.type) { + case TypeUndefined: + case TypeNull: + case TypeString: + case TypeNumber: + case TypeBoolean: + case TypeBigInt: + case TypeWrapped: + case TypeTemplateString: + return true; + case TypeRegExp: + case TypeArray: + case TypeConstArray: + return false; + default: + return undefined; } - throw new Error( - expression.type + " is not supported as parameter for require" - ); } - parseCalculatedString(expression) { - switch (expression.type) { - case "BinaryExpression": - if (expression.operator === "+") { - const left = this.parseCalculatedString(expression.left); - const right = this.parseCalculatedString(expression.right); - if (left.code) { - return { - range: left.range, - value: left.value, - code: true, - conditional: false - }; - } else if (right.code) { - return { - range: [ - left.range[0], - right.range ? right.range[1] : left.range[1] - ], - value: left.value + right.value, - code: true, - conditional: false - }; - } else { - return { - range: [left.range[0], right.range[1]], - value: left.value + right.value, - code: false, - conditional: false - }; - } - } - break; - case "ConditionalExpression": { - const consequent = this.parseCalculatedString(expression.consequent); - const alternate = this.parseCalculatedString(expression.alternate); - const items = []; - if (consequent.conditional) { - items.push(...consequent.conditional); - } else if (!consequent.code) { - items.push(consequent); - } else { - break; - } - if (alternate.conditional) { - items.push(...alternate.conditional); - } else if (!alternate.code) { - items.push(alternate); - } else { - break; - } - return { - range: undefined, - value: "", - code: true, - conditional: items - }; - } - case "Literal": - return { - range: expression.range, - value: expression.value + "", - code: false, - conditional: false - }; + /** + * Is expression a runtime or compile-time value? + * @returns {boolean} true: compile time value, false: runtime value + */ + isCompileTimeValue() { + switch (this.type) { + case TypeUndefined: + case TypeNull: + case TypeString: + case TypeNumber: + case TypeBoolean: + case TypeRegExp: + case TypeConstArray: + case TypeBigInt: + return true; + default: + return false; } - return { - range: undefined, - value: "", - code: true, - conditional: false - }; } /** - * @param {string | Buffer | PreparsedAst} source the source to parse - * @param {ParserState} state the parser state - * @returns {ParserState} the parser state + * Gets the compile-time value of the expression + * @returns {any} the javascript value */ - parse(source, state) { - let ast; - let comments; - const semicolons = new Set(); - if (source === null) { - throw new Error("source must not be null"); - } - if (Buffer.isBuffer(source)) { - source = source.toString("utf-8"); - } - if (typeof source === "object") { - ast = /** @type {ProgramNode} */ (source); - comments = source.comments; - } else { - comments = []; - ast = JavascriptParser._parse(source, { - sourceType: this.sourceType, - onComment: comments, - onInsertedSemicolon: pos => semicolons.add(pos) - }); + asCompileTimeValue() { + switch (this.type) { + case TypeUndefined: + return undefined; + case TypeNull: + return null; + case TypeString: + return this.string; + case TypeNumber: + return this.number; + case TypeBoolean: + return this.bool; + case TypeRegExp: + return this.regExp; + case TypeConstArray: + return this.array; + case TypeBigInt: + return this.bigint; + default: + throw new Error( + "asCompileTimeValue must only be called for compile-time values" + ); } + } - const oldScope = this.scope; - const oldState = this.state; - const oldComments = this.comments; - const oldSemicolons = this.semicolons; - const oldStatementPath = this.statementPath; - const oldPrevStatement = this.prevStatement; - this.scope = { - topLevelScope: true, - inTry: false, - inShorthand: false, - isStrict: false, - isAsmJs: false, - definitions: new StackedMap() - }; - /** @type {ParserState} */ - this.state = state; - this.comments = comments; - this.semicolons = semicolons; - this.statementPath = []; - this.prevStatement = undefined; - if (this.hooks.program.call(ast, comments) === undefined) { - this.detectMode(ast.body); - this.preWalkStatements(ast.body); - this.prevStatement = undefined; - this.blockPreWalkStatements(ast.body); - this.prevStatement = undefined; - this.walkStatements(ast.body); - } - this.hooks.finish.call(ast, comments); - this.scope = oldScope; - /** @type {ParserState} */ - this.state = oldState; - this.comments = oldComments; - this.semicolons = oldSemicolons; - this.statementPath = oldStatementPath; - this.prevStatement = oldPrevStatement; - return state; + isTruthy() { + return this.truthy; } - evaluate(source) { - const ast = JavascriptParser._parse("(" + source + ")", { - sourceType: this.sourceType, - locations: false - }); - if (ast.body.length !== 1 || ast.body[0].type !== "ExpressionStatement") { - throw new Error("evaluate: Source is not a expression"); - } - return this.evaluateExpression(ast.body[0].expression); + isFalsy() { + return this.falsy; + } + + isNullish() { + return this.nullish; } /** - * @param {ExpressionNode | DeclarationNode | PrivateIdentifierNode | null | undefined} expr an expression - * @param {number} commentsStartPos source position from which annotation comments are checked - * @returns {boolean} true, when the expression is pure + * Can this expression have side effects? + * @returns {boolean} false: never has side effects */ - isPure(expr, commentsStartPos) { - if (!expr) return true; - const result = this.hooks.isPure - .for(expr.type) - .call(expr, commentsStartPos); - if (typeof result === "boolean") return result; - switch (expr.type) { - case "ClassDeclaration": - case "ClassExpression": { - if (expr.body.type !== "ClassBody") return false; - if (expr.superClass && !this.isPure(expr.superClass, expr.range[0])) { - return false; - } - const items = - /** @type {(MethodDefinitionNode | PropertyDefinitionNode)[]} */ ( - expr.body.body - ); - return items.every( - item => - (!item.computed || - !item.key || - this.isPure(item.key, item.range[0])) && - (!item.static || - !item.value || - this.isPure( - item.value, - item.key ? item.key.range[1] : item.range[0] - )) - ); - } + couldHaveSideEffects() { + return this.sideEffects; + } - case "FunctionDeclaration": - case "FunctionExpression": - case "ArrowFunctionExpression": - case "Literal": - case "PrivateIdentifier": - return true; + asBool() { + if (this.truthy) return true; + if (this.falsy || this.nullish) return false; + if (this.isBoolean()) return this.bool; + if (this.isNull()) return false; + if (this.isUndefined()) return false; + if (this.isString()) return this.string !== ""; + if (this.isNumber()) return this.number !== 0; + if (this.isBigInt()) return this.bigint !== BigInt(0); + if (this.isRegExp()) return true; + if (this.isArray()) return true; + if (this.isConstArray()) return true; + if (this.isWrapped()) { + return (this.prefix && this.prefix.asBool()) || + (this.postfix && this.postfix.asBool()) + ? true + : undefined; + } + if (this.isTemplateString()) { + const str = this.asString(); + if (typeof str === "string") return str !== ""; + } + return undefined; + } - case "VariableDeclaration": - return expr.declarations.every(decl => - this.isPure(decl.init, decl.range[0]) - ); + asNullish() { + const nullish = this.isNullish(); - case "ConditionalExpression": - return ( - this.isPure(expr.test, commentsStartPos) && - this.isPure(expr.consequent, expr.test.range[1]) && - this.isPure(expr.alternate, expr.consequent.range[1]) - ); + if (nullish === true || this.isNull() || this.isUndefined()) return true; - case "SequenceExpression": - return expr.expressions.every(expr => { - const pureFlag = this.isPure(expr, commentsStartPos); - commentsStartPos = expr.range[1]; - return pureFlag; - }); + if (nullish === false) return false; + if (this.isTruthy()) return false; + if (this.isBoolean()) return false; + if (this.isString()) return false; + if (this.isNumber()) return false; + if (this.isBigInt()) return false; + if (this.isRegExp()) return false; + if (this.isArray()) return false; + if (this.isConstArray()) return false; + if (this.isTemplateString()) return false; + if (this.isRegExp()) return false; - case "CallExpression": { - const pureFlag = - expr.range[0] - commentsStartPos > 12 && - this.getComments([commentsStartPos, expr.range[0]]).some( - comment => - comment.type === "Block" && - /^\s*(#|@)__PURE__\s*$/.test(comment.value) - ); - if (!pureFlag) return false; - commentsStartPos = expr.callee.range[1]; - return expr.arguments.every(arg => { - if (arg.type === "SpreadElement") return false; - const pureFlag = this.isPure(arg, commentsStartPos); - commentsStartPos = arg.range[1]; - return pureFlag; - }); - } - } - const evaluated = this.evaluateExpression(expr); - return !evaluated.couldHaveSideEffects(); + return undefined; } - getComments(range) { - const [rangeStart, rangeEnd] = range; - const compare = (comment, needle) => comment.range[0] - needle; - let idx = binarySearchBounds.ge(this.comments, rangeStart, compare); - let commentsInRange = []; - while (this.comments[idx] && this.comments[idx].range[1] <= rangeEnd) { - commentsInRange.push(this.comments[idx]); - idx++; + asString() { + if (this.isBoolean()) return `${this.bool}`; + if (this.isNull()) return "null"; + if (this.isUndefined()) return "undefined"; + if (this.isString()) return this.string; + if (this.isNumber()) return `${this.number}`; + if (this.isBigInt()) return `${this.bigint}`; + if (this.isRegExp()) return `${this.regExp}`; + if (this.isArray()) { + let array = []; + for (const item of this.items) { + const itemStr = item.asString(); + if (itemStr === undefined) return undefined; + array.push(itemStr); + } + return `${array}`; + } + if (this.isConstArray()) return `${this.array}`; + if (this.isTemplateString()) { + let str = ""; + for (const part of this.parts) { + const partStr = part.asString(); + if (partStr === undefined) return undefined; + str += partStr; + } + return str; } + return undefined; + } - return commentsInRange; + setString(string) { + this.type = TypeString; + this.string = string; + this.sideEffects = false; + return this; } - /** - * @param {number} pos source code position - * @returns {boolean} true when a semicolon has been inserted before this position, false if not - */ - isAsiPosition(pos) { - const currentStatement = this.statementPath[this.statementPath.length - 1]; - if (currentStatement === undefined) throw new Error("Not in statement"); - return ( - // Either asking directly for the end position of the current statement - (currentStatement.range[1] === pos && this.semicolons.has(pos)) || - // Or asking for the start position of the current statement, - // here we have to check multiple things - (currentStatement.range[0] === pos && - // is there a previous statement which might be relevant? - this.prevStatement !== undefined && - // is the end position of the previous statement an ASI position? - this.semicolons.has(this.prevStatement.range[1])) - ); + setUndefined() { + this.type = TypeUndefined; + this.sideEffects = false; + return this; } - /** - * @param {number} pos source code position - * @returns {void} - */ - unsetAsiPosition(pos) { - this.semicolons.delete(pos); + setNull() { + this.type = TypeNull; + this.sideEffects = false; + return this; } - isStatementLevelExpression(expr) { - const currentStatement = this.statementPath[this.statementPath.length - 1]; - return ( - expr === currentStatement || - (currentStatement.type === "ExpressionStatement" && - currentStatement.expression === expr) - ); + setNumber(number) { + this.type = TypeNumber; + this.number = number; + this.sideEffects = false; + return this; } - getTagData(name, tag) { - const info = this.scope.definitions.get(name); - if (info instanceof VariableInfo) { - let tagInfo = info.tagInfo; - while (tagInfo !== undefined) { - if (tagInfo.tag === tag) return tagInfo.data; - tagInfo = tagInfo.next; - } - } + setBigInt(bigint) { + this.type = TypeBigInt; + this.bigint = bigint; + this.sideEffects = false; + return this; } - tagVariable(name, tag, data) { - const oldInfo = this.scope.definitions.get(name); - /** @type {VariableInfo} */ - let newInfo; - if (oldInfo === undefined) { - newInfo = new VariableInfo(this.scope, name, { - tag, - data, - next: undefined - }); - } else if (oldInfo instanceof VariableInfo) { - newInfo = new VariableInfo(oldInfo.declaredScope, oldInfo.freeName, { - tag, - data, - next: oldInfo.tagInfo - }); - } else { - newInfo = new VariableInfo(oldInfo, true, { - tag, - data, - next: undefined - }); - } - this.scope.definitions.set(name, newInfo); + setBoolean(bool) { + this.type = TypeBoolean; + this.bool = bool; + this.sideEffects = false; + return this; } - defineVariable(name) { - const oldInfo = this.scope.definitions.get(name); - // Don't redefine variable in same scope to keep existing tags - if (oldInfo instanceof VariableInfo && oldInfo.declaredScope === this.scope) - return; - this.scope.definitions.set(name, this.scope); + setRegExp(regExp) { + this.type = TypeRegExp; + this.regExp = regExp; + this.sideEffects = false; + return this; } - undefineVariable(name) { - this.scope.definitions.delete(name); + setIdentifier(identifier, rootInfo, getMembers) { + this.type = TypeIdentifier; + this.identifier = identifier; + this.rootInfo = rootInfo; + this.getMembers = getMembers; + this.sideEffects = true; + return this; } - isVariableDefined(name) { - const info = this.scope.definitions.get(name); - if (info === undefined) return false; - if (info instanceof VariableInfo) { - return info.freeName === true; - } - return true; + setWrapped(prefix, postfix, innerExpressions) { + this.type = TypeWrapped; + this.prefix = prefix; + this.postfix = postfix; + this.wrappedInnerExpressions = innerExpressions; + this.sideEffects = true; + return this; } - /** - * @param {string} name variable name - * @returns {ExportedVariableInfo} info for this variable - */ - getVariableInfo(name) { - const value = this.scope.definitions.get(name); - if (value === undefined) { - return name; - } else { - return value; - } + setOptions(options) { + this.type = TypeConditional; + this.options = options; + this.sideEffects = true; + return this; } - /** - * @param {string} name variable name - * @param {ExportedVariableInfo} variableInfo new info for this variable - * @returns {void} - */ - setVariable(name, variableInfo) { - if (typeof variableInfo === "string") { - if (variableInfo === name) { - this.scope.definitions.delete(name); - } else { - this.scope.definitions.set( - name, - new VariableInfo(this.scope, variableInfo, undefined) - ); - } - } else { - this.scope.definitions.set(name, variableInfo); + addOptions(options) { + if (!this.options) { + this.type = TypeConditional; + this.options = []; + this.sideEffects = true; + } + for (const item of options) { + this.options.push(item); } + return this; } - parseCommentOptions(range) { - const comments = this.getComments(range); - if (comments.length === 0) { - return EMPTY_COMMENT_OPTIONS; - } - let options = {}; - let errors = []; - for (const comment of comments) { - const { value } = comment; - if (value && webpackCommentRegExp.test(value)) { - // try compile only if webpack options comment is present - try { - const val = vm.runInNewContext(`(function(){return {${value}};})()`); - Object.assign(options, val); - } catch (e) { - e.comment = comment; - errors.push(e); - } - } - } - return { options, errors }; + setItems(items) { + this.type = TypeArray; + this.items = items; + this.sideEffects = items.some(i => i.couldHaveSideEffects()); + return this; } - /** - * @param {MemberExpressionNode} expression a member expression - * @returns {{ members: string[], object: ExpressionNode | SuperNode }} member names (reverse order) and remaining object - */ - extractMemberExpressionChain(expression) { - /** @type {AnyNode} */ - let expr = expression; - const members = []; - while (expr.type === "MemberExpression") { - if (expr.computed) { - if (expr.property.type !== "Literal") break; - members.push(`${expr.property.value}`); - } else { - if (expr.property.type !== "Identifier") break; - members.push(expr.property.name); - } - expr = expr.object; - } - return { - members, - object: expr - }; + setArray(array) { + this.type = TypeConstArray; + this.array = array; + this.sideEffects = false; + return this; } - /** - * @param {string} varName variable name - * @returns {{name: string, info: VariableInfo | string}} name of the free variable and variable info for that - */ - getFreeInfoFromVariable(varName) { - const info = this.getVariableInfo(varName); - let name; - if (info instanceof VariableInfo) { - name = info.freeName; - if (typeof name !== "string") return undefined; - } else if (typeof info !== "string") { - return undefined; - } else { - name = info; - } - return { info, name }; + setTemplateString(quasis, parts, kind) { + this.type = TypeTemplateString; + this.quasis = quasis; + this.parts = parts; + this.templateStringKind = kind; + this.sideEffects = parts.some(p => p.sideEffects); + return this; } - /** @typedef {{ type: "call", call: CallExpressionNode, calleeName: string, rootInfo: string | VariableInfo, getCalleeMembers: () => string[], name: string, getMembers: () => string[]}} CallExpressionInfo */ - /** @typedef {{ type: "expression", rootInfo: string | VariableInfo, name: string, getMembers: () => string[]}} ExpressionExpressionInfo */ + setTruthy() { + this.falsy = false; + this.truthy = true; + this.nullish = false; + return this; + } - /** - * @param {MemberExpressionNode} expression a member expression - * @param {number} allowedTypes which types should be returned, presented in bit mask - * @returns {CallExpressionInfo | ExpressionExpressionInfo | undefined} expression info - */ - getMemberExpressionInfo(expression, allowedTypes) { - const { object, members } = this.extractMemberExpressionChain(expression); - switch (object.type) { - case "CallExpression": { - if ((allowedTypes & ALLOWED_MEMBER_TYPES_CALL_EXPRESSION) === 0) - return undefined; - let callee = object.callee; - let rootMembers = EMPTY_ARRAY; - if (callee.type === "MemberExpression") { - ({ object: callee, members: rootMembers } = - this.extractMemberExpressionChain(callee)); - } - const rootName = getRootName(callee); - if (!rootName) return undefined; - const result = this.getFreeInfoFromVariable(rootName); - if (!result) return undefined; - const { info: rootInfo, name: resolvedRoot } = result; - const calleeName = objectAndMembersToName(resolvedRoot, rootMembers); - return { - type: "call", - call: object, - calleeName, - rootInfo, - getCalleeMembers: memoize(() => rootMembers.reverse()), - name: objectAndMembersToName(`${calleeName}()`, members), - getMembers: memoize(() => members.reverse()) - }; - } - case "Identifier": - case "MetaProperty": - case "ThisExpression": { - if ((allowedTypes & ALLOWED_MEMBER_TYPES_EXPRESSION) === 0) - return undefined; - const rootName = getRootName(object); - if (!rootName) return undefined; + setFalsy() { + this.falsy = true; + this.truthy = false; + return this; + } - const result = this.getFreeInfoFromVariable(rootName); - if (!result) return undefined; - const { info: rootInfo, name: resolvedRoot } = result; - return { - type: "expression", - name: objectAndMembersToName(resolvedRoot, members), - rootInfo, - getMembers: memoize(() => members.reverse()) - }; - } - } + setNullish(value) { + this.nullish = value; + + if (value) return this.setFalsy(); + + return this; } - /** - * @param {MemberExpressionNode} expression an expression - * @returns {{ name: string, rootInfo: ExportedVariableInfo, getMembers: () => string[]}} name info - */ - getNameForExpression(expression) { - return this.getMemberExpressionInfo( - expression, - ALLOWED_MEMBER_TYPES_EXPRESSION - ); + setRange(range) { + this.range = range; + return this; } - /** - * @param {string} code source code - * @param {ParseOptions} options parsing options - * @returns {ProgramNode} parsed ast - */ - static _parse(code, options) { - const type = options ? options.sourceType : "module"; - /** @type {AcornOptions} */ - const parserOptions = { - ...defaultParserOptions, - allowReturnOutsideFunction: type === "script", - ...options, - sourceType: type === "auto" ? "module" : type - }; + setSideEffects(sideEffects = true) { + this.sideEffects = sideEffects; + return this; + } - /** @type {AnyNode} */ - let ast; - let error; - let threw = false; - try { - ast = /** @type {AnyNode} */ (parser.parse(code, parserOptions)); - } catch (e) { - error = e; - threw = true; - } + setExpression(expression) { + this.expression = expression; + return this; + } +} - if (threw && type === "auto") { - parserOptions.sourceType = "script"; - if (!("allowReturnOutsideFunction" in options)) { - parserOptions.allowReturnOutsideFunction = true; - } - if (Array.isArray(parserOptions.onComment)) { - parserOptions.onComment.length = 0; - } - try { - ast = /** @type {AnyNode} */ (parser.parse(code, parserOptions)); - threw = false; - } catch (e) { - // we use the error from first parse try - // so nothing to do here - } - } +/** + * @param {string} flags regexp flags + * @returns {boolean} is valid flags + */ +BasicEvaluatedExpression.isValidRegExpFlags = flags => { + const len = flags.length; - if (threw) { - throw error; + if (len === 0) return true; + if (len > 4) return false; + + // cspell:word gimy + let remaining = 0b0000; // bit per RegExp flag: gimy + + for (let i = 0; i < len; i++) + switch (flags.charCodeAt(i)) { + case 103 /* g */: + if (remaining & 0b1000) return false; + remaining |= 0b1000; + break; + case 105 /* i */: + if (remaining & 0b0100) return false; + remaining |= 0b0100; + break; + case 109 /* m */: + if (remaining & 0b0010) return false; + remaining |= 0b0010; + break; + case 121 /* y */: + if (remaining & 0b0001) return false; + remaining |= 0b0001; + break; + default: + return false; } - return /** @type {ProgramNode} */ (ast); - } -} + return true; +}; -module.exports = JavascriptParser; -module.exports.ALLOWED_MEMBER_TYPES_ALL = ALLOWED_MEMBER_TYPES_ALL; -module.exports.ALLOWED_MEMBER_TYPES_EXPRESSION = - ALLOWED_MEMBER_TYPES_EXPRESSION; -module.exports.ALLOWED_MEMBER_TYPES_CALL_EXPRESSION = - ALLOWED_MEMBER_TYPES_CALL_EXPRESSION; +module.exports = BasicEvaluatedExpression; /***/ }), -/***/ 28723: -/***/ (function(__unused_webpack_module, exports, __webpack_require__) { +/***/ 57634: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; /* @@ -96389,112 +92570,177 @@ module.exports.ALLOWED_MEMBER_TYPES_CALL_EXPRESSION = -const UnsupportedFeatureWarning = __webpack_require__(9532); -const ConstDependency = __webpack_require__(60864); -const BasicEvaluatedExpression = __webpack_require__(2412); - -/** @typedef {import("estree").Expression} ExpressionNode */ -/** @typedef {import("estree").Node} Node */ -/** @typedef {import("./JavascriptParser")} JavascriptParser */ - -/** - * @param {JavascriptParser} parser the parser - * @param {string} value the const value - * @param {string[]=} runtimeRequirements runtime requirements - * @returns {function(ExpressionNode): true} plugin function - */ -exports.toConstantDependency = (parser, value, runtimeRequirements) => { - return function constDependency(expr) { - const dep = new ConstDependency(value, expr.range, runtimeRequirements); - dep.loc = expr.loc; - parser.state.module.addPresentationalDependency(dep); - return true; - }; -}; +const { ConcatSource, RawSource } = __webpack_require__(96192); +const RuntimeGlobals = __webpack_require__(49404); +const Template = __webpack_require__(92066); +const { + getChunkFilenameTemplate, + getCompilationHooks +} = __webpack_require__(76767); +const { + generateEntryStartup, + updateHashForEntryStartup +} = __webpack_require__(30951); -/** - * @param {string} value the string value - * @returns {function(ExpressionNode): BasicEvaluatedExpression} plugin function - */ -exports.evaluateToString = value => { - return function stringExpression(expr) { - return new BasicEvaluatedExpression().setString(value).setRange(expr.range); - }; -}; +/** @typedef {import("../Compiler")} Compiler */ -/** - * @param {number} value the number value - * @returns {function(ExpressionNode): BasicEvaluatedExpression} plugin function - */ -exports.evaluateToNumber = value => { - return function stringExpression(expr) { - return new BasicEvaluatedExpression().setNumber(value).setRange(expr.range); - }; -}; +class CommonJsChunkFormatPlugin { + /** + * Apply the plugin + * @param {Compiler} compiler the compiler instance + * @returns {void} + */ + apply(compiler) { + compiler.hooks.thisCompilation.tap( + "CommonJsChunkFormatPlugin", + compilation => { + compilation.hooks.additionalChunkRuntimeRequirements.tap( + "CommonJsChunkLoadingPlugin", + (chunk, set, { chunkGraph }) => { + if (chunk.hasRuntime()) return; + if (chunkGraph.getNumberOfEntryModules(chunk) > 0) { + set.add(RuntimeGlobals.require); + set.add(RuntimeGlobals.startupEntrypoint); + set.add(RuntimeGlobals.externalInstallChunk); + } + } + ); + const hooks = getCompilationHooks(compilation); + hooks.renderChunk.tap( + "CommonJsChunkFormatPlugin", + (modules, renderContext) => { + const { chunk, chunkGraph, runtimeTemplate } = renderContext; + const source = new ConcatSource(); + source.add(`exports.id = ${JSON.stringify(chunk.id)};\n`); + source.add(`exports.ids = ${JSON.stringify(chunk.ids)};\n`); + source.add(`exports.modules = `); + source.add(modules); + source.add(";\n"); + const runtimeModules = + chunkGraph.getChunkRuntimeModulesInOrder(chunk); + if (runtimeModules.length > 0) { + source.add("exports.runtime =\n"); + source.add( + Template.renderChunkRuntimeModules( + runtimeModules, + renderContext + ) + ); + } + const entries = Array.from( + chunkGraph.getChunkEntryModulesWithChunkGroupIterable(chunk) + ); + if (entries.length > 0) { + const runtimeChunk = entries[0][1].getRuntimeChunk(); + const currentOutputName = compilation + .getPath( + getChunkFilenameTemplate(chunk, compilation.outputOptions), + { + chunk, + contentHashType: "javascript" + } + ) + .split("/"); + const runtimeOutputName = compilation + .getPath( + getChunkFilenameTemplate( + runtimeChunk, + compilation.outputOptions + ), + { + chunk: runtimeChunk, + contentHashType: "javascript" + } + ) + .split("/"); -/** - * @param {boolean} value the boolean value - * @returns {function(ExpressionNode): BasicEvaluatedExpression} plugin function - */ -exports.evaluateToBoolean = value => { - return function booleanExpression(expr) { - return new BasicEvaluatedExpression() - .setBoolean(value) - .setRange(expr.range); - }; -}; + // remove filename, we only need the directory + currentOutputName.pop(); -/** - * @param {string} identifier identifier - * @param {string} rootInfo rootInfo - * @param {function(): string[]} getMembers getMembers - * @param {boolean|null=} truthy is truthy, null if nullish - * @returns {function(ExpressionNode): BasicEvaluatedExpression} callback - */ -exports.evaluateToIdentifier = (identifier, rootInfo, getMembers, truthy) => { - return function identifierExpression(expr) { - let evaluatedExpression = new BasicEvaluatedExpression() - .setIdentifier(identifier, rootInfo, getMembers) - .setSideEffects(false) - .setRange(expr.range); - switch (truthy) { - case true: - evaluatedExpression.setTruthy(); - break; - case null: - evaluatedExpression.setNullish(true); - break; - case false: - evaluatedExpression.setFalsy(); - break; - } + // remove common parts + while ( + currentOutputName.length > 0 && + runtimeOutputName.length > 0 && + currentOutputName[0] === runtimeOutputName[0] + ) { + currentOutputName.shift(); + runtimeOutputName.shift(); + } - return evaluatedExpression; - }; -}; + // create final path + const runtimePath = + (currentOutputName.length > 0 + ? "../".repeat(currentOutputName.length) + : "./") + runtimeOutputName.join("/"); -exports.expressionIsUnsupported = (parser, message) => { - return function unsupportedExpression(expr) { - const dep = new ConstDependency("(void 0)", expr.range, null); - dep.loc = expr.loc; - parser.state.module.addPresentationalDependency(dep); - if (!parser.state.module) return; - parser.state.module.addWarning( - new UnsupportedFeatureWarning(message, expr.loc) + const entrySource = new ConcatSource(); + entrySource.add( + `(${ + runtimeTemplate.supportsArrowFunction() + ? "() => " + : "function() " + }{\n` + ); + entrySource.add("var exports = {};\n"); + entrySource.add(source); + entrySource.add(";\n\n// load runtime\n"); + entrySource.add( + `var __webpack_require__ = require(${JSON.stringify( + runtimePath + )});\n` + ); + entrySource.add( + `${RuntimeGlobals.externalInstallChunk}(exports);\n` + ); + const startupSource = new RawSource( + generateEntryStartup( + chunkGraph, + runtimeTemplate, + entries, + chunk, + false + ) + ); + entrySource.add( + hooks.renderStartup.call( + startupSource, + entries[entries.length - 1][0], + { + ...renderContext, + inlined: false + } + ) + ); + entrySource.add("\n})()"); + return entrySource; + } + return source; + } + ); + hooks.chunkHash.tap( + "CommonJsChunkFormatPlugin", + (chunk, hash, { chunkGraph }) => { + if (chunk.hasRuntime()) return; + hash.update("CommonJsChunkFormatPlugin"); + hash.update("1"); + const entries = Array.from( + chunkGraph.getChunkEntryModulesWithChunkGroupIterable(chunk) + ); + updateHashForEntryStartup(hash, chunkGraph, entries, chunk); + } + ); + } ); - return true; - }; -}; - -exports.skipTraversal = () => true; + } +} -exports.approve = () => true; +module.exports = CommonJsChunkFormatPlugin; /***/ }), -/***/ 30951: -/***/ (function(__unused_webpack_module, exports, __webpack_require__) { +/***/ 34726: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; /* @@ -96504,208 +92750,122 @@ exports.approve = () => true; -const Entrypoint = __webpack_require__(86695); -const RuntimeGlobals = __webpack_require__(49404); -const Template = __webpack_require__(92066); -const { isSubset } = __webpack_require__(34715); -const { chunkHasJs } = __webpack_require__(76767); - -/** @typedef {import("../util/Hash")} Hash */ -/** @typedef {import("../Chunk")} Chunk */ -/** @typedef {import("../Compilation")} Compilation */ -/** @typedef {import("../ChunkGraph")} ChunkGraph */ -/** @typedef {import("../ChunkGroup")} ChunkGroup */ -/** @typedef {import("../RuntimeTemplate")} RuntimeTemplate */ -/** @typedef {(string|number)[]} EntryItem */ +/** @typedef {import("../../declarations/WebpackOptions").ChunkLoadingType} ChunkLoadingType */ +/** @typedef {import("../Compiler")} Compiler */ -// TODO move to this file to ../javascript/ChunkHelpers.js +/** @type {WeakMap>} */ +const enabledTypes = new WeakMap(); -/** - * @param {Entrypoint} entrypoint a chunk group - * @param {Chunk} excludedChunk1 current chunk which is excluded - * @param {Chunk} excludedChunk2 runtime chunk which is excluded - * @returns {Set} chunks - */ -const getAllChunks = (entrypoint, excludedChunk1, excludedChunk2) => { - const queue = new Set([entrypoint]); - const chunks = new Set(); - for (const entrypoint of queue) { - for (const chunk of entrypoint.chunks) { - if (chunk === excludedChunk1) continue; - if (chunk === excludedChunk2) continue; - chunks.add(chunk); - } - for (const parent of entrypoint.parentsIterable) { - if (parent instanceof Entrypoint) queue.add(parent); - } +const getEnabledTypes = compiler => { + let set = enabledTypes.get(compiler); + if (set === undefined) { + set = new Set(); + enabledTypes.set(compiler, set); } - return chunks; + return set; }; -const EXPORT_PREFIX = "var __webpack_exports__ = "; - -/** - * @param {ChunkGraph} chunkGraph chunkGraph - * @param {RuntimeTemplate} runtimeTemplate runtimeTemplate - * @param {import("../ChunkGraph").EntryModuleWithChunkGroup[]} entries entries - * @param {Chunk} chunk chunk - * @param {boolean} passive true: passive startup with on chunks loaded - * @returns {string} runtime code - */ -exports.generateEntryStartup = ( - chunkGraph, - runtimeTemplate, - entries, - chunk, - passive -) => { - /** @type {string[]} */ - const runtime = [ - `var __webpack_exec__ = ${runtimeTemplate.returningFunction( - `__webpack_require__(${RuntimeGlobals.entryModuleId} = moduleId)`, - "moduleId" - )}` - ]; - - const runModule = id => { - return `__webpack_exec__(${JSON.stringify(id)})`; - }; - const outputCombination = (chunks, moduleIds, final) => { - if (chunks.size === 0) { - runtime.push( - `${final ? EXPORT_PREFIX : ""}(${moduleIds.map(runModule).join(", ")});` - ); - } else { - const fn = runtimeTemplate.returningFunction( - moduleIds.map(runModule).join(", ") - ); - runtime.push( - `${final && !passive ? EXPORT_PREFIX : ""}${ - passive - ? RuntimeGlobals.onChunksLoaded - : RuntimeGlobals.startupEntrypoint - }(0, ${JSON.stringify(Array.from(chunks, c => c.id))}, ${fn});` - ); - if (final && passive) { - runtime.push(`${EXPORT_PREFIX}${RuntimeGlobals.onChunksLoaded}();`); - } - } - }; - - let currentChunks = undefined; - let currentModuleIds = undefined; - - for (const [module, entrypoint] of entries) { - const runtimeChunk = entrypoint.getRuntimeChunk(); - const moduleId = chunkGraph.getModuleId(module); - const chunks = getAllChunks(entrypoint, chunk, runtimeChunk); - if ( - currentChunks && - currentChunks.size === chunks.size && - isSubset(currentChunks, chunks) - ) { - currentModuleIds.push(moduleId); - } else { - if (currentChunks) { - outputCombination(currentChunks, currentModuleIds); - } - currentChunks = chunks; - currentModuleIds = [moduleId]; - } - } - - // output current modules with export prefix - if (currentChunks) { - outputCombination(currentChunks, currentModuleIds, true); +class EnableChunkLoadingPlugin { + /** + * @param {ChunkLoadingType} type library type that should be available + */ + constructor(type) { + this.type = type; } - runtime.push(""); - return Template.asString(runtime); -}; -/** - * @param {Hash} hash the hash to update - * @param {ChunkGraph} chunkGraph chunkGraph - * @param {import("../ChunkGraph").EntryModuleWithChunkGroup[]} entries entries - * @param {Chunk} chunk chunk - * @returns {void} - */ -exports.updateHashForEntryStartup = (hash, chunkGraph, entries, chunk) => { - for (const [module, entrypoint] of entries) { - const runtimeChunk = entrypoint.getRuntimeChunk(); - const moduleId = chunkGraph.getModuleId(module); - hash.update(`${moduleId}`); - for (const c of getAllChunks(entrypoint, chunk, runtimeChunk)) - hash.update(`${c.id}`); + /** + * @param {Compiler} compiler the compiler instance + * @param {ChunkLoadingType} type type of library + * @returns {void} + */ + static setEnabled(compiler, type) { + getEnabledTypes(compiler).add(type); } -}; -/** - * @param {Chunk} chunk the chunk - * @param {ChunkGraph} chunkGraph the chunk graph - * @returns {Set} initially fulfilled chunk ids - */ -exports.getInitialChunkIds = (chunk, chunkGraph) => { - const initialChunkIds = new Set(chunk.ids); - for (const c of chunk.getAllInitialChunks()) { - if (c === chunk || chunkHasJs(c, chunkGraph)) continue; - for (const id of c.ids) initialChunkIds.add(id); + /** + * @param {Compiler} compiler the compiler instance + * @param {ChunkLoadingType} type type of library + * @returns {void} + */ + static checkEnabled(compiler, type) { + if (!getEnabledTypes(compiler).has(type)) { + throw new Error( + `Chunk loading type "${type}" is not enabled. ` + + "EnableChunkLoadingPlugin need to be used to enable this type of chunk loading. " + + 'This usually happens through the "output.enabledChunkLoadingTypes" option. ' + + 'If you are using a function as entry which sets "chunkLoading", you need to add all potential chunk loading types to "output.enabledChunkLoadingTypes". ' + + "These types are enabled: " + + Array.from(getEnabledTypes(compiler)).join(", ") + ); + } } - return initialChunkIds; -}; - - -/***/ }), - -/***/ 97637: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ - + /** + * Apply the plugin + * @param {Compiler} compiler the compiler instance + * @returns {void} + */ + apply(compiler) { + const { type } = this; -const { register } = __webpack_require__(99551); + // Only enable once + const enabled = getEnabledTypes(compiler); + if (enabled.has(type)) return; + enabled.add(type); -class JsonData { - constructor(data) { - this._buffer = undefined; - this._data = undefined; - if (Buffer.isBuffer(data)) { - this._buffer = data; + if (typeof type === "string") { + switch (type) { + case "jsonp": { + const JsonpChunkLoadingPlugin = __webpack_require__(9253); + new JsonpChunkLoadingPlugin().apply(compiler); + break; + } + case "import-scripts": { + const ImportScriptsChunkLoadingPlugin = __webpack_require__(56354); + new ImportScriptsChunkLoadingPlugin().apply(compiler); + break; + } + case "require": { + //@ts-expect-error https://github.com/microsoft/TypeScript/issues/41697 + const CommonJsChunkLoadingPlugin = __webpack_require__(32610); + new CommonJsChunkLoadingPlugin({ + asyncChunkLoading: false + }).apply(compiler); + break; + } + case "async-node": { + //@ts-expect-error https://github.com/microsoft/TypeScript/issues/41697 + const CommonJsChunkLoadingPlugin = __webpack_require__(32610); + new CommonJsChunkLoadingPlugin({ + asyncChunkLoading: true + }).apply(compiler); + break; + } + case "import": { + const ModuleChunkLoadingPlugin = __webpack_require__(94970); + new ModuleChunkLoadingPlugin().apply(compiler); + break; + } + case "universal": + // TODO implement universal chunk loading + throw new Error("Universal Chunk Loading is not implemented yet"); + default: + throw new Error(`Unsupported chunk loading type ${type}. +Plugins which provide custom chunk loading types must call EnableChunkLoadingPlugin.setEnabled(compiler, type) to disable this error.`); + } } else { - this._data = data; - } - } - - get() { - if (this._data === undefined && this._buffer !== undefined) { - this._data = JSON.parse(this._buffer.toString()); + // TODO support plugin instances here + // apply them to the compiler } - return this._data; } } -register(JsonData, "webpack/lib/json/JsonData", null, { - serialize(obj, { write }) { - if (obj._buffer === undefined && obj._data !== undefined) { - obj._buffer = Buffer.from(JSON.stringify(obj._data)); - } - write(obj._buffer); - }, - deserialize({ read }) { - return new JsonData(read()); - } -}); - -module.exports = JsonData; +module.exports = EnableChunkLoadingPlugin; /***/ }), -/***/ 38140: +/***/ 41813: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; @@ -96716,103 +92876,35 @@ module.exports = JsonData; -const { RawSource } = __webpack_require__(96192); -const ConcatenationScope = __webpack_require__(14067); -const { UsageState } = __webpack_require__(4295); +const util = __webpack_require__(31669); +const { RawSource, ReplaceSource } = __webpack_require__(96192); const Generator = __webpack_require__(1826); -const RuntimeGlobals = __webpack_require__(49404); +const InitFragment = __webpack_require__(51739); +const HarmonyCompatibilityDependency = __webpack_require__(56164); /** @typedef {import("webpack-sources").Source} Source */ -/** @typedef {import("../ExportsInfo")} ExportsInfo */ +/** @typedef {import("../DependenciesBlock")} DependenciesBlock */ +/** @typedef {import("../Dependency")} Dependency */ +/** @typedef {import("../DependencyTemplates")} DependencyTemplates */ /** @typedef {import("../Generator").GenerateContext} GenerateContext */ +/** @typedef {import("../Module")} Module */ /** @typedef {import("../Module").ConcatenationBailoutReasonContext} ConcatenationBailoutReasonContext */ /** @typedef {import("../NormalModule")} NormalModule */ -/** @typedef {import("../util/runtime").RuntimeSpec} RuntimeSpec */ - -const stringifySafe = data => { - const stringified = JSON.stringify(data); - if (!stringified) { - return undefined; // Invalid JSON - } - - return stringified.replace(/\u2028|\u2029/g, str => - str === "\u2029" ? "\\u2029" : "\\u2028" - ); // invalid in JavaScript but valid JSON -}; - -/** - * @param {Object} data data (always an object or array) - * @param {ExportsInfo} exportsInfo exports info - * @param {RuntimeSpec} runtime the runtime - * @returns {Object} reduced data - */ -const createObjectForExportsInfo = (data, exportsInfo, runtime) => { - if (exportsInfo.otherExportsInfo.getUsed(runtime) !== UsageState.Unused) - return data; - const isArray = Array.isArray(data); - const reducedData = isArray ? [] : {}; - for (const key of Object.keys(data)) { - const exportInfo = exportsInfo.getReadOnlyExportInfo(key); - const used = exportInfo.getUsed(runtime); - if (used === UsageState.Unused) continue; +/** @typedef {import("../RuntimeTemplate")} RuntimeTemplate */ - let value; - if (used === UsageState.OnlyPropertiesUsed && exportInfo.exportsInfo) { - value = createObjectForExportsInfo( - data[key], - exportInfo.exportsInfo, - runtime - ); - } else { - value = data[key]; - } - const name = exportInfo.getUsedName(key, runtime); - reducedData[name] = value; - } - if (isArray) { - let arrayLengthWhenUsed = - exportsInfo.getReadOnlyExportInfo("length").getUsed(runtime) !== - UsageState.Unused - ? data.length - : undefined; +// TODO: clean up this file +// replace with newer constructs - let sizeObjectMinusArray = 0; - for (let i = 0; i < reducedData.length; i++) { - if (reducedData[i] === undefined) { - sizeObjectMinusArray -= 2; - } else { - sizeObjectMinusArray += `${i}`.length + 3; - } - } - if (arrayLengthWhenUsed !== undefined) { - sizeObjectMinusArray += - `${arrayLengthWhenUsed}`.length + - 8 - - (arrayLengthWhenUsed - reducedData.length) * 2; - } - if (sizeObjectMinusArray < 0) - return Object.assign( - arrayLengthWhenUsed === undefined - ? {} - : { length: arrayLengthWhenUsed }, - reducedData - ); - const generatedLength = - arrayLengthWhenUsed !== undefined - ? Math.max(arrayLengthWhenUsed, reducedData.length) - : reducedData.length; - for (let i = 0; i < generatedLength; i++) { - if (reducedData[i] === undefined) { - reducedData[i] = 0; - } - } - } - return reducedData; -}; +const deprecatedGetInitFragments = util.deprecate( + (template, dependency, templateContext) => + template.getInitFragments(dependency, templateContext), + "DependencyTemplate.getInitFragment is deprecated (use apply(dep, source, { initFragments }) instead)", + "DEP_WEBPACK_JAVASCRIPT_GENERATOR_GET_INIT_FRAGMENTS" +); const TYPES = new Set(["javascript"]); -class JsonGenerator extends Generator { +class JavascriptGenerator extends Generator { /** * @param {NormalModule} module fresh module * @returns {Set} available types (do not mutate) @@ -96827,12 +92919,11 @@ class JsonGenerator extends Generator { * @returns {number} estimate size of the module */ getSize(module, type) { - let data = - module.buildInfo && - module.buildInfo.jsonData && - module.buildInfo.jsonData.get(); - if (!data) return 0; - return stringifySafe(data).length + 10; + const originalSource = module.originalSource(); + if (!originalSource) { + return 39; + } + return originalSource.size(); } /** @@ -96841,193 +92932,172 @@ class JsonGenerator extends Generator { * @returns {string | undefined} reason why this module can't be concatenated, undefined when it can be concatenated */ getConcatenationBailoutReason(module, context) { - return undefined; - } - - /** - * @param {NormalModule} module module for which the code should be generated - * @param {GenerateContext} generateContext context for generate - * @returns {Source} generated code - */ - generate( - module, - { - moduleGraph, - runtimeTemplate, - runtimeRequirements, - runtime, - concatenationScope - } - ) { - const data = - module.buildInfo && - module.buildInfo.jsonData && - module.buildInfo.jsonData.get(); - if (data === undefined) { - return new RawSource( - runtimeTemplate.missingModuleStatement({ - request: module.rawRequest - }) - ); - } - const exportsInfo = moduleGraph.getExportsInfo(module); - let finalJson = - typeof data === "object" && - data && - exportsInfo.otherExportsInfo.getUsed(runtime) === UsageState.Unused - ? createObjectForExportsInfo(data, exportsInfo, runtime) - : data; - // Use JSON because JSON.parse() is much faster than JavaScript evaluation - const jsonStr = stringifySafe(finalJson); - const jsonExpr = - jsonStr.length > 20 && typeof finalJson === "object" - ? `JSON.parse('${jsonStr.replace(/[\\']/g, "\\$&")}')` - : jsonStr; - let content; - if (concatenationScope) { - content = `${runtimeTemplate.supportsConst() ? "const" : "var"} ${ - ConcatenationScope.NAMESPACE_OBJECT_EXPORT - } = ${jsonExpr};`; - concatenationScope.registerNamespaceExport( - ConcatenationScope.NAMESPACE_OBJECT_EXPORT - ); - } else { - runtimeRequirements.add(RuntimeGlobals.module); - content = `${module.moduleArgument}.exports = ${jsonExpr};`; - } - return new RawSource(content); - } -} - -module.exports = JsonGenerator; - - -/***/ }), - -/***/ 8841: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ - - - -const createSchemaValidation = __webpack_require__(77695); -const JsonGenerator = __webpack_require__(38140); -const JsonParser = __webpack_require__(27679); - -/** @typedef {import("../Compiler")} Compiler */ - -const validate = createSchemaValidation( - __webpack_require__(95306), - () => __webpack_require__(15685), - { - name: "Json Modules Plugin", - baseDataPath: "parser" - } -); - -class JsonModulesPlugin { - /** - * Apply the plugin - * @param {Compiler} compiler the compiler instance - * @returns {void} - */ - apply(compiler) { - compiler.hooks.compilation.tap( - "JsonModulesPlugin", - (compilation, { normalModuleFactory }) => { - normalModuleFactory.hooks.createParser - .for("json") - .tap("JsonModulesPlugin", parserOptions => { - validate(parserOptions); - - return new JsonParser(parserOptions); - }); - normalModuleFactory.hooks.createGenerator - .for("json") - .tap("JsonModulesPlugin", () => { - return new JsonGenerator(); - }); - } - ); - } -} - -module.exports = JsonModulesPlugin; + // Only harmony modules are valid for optimization + if ( + !module.buildMeta || + module.buildMeta.exportsType !== "namespace" || + module.presentationalDependencies === undefined || + !module.presentationalDependencies.some( + d => d instanceof HarmonyCompatibilityDependency + ) + ) { + return "Module is not an ECMAScript module"; + } + // Some expressions are not compatible with module concatenation + // because they may produce unexpected results. The plugin bails out + // if some were detected upfront. + if (module.buildInfo && module.buildInfo.moduleConcatenationBailout) { + return `Module uses ${module.buildInfo.moduleConcatenationBailout}`; + } + } -/***/ }), + /** + * @param {NormalModule} module module for which the code should be generated + * @param {GenerateContext} generateContext context for generate + * @returns {Source} generated code + */ + generate(module, generateContext) { + const originalSource = module.originalSource(); + if (!originalSource) { + return new RawSource("throw new Error('No source available');"); + } -/***/ 27679: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + const source = new ReplaceSource(originalSource); + const initFragments = []; -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ + this.sourceModule(module, initFragments, source, generateContext); + return InitFragment.addToSource(source, initFragments, generateContext); + } + /** + * @param {Module} module the module to generate + * @param {InitFragment[]} initFragments mutable list of init fragments + * @param {ReplaceSource} source the current replace source which can be modified + * @param {GenerateContext} generateContext the generateContext + * @returns {void} + */ + sourceModule(module, initFragments, source, generateContext) { + for (const dependency of module.dependencies) { + this.sourceDependency( + module, + dependency, + initFragments, + source, + generateContext + ); + } -const parseJson = __webpack_require__(48335); -const Parser = __webpack_require__(68214); -const JsonExportsDependency = __webpack_require__(36986); -const JsonData = __webpack_require__(97637); + if (module.presentationalDependencies !== undefined) { + for (const dependency of module.presentationalDependencies) { + this.sourceDependency( + module, + dependency, + initFragments, + source, + generateContext + ); + } + } -/** @typedef {import("../../declarations/plugins/JsonModulesPluginParser").JsonModulesPluginParserOptions} JsonModulesPluginParserOptions */ -/** @typedef {import("../Parser").ParserState} ParserState */ -/** @typedef {import("../Parser").PreparsedAst} PreparsedAst */ + for (const childBlock of module.blocks) { + this.sourceBlock( + module, + childBlock, + initFragments, + source, + generateContext + ); + } + } -class JsonParser extends Parser { /** - * @param {JsonModulesPluginParserOptions} options parser options + * @param {Module} module the module to generate + * @param {DependenciesBlock} block the dependencies block which will be processed + * @param {InitFragment[]} initFragments mutable list of init fragments + * @param {ReplaceSource} source the current replace source which can be modified + * @param {GenerateContext} generateContext the generateContext + * @returns {void} */ - constructor(options) { - super(); - this.options = options || {}; + sourceBlock(module, block, initFragments, source, generateContext) { + for (const dependency of block.dependencies) { + this.sourceDependency( + module, + dependency, + initFragments, + source, + generateContext + ); + } + + for (const childBlock of block.blocks) { + this.sourceBlock( + module, + childBlock, + initFragments, + source, + generateContext + ); + } } /** - * @param {string | Buffer | PreparsedAst} source the source to parse - * @param {ParserState} state the parser state - * @returns {ParserState} the parser state + * @param {Module} module the current module + * @param {Dependency} dependency the dependency to generate + * @param {InitFragment[]} initFragments mutable list of init fragments + * @param {ReplaceSource} source the current replace source which can be modified + * @param {GenerateContext} generateContext the render context + * @returns {void} */ - parse(source, state) { - if (Buffer.isBuffer(source)) { - source = source.toString("utf-8"); + sourceDependency(module, dependency, initFragments, source, generateContext) { + const constructor = /** @type {new (...args: any[]) => Dependency} */ ( + dependency.constructor + ); + const template = generateContext.dependencyTemplates.get(constructor); + if (!template) { + throw new Error( + "No template for dependency: " + dependency.constructor.name + ); } - /** @type {JsonModulesPluginParserOptions["parse"]} */ - const parseFn = - typeof this.options.parse === "function" ? this.options.parse : parseJson; + const templateContext = { + runtimeTemplate: generateContext.runtimeTemplate, + dependencyTemplates: generateContext.dependencyTemplates, + moduleGraph: generateContext.moduleGraph, + chunkGraph: generateContext.chunkGraph, + module, + runtime: generateContext.runtime, + runtimeRequirements: generateContext.runtimeRequirements, + concatenationScope: generateContext.concatenationScope, + initFragments + }; - const data = - typeof source === "object" - ? source - : parseFn(source[0] === "\ufeff" ? source.slice(1) : source); + template.apply(dependency, source, templateContext); - state.module.buildInfo.jsonData = new JsonData(data); - state.module.buildInfo.strict = true; - state.module.buildMeta.exportsType = "default"; - state.module.buildMeta.defaultObject = - typeof data === "object" ? "redirect-warn" : false; - state.module.addDependency( - new JsonExportsDependency(JsonExportsDependency.getExportsFromData(data)) - ); - return state; + // TODO remove in webpack 6 + if ("getInitFragments" in template) { + const fragments = deprecatedGetInitFragments( + template, + dependency, + templateContext + ); + + if (fragments) { + for (const fragment of fragments) { + initFragments.push(fragment); + } + } + } } } -module.exports = JsonParser; +module.exports = JavascriptGenerator; /***/ }), -/***/ 94051: +/***/ 76767: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; @@ -97038,46 +93108,186 @@ module.exports = JsonParser; +const { SyncWaterfallHook, SyncHook, SyncBailHook } = __webpack_require__(34718); +const vm = __webpack_require__(92184); +const { + ConcatSource, + OriginalSource, + PrefixSource, + RawSource, + CachedSource +} = __webpack_require__(96192); +const Compilation = __webpack_require__(59622); +const { tryRunOrWebpackError } = __webpack_require__(89935); +const HotUpdateChunk = __webpack_require__(39222); +const InitFragment = __webpack_require__(51739); const RuntimeGlobals = __webpack_require__(49404); -const JavascriptModulesPlugin = __webpack_require__(76767); +const Template = __webpack_require__(92066); +const { last, someInIterable } = __webpack_require__(31065); +const StringXor = __webpack_require__(23877); +const { compareModulesByIdentifier } = __webpack_require__(26296); +const createHash = __webpack_require__(24123); +const { intersectRuntime } = __webpack_require__(19655); +const JavascriptGenerator = __webpack_require__(41813); +const JavascriptParser = __webpack_require__(42060); /** @typedef {import("webpack-sources").Source} Source */ -/** @typedef {import("../../declarations/WebpackOptions").LibraryOptions} LibraryOptions */ -/** @typedef {import("../../declarations/WebpackOptions").LibraryType} LibraryType */ /** @typedef {import("../Chunk")} Chunk */ /** @typedef {import("../ChunkGraph")} ChunkGraph */ -/** @typedef {import("../Compilation")} Compilation */ +/** @typedef {import("../CodeGenerationResults")} CodeGenerationResults */ /** @typedef {import("../Compilation").ChunkHashContext} ChunkHashContext */ /** @typedef {import("../Compiler")} Compiler */ +/** @typedef {import("../DependencyTemplates")} DependencyTemplates */ /** @typedef {import("../Module")} Module */ -/** @typedef {import("../javascript/JavascriptModulesPlugin").RenderContext} RenderContext */ -/** @typedef {import("../javascript/JavascriptModulesPlugin").StartupRenderContext} StartupRenderContext */ +/** @typedef {import("../ModuleGraph")} ModuleGraph */ +/** @typedef {import("../RuntimeTemplate")} RuntimeTemplate */ /** @typedef {import("../util/Hash")} Hash */ -const COMMON_LIBRARY_NAME_MESSAGE = - "Common configuration options that specific library names are 'output.library[.name]', 'entry.xyz.library[.name]', 'ModuleFederationPlugin.name' and 'ModuleFederationPlugin.library[.name]'."; +/** + * @param {Chunk} chunk a chunk + * @param {ChunkGraph} chunkGraph the chunk graph + * @returns {boolean} true, when a JS file is needed for this chunk + */ +const chunkHasJs = (chunk, chunkGraph) => { + if (chunkGraph.getNumberOfEntryModules(chunk) > 0) return true; + + return chunkGraph.getChunkModulesIterableBySourceType(chunk, "javascript") + ? true + : false; +}; + +const printGeneratedCodeForStack = (module, code) => { + const lines = code.split("\n"); + const n = `${lines.length}`.length; + return `\n\nGenerated code for ${module.identifier()}\n${lines + .map((line, i, lines) => { + const iStr = `${i + 1}`; + return `${" ".repeat(n - iStr.length)}${iStr} | ${line}`; + }) + .join("\n")}`; +}; /** - * @template T - * @typedef {Object} LibraryContext - * @property {Compilation} compilation - * @property {ChunkGraph} chunkGraph - * @property {T} options + * @typedef {Object} RenderContext + * @property {Chunk} chunk the chunk + * @property {DependencyTemplates} dependencyTemplates the dependency templates + * @property {RuntimeTemplate} runtimeTemplate the runtime template + * @property {ModuleGraph} moduleGraph the module graph + * @property {ChunkGraph} chunkGraph the chunk graph + * @property {CodeGenerationResults} codeGenerationResults results of code generation + * @property {boolean} strictMode rendering in strict context */ /** - * @template T + * @typedef {Object} MainRenderContext + * @property {Chunk} chunk the chunk + * @property {DependencyTemplates} dependencyTemplates the dependency templates + * @property {RuntimeTemplate} runtimeTemplate the runtime template + * @property {ModuleGraph} moduleGraph the module graph + * @property {ChunkGraph} chunkGraph the chunk graph + * @property {CodeGenerationResults} codeGenerationResults results of code generation + * @property {string} hash hash to be used for render call + * @property {boolean} strictMode rendering in strict context */ -class AbstractLibraryPlugin { + +/** + * @typedef {Object} ChunkRenderContext + * @property {Chunk} chunk the chunk + * @property {DependencyTemplates} dependencyTemplates the dependency templates + * @property {RuntimeTemplate} runtimeTemplate the runtime template + * @property {ModuleGraph} moduleGraph the module graph + * @property {ChunkGraph} chunkGraph the chunk graph + * @property {CodeGenerationResults} codeGenerationResults results of code generation + * @property {InitFragment[]} chunkInitFragments init fragments for the chunk + * @property {boolean} strictMode rendering in strict context + */ + +/** + * @typedef {Object} RenderBootstrapContext + * @property {Chunk} chunk the chunk + * @property {RuntimeTemplate} runtimeTemplate the runtime template + * @property {ModuleGraph} moduleGraph the module graph + * @property {ChunkGraph} chunkGraph the chunk graph + * @property {string} hash hash to be used for render call + */ + +/** @typedef {RenderContext & { inlined: boolean }} StartupRenderContext */ + +/** + * @typedef {Object} CompilationHooks + * @property {SyncWaterfallHook<[Source, Module, ChunkRenderContext]>} renderModuleContent + * @property {SyncWaterfallHook<[Source, Module, ChunkRenderContext]>} renderModuleContainer + * @property {SyncWaterfallHook<[Source, Module, ChunkRenderContext]>} renderModulePackage + * @property {SyncWaterfallHook<[Source, RenderContext]>} renderChunk + * @property {SyncWaterfallHook<[Source, RenderContext]>} renderMain + * @property {SyncWaterfallHook<[Source, RenderContext]>} renderContent + * @property {SyncWaterfallHook<[Source, RenderContext]>} render + * @property {SyncWaterfallHook<[Source, Module, StartupRenderContext]>} renderStartup + * @property {SyncWaterfallHook<[string, RenderBootstrapContext]>} renderRequire + * @property {SyncBailHook<[Module, RenderBootstrapContext], string>} inlineInRuntimeBailout + * @property {SyncBailHook<[Module, RenderContext], string>} embedInRuntimeBailout + * @property {SyncBailHook<[RenderContext], string>} strictRuntimeBailout + * @property {SyncHook<[Chunk, Hash, ChunkHashContext]>} chunkHash + * @property {SyncBailHook<[Chunk, RenderContext], boolean>} useSourceMap + */ + +/** @type {WeakMap} */ +const compilationHooksMap = new WeakMap(); + +class JavascriptModulesPlugin { /** - * @param {Object} options options - * @param {string} options.pluginName name of the plugin - * @param {LibraryType} options.type used library type + * @param {Compilation} compilation the compilation + * @returns {CompilationHooks} the attached hooks */ - constructor({ pluginName, type }) { - this._pluginName = pluginName; - this._type = type; - this._parseCache = new WeakMap(); + static getCompilationHooks(compilation) { + if (!(compilation instanceof Compilation)) { + throw new TypeError( + "The 'compilation' argument must be an instance of Compilation" + ); + } + let hooks = compilationHooksMap.get(compilation); + if (hooks === undefined) { + hooks = { + renderModuleContent: new SyncWaterfallHook([ + "source", + "module", + "renderContext" + ]), + renderModuleContainer: new SyncWaterfallHook([ + "source", + "module", + "renderContext" + ]), + renderModulePackage: new SyncWaterfallHook([ + "source", + "module", + "renderContext" + ]), + render: new SyncWaterfallHook(["source", "renderContext"]), + renderContent: new SyncWaterfallHook(["source", "renderContext"]), + renderStartup: new SyncWaterfallHook([ + "source", + "module", + "startupRenderContext" + ]), + renderChunk: new SyncWaterfallHook(["source", "renderContext"]), + renderMain: new SyncWaterfallHook(["source", "renderContext"]), + renderRequire: new SyncWaterfallHook(["code", "renderContext"]), + inlineInRuntimeBailout: new SyncBailHook(["module", "renderContext"]), + embedInRuntimeBailout: new SyncBailHook(["module", "renderContext"]), + strictRuntimeBailout: new SyncBailHook(["renderContext"]), + chunkHash: new SyncHook(["chunk", "hash", "context"]), + useSourceMap: new SyncBailHook(["chunk", "renderContext"]) + }; + compilationHooksMap.set(compilation, hooks); + } + return hooks; + } + + constructor(options = {}) { + this.options = options; + /** @type {WeakMap} */ + this._moduleFactoryCache = new WeakMap(); } /** @@ -97086,782 +93296,1161 @@ class AbstractLibraryPlugin { * @returns {void} */ apply(compiler) { - const { _pluginName } = this; - compiler.hooks.thisCompilation.tap(_pluginName, compilation => { - compilation.hooks.finishModules.tap( - { name: _pluginName, stage: 10 }, - () => { - for (const [ - name, - { - dependencies: deps, - options: { library } + compiler.hooks.compilation.tap( + "JavascriptModulesPlugin", + (compilation, { normalModuleFactory }) => { + const hooks = JavascriptModulesPlugin.getCompilationHooks(compilation); + normalModuleFactory.hooks.createParser + .for("javascript/auto") + .tap("JavascriptModulesPlugin", options => { + return new JavascriptParser("auto"); + }); + normalModuleFactory.hooks.createParser + .for("javascript/dynamic") + .tap("JavascriptModulesPlugin", options => { + return new JavascriptParser("script"); + }); + normalModuleFactory.hooks.createParser + .for("javascript/esm") + .tap("JavascriptModulesPlugin", options => { + return new JavascriptParser("module"); + }); + normalModuleFactory.hooks.createGenerator + .for("javascript/auto") + .tap("JavascriptModulesPlugin", () => { + return new JavascriptGenerator(); + }); + normalModuleFactory.hooks.createGenerator + .for("javascript/dynamic") + .tap("JavascriptModulesPlugin", () => { + return new JavascriptGenerator(); + }); + normalModuleFactory.hooks.createGenerator + .for("javascript/esm") + .tap("JavascriptModulesPlugin", () => { + return new JavascriptGenerator(); + }); + compilation.hooks.renderManifest.tap( + "JavascriptModulesPlugin", + (result, options) => { + const { + hash, + chunk, + chunkGraph, + moduleGraph, + runtimeTemplate, + dependencyTemplates, + outputOptions, + codeGenerationResults + } = options; + + const hotUpdateChunk = + chunk instanceof HotUpdateChunk ? chunk : null; + + let render; + const filenameTemplate = + JavascriptModulesPlugin.getChunkFilenameTemplate( + chunk, + outputOptions + ); + if (hotUpdateChunk) { + render = () => + this.renderChunk( + { + chunk, + dependencyTemplates, + runtimeTemplate, + moduleGraph, + chunkGraph, + codeGenerationResults, + strictMode: runtimeTemplate.isModule() + }, + hooks + ); + } else if (chunk.hasRuntime()) { + render = () => + this.renderMain( + { + hash, + chunk, + dependencyTemplates, + runtimeTemplate, + moduleGraph, + chunkGraph, + codeGenerationResults, + strictMode: runtimeTemplate.isModule() + }, + hooks, + compilation + ); + } else { + if (!chunkHasJs(chunk, chunkGraph)) { + return result; + } + + render = () => + this.renderChunk( + { + chunk, + dependencyTemplates, + runtimeTemplate, + moduleGraph, + chunkGraph, + codeGenerationResults, + strictMode: runtimeTemplate.isModule() + }, + hooks + ); + } + + result.push({ + render, + filenameTemplate, + pathOptions: { + hash, + runtime: chunk.runtime, + chunk, + contentHashType: "javascript" + }, + info: { + javascriptModule: compilation.runtimeTemplate.isModule() + }, + identifier: hotUpdateChunk + ? `hotupdatechunk${chunk.id}` + : `chunk${chunk.id}`, + hash: chunk.contentHash.javascript + }); + + return result; + } + ); + compilation.hooks.chunkHash.tap( + "JavascriptModulesPlugin", + (chunk, hash, context) => { + hooks.chunkHash.call(chunk, hash, context); + if (chunk.hasRuntime()) { + this.updateHashWithBootstrap( + hash, + { + hash: "0000", + chunk, + chunkGraph: context.chunkGraph, + moduleGraph: context.moduleGraph, + runtimeTemplate: context.runtimeTemplate + }, + hooks + ); } - ] of compilation.entries) { - const options = this._parseOptionsCached( - library !== undefined - ? library - : compilation.outputOptions.library + } + ); + compilation.hooks.contentHash.tap("JavascriptModulesPlugin", chunk => { + const { + chunkGraph, + moduleGraph, + runtimeTemplate, + outputOptions: { + hashSalt, + hashDigest, + hashDigestLength, + hashFunction + } + } = compilation; + const hash = createHash(hashFunction); + if (hashSalt) hash.update(hashSalt); + if (chunk.hasRuntime()) { + this.updateHashWithBootstrap( + hash, + { + hash: "0000", + chunk, + chunkGraph: compilation.chunkGraph, + moduleGraph: compilation.moduleGraph, + runtimeTemplate: compilation.runtimeTemplate + }, + hooks ); - if (options !== false) { - const dep = deps[deps.length - 1]; - if (dep) { - const module = compilation.moduleGraph.getModule(dep); - if (module) { - this.finishEntryModule(module, name, { - options, - compilation, - chunkGraph: compilation.chunkGraph - }); - } - } + } else { + hash.update(`${chunk.id} `); + hash.update(chunk.ids ? chunk.ids.join(",") : ""); + } + hooks.chunkHash.call(chunk, hash, { + chunkGraph, + moduleGraph, + runtimeTemplate + }); + const modules = chunkGraph.getChunkModulesIterableBySourceType( + chunk, + "javascript" + ); + if (modules) { + const xor = new StringXor(); + for (const m of modules) { + xor.add(chunkGraph.getModuleHash(m, chunk.runtime)); } + xor.updateHash(hash); } - } - ); - - const getOptionsForChunk = chunk => { - if (compilation.chunkGraph.getNumberOfEntryModules(chunk) === 0) - return false; - const options = chunk.getEntryOptions(); - const library = options && options.library; - return this._parseOptionsCached( - library !== undefined ? library : compilation.outputOptions.library - ); - }; - - if ( - this.render !== AbstractLibraryPlugin.prototype.render || - this.runtimeRequirements !== - AbstractLibraryPlugin.prototype.runtimeRequirements - ) { - compilation.hooks.additionalChunkRuntimeRequirements.tap( - _pluginName, + const runtimeModules = chunkGraph.getChunkModulesIterableBySourceType( + chunk, + "runtime" + ); + if (runtimeModules) { + const xor = new StringXor(); + for (const m of runtimeModules) { + xor.add(chunkGraph.getModuleHash(m, chunk.runtime)); + } + xor.updateHash(hash); + } + const digest = /** @type {string} */ (hash.digest(hashDigest)); + chunk.contentHash.javascript = digest.substr(0, hashDigestLength); + }); + compilation.hooks.additionalTreeRuntimeRequirements.tap( + "JavascriptModulesPlugin", (chunk, set, { chunkGraph }) => { - const options = getOptionsForChunk(chunk); - if (options !== false) { - this.runtimeRequirements(chunk, set, { - options, - compilation, - chunkGraph - }); + if ( + !set.has(RuntimeGlobals.startupNoDefault) && + chunkGraph.hasChunkEntryDependentChunks(chunk) + ) { + set.add(RuntimeGlobals.onChunksLoaded); + set.add(RuntimeGlobals.require); } } ); - } - - const hooks = JavascriptModulesPlugin.getCompilationHooks(compilation); - - if (this.render !== AbstractLibraryPlugin.prototype.render) { - hooks.render.tap(_pluginName, (source, renderContext) => { - const options = getOptionsForChunk(renderContext.chunk); - if (options === false) return source; - return this.render(source, renderContext, { - options, - compilation, - chunkGraph: compilation.chunkGraph - }); - }); - } + compilation.hooks.executeModule.tap( + "JavascriptModulesPlugin", + (options, context) => { + const source = + options.codeGenerationResult.sources.get("javascript"); + if (source === undefined) return; + const { module, moduleObject } = options; + const code = source.source(); - if ( - this.embedInRuntimeBailout !== - AbstractLibraryPlugin.prototype.embedInRuntimeBailout - ) { - hooks.embedInRuntimeBailout.tap( - _pluginName, - (module, renderContext) => { - const options = getOptionsForChunk(renderContext.chunk); - if (options === false) return; - return this.embedInRuntimeBailout(module, renderContext, { - options, - compilation, - chunkGraph: compilation.chunkGraph - }); + const fn = vm.runInThisContext( + `(function(${module.moduleArgument}, ${module.exportsArgument}, __webpack_require__) {\n${code}\n/**/})`, + { + filename: module.identifier(), + lineOffset: -1 + } + ); + try { + fn.call( + moduleObject.exports, + moduleObject, + moduleObject.exports, + context.__webpack_require__ + ); + } catch (e) { + e.stack += printGeneratedCodeForStack(options.module, code); + throw e; + } } ); - } - - if ( - this.strictRuntimeBailout !== - AbstractLibraryPlugin.prototype.strictRuntimeBailout - ) { - hooks.strictRuntimeBailout.tap(_pluginName, renderContext => { - const options = getOptionsForChunk(renderContext.chunk); - if (options === false) return; - return this.strictRuntimeBailout(renderContext, { - options, - compilation, - chunkGraph: compilation.chunkGraph - }); - }); - } + compilation.hooks.executeModule.tap( + "JavascriptModulesPlugin", + (options, context) => { + const source = options.codeGenerationResult.sources.get("runtime"); + if (source === undefined) return; + let code = source.source(); + if (typeof code !== "string") code = code.toString(); - if ( - this.renderStartup !== AbstractLibraryPlugin.prototype.renderStartup - ) { - hooks.renderStartup.tap( - _pluginName, - (source, module, renderContext) => { - const options = getOptionsForChunk(renderContext.chunk); - if (options === false) return source; - return this.renderStartup(source, module, renderContext, { - options, - compilation, - chunkGraph: compilation.chunkGraph - }); + const fn = vm.runInThisContext( + `(function(__webpack_require__) {\n${code}\n/**/})`, + { + filename: options.module.identifier(), + lineOffset: -1 + } + ); + try { + fn.call(null, context.__webpack_require__); + } catch (e) { + e.stack += printGeneratedCodeForStack(options.module, code); + throw e; + } } ); } - - hooks.chunkHash.tap(_pluginName, (chunk, hash, context) => { - const options = getOptionsForChunk(chunk); - if (options === false) return; - this.chunkHash(chunk, hash, context, { - options, - compilation, - chunkGraph: compilation.chunkGraph - }); - }); - }); - } - - /** - * @param {LibraryOptions=} library normalized library option - * @returns {T | false} preprocess as needed by overriding - */ - _parseOptionsCached(library) { - if (!library) return false; - if (library.type !== this._type) return false; - const cacheEntry = this._parseCache.get(library); - if (cacheEntry !== undefined) return cacheEntry; - const result = this.parseOptions(library); - this._parseCache.set(library, result); - return result; - } - - /* istanbul ignore next */ - /** - * @abstract - * @param {LibraryOptions} library normalized library option - * @returns {T | false} preprocess as needed by overriding - */ - parseOptions(library) { - const AbstractMethodError = __webpack_require__(570); - throw new AbstractMethodError(); - } - - /** - * @param {Module} module the exporting entry module - * @param {string} entryName the name of the entrypoint - * @param {LibraryContext} libraryContext context - * @returns {void} - */ - finishEntryModule(module, entryName, libraryContext) {} - - /** - * @param {Module} module the exporting entry module - * @param {RenderContext} renderContext render context - * @param {LibraryContext} libraryContext context - * @returns {string | undefined} bailout reason - */ - embedInRuntimeBailout(module, renderContext, libraryContext) { - return undefined; - } - - /** - * @param {RenderContext} renderContext render context - * @param {LibraryContext} libraryContext context - * @returns {string | undefined} bailout reason - */ - strictRuntimeBailout(renderContext, libraryContext) { - return undefined; - } - - /** - * @param {Chunk} chunk the chunk - * @param {Set} set runtime requirements - * @param {LibraryContext} libraryContext context - * @returns {void} - */ - runtimeRequirements(chunk, set, libraryContext) { - if (this.render !== AbstractLibraryPlugin.prototype.render) - set.add(RuntimeGlobals.returnExportsFromRuntime); - } - - /** - * @param {Source} source source - * @param {RenderContext} renderContext render context - * @param {LibraryContext} libraryContext context - * @returns {Source} source with library export - */ - render(source, renderContext, libraryContext) { - return source; - } - - /** - * @param {Source} source source - * @param {Module} module module - * @param {StartupRenderContext} renderContext render context - * @param {LibraryContext} libraryContext context - * @returns {Source} source with library export - */ - renderStartup(source, module, renderContext, libraryContext) { - return source; - } - - /** - * @param {Chunk} chunk the chunk - * @param {Hash} hash hash - * @param {ChunkHashContext} chunkHashContext chunk hash context - * @param {LibraryContext} libraryContext context - * @returns {void} - */ - chunkHash(chunk, hash, chunkHashContext, libraryContext) { - const options = this._parseOptionsCached( - libraryContext.compilation.outputOptions.library ); - hash.update(this._pluginName); - hash.update(JSON.stringify(options)); } -} - -AbstractLibraryPlugin.COMMON_LIBRARY_NAME_MESSAGE = COMMON_LIBRARY_NAME_MESSAGE; -module.exports = AbstractLibraryPlugin; - - -/***/ }), - -/***/ 4494: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ - - - -const { ConcatSource } = __webpack_require__(96192); -const ExternalModule = __webpack_require__(89805); -const Template = __webpack_require__(92066); -const AbstractLibraryPlugin = __webpack_require__(94051); - -/** @typedef {import("webpack-sources").Source} Source */ -/** @typedef {import("../../declarations/WebpackOptions").LibraryOptions} LibraryOptions */ -/** @typedef {import("../../declarations/WebpackOptions").LibraryType} LibraryType */ -/** @typedef {import("../Chunk")} Chunk */ -/** @typedef {import("../Compilation").ChunkHashContext} ChunkHashContext */ -/** @typedef {import("../Compiler")} Compiler */ -/** @typedef {import("../javascript/JavascriptModulesPlugin").RenderContext} RenderContext */ -/** @typedef {import("../util/Hash")} Hash */ -/** @template T @typedef {import("./AbstractLibraryPlugin").LibraryContext} LibraryContext */ - -/** - * @typedef {Object} AmdLibraryPluginOptions - * @property {LibraryType} type - * @property {boolean=} requireAsWrapper - */ - -/** - * @typedef {Object} AmdLibraryPluginParsed - * @property {string} name - */ -/** - * @typedef {AmdLibraryPluginParsed} T - * @extends {AbstractLibraryPlugin} - */ -class AmdLibraryPlugin extends AbstractLibraryPlugin { - /** - * @param {AmdLibraryPluginOptions} options the plugin options - */ - constructor(options) { - super({ - pluginName: "AmdLibraryPlugin", - type: options.type - }); - this.requireAsWrapper = options.requireAsWrapper; + static getChunkFilenameTemplate(chunk, outputOptions) { + if (chunk.filenameTemplate) { + return chunk.filenameTemplate; + } else if (chunk instanceof HotUpdateChunk) { + return outputOptions.hotUpdateChunkFilename; + } else if (chunk.canBeInitial()) { + return outputOptions.filename; + } else { + return outputOptions.chunkFilename; + } } /** - * @param {LibraryOptions} library normalized library option - * @returns {T | false} preprocess as needed by overriding + * @param {Module} module the rendered module + * @param {ChunkRenderContext} renderContext options object + * @param {CompilationHooks} hooks hooks + * @param {boolean} factory true: renders as factory method, false: pure module content + * @returns {Source} the newly generated source from rendering */ - parseOptions(library) { - const { name } = library; - if (this.requireAsWrapper) { - if (name) { - throw new Error( - `AMD library name must be unset. ${AbstractLibraryPlugin.COMMON_LIBRARY_NAME_MESSAGE}` - ); + renderModule(module, renderContext, hooks, factory) { + const { + chunk, + chunkGraph, + runtimeTemplate, + codeGenerationResults, + strictMode + } = renderContext; + try { + const codeGenResult = codeGenerationResults.get(module, chunk.runtime); + const moduleSource = codeGenResult.sources.get("javascript"); + if (!moduleSource) return null; + if (codeGenResult.data !== undefined) { + const chunkInitFragments = codeGenResult.data.get("chunkInitFragments"); + if (chunkInitFragments) { + for (const i of chunkInitFragments) + renderContext.chunkInitFragments.push(i); + } } - } else { - if (name && typeof name !== "string") { - throw new Error( - `AMD library name must be a simple string or unset. ${AbstractLibraryPlugin.COMMON_LIBRARY_NAME_MESSAGE}` + const moduleSourcePostContent = tryRunOrWebpackError( + () => + hooks.renderModuleContent.call(moduleSource, module, renderContext), + "JavascriptModulesPlugin.getCompilationHooks().renderModuleContent" + ); + let moduleSourcePostContainer; + if (factory) { + const runtimeRequirements = chunkGraph.getModuleRuntimeRequirements( + module, + chunk.runtime + ); + const needModule = runtimeRequirements.has(RuntimeGlobals.module); + const needExports = runtimeRequirements.has(RuntimeGlobals.exports); + const needRequire = + runtimeRequirements.has(RuntimeGlobals.require) || + runtimeRequirements.has(RuntimeGlobals.requireScope); + const needThisAsExports = runtimeRequirements.has( + RuntimeGlobals.thisAsExports + ); + const needStrict = module.buildInfo.strict && !strictMode; + const cacheEntry = this._moduleFactoryCache.get( + moduleSourcePostContent + ); + let source; + if ( + cacheEntry && + cacheEntry.needModule === needModule && + cacheEntry.needExports === needExports && + cacheEntry.needRequire === needRequire && + cacheEntry.needThisAsExports === needThisAsExports && + cacheEntry.needStrict === needStrict + ) { + source = cacheEntry.source; + } else { + const factorySource = new ConcatSource(); + const args = []; + if (needExports || needRequire || needModule) + args.push( + needModule + ? module.moduleArgument + : "__unused_webpack_" + module.moduleArgument + ); + if (needExports || needRequire) + args.push( + needExports + ? module.exportsArgument + : "__unused_webpack_" + module.exportsArgument + ); + if (needRequire) args.push("__webpack_require__"); + if (!needThisAsExports && runtimeTemplate.supportsArrowFunction()) { + factorySource.add("/***/ ((" + args.join(", ") + ") => {\n\n"); + } else { + factorySource.add("/***/ (function(" + args.join(", ") + ") {\n\n"); + } + if (needStrict) { + factorySource.add('"use strict";\n'); + } + factorySource.add(moduleSourcePostContent); + factorySource.add("\n\n/***/ })"); + source = new CachedSource(factorySource); + this._moduleFactoryCache.set(moduleSourcePostContent, { + source, + needModule, + needExports, + needRequire, + needThisAsExports, + needStrict + }); + } + moduleSourcePostContainer = tryRunOrWebpackError( + () => hooks.renderModuleContainer.call(source, module, renderContext), + "JavascriptModulesPlugin.getCompilationHooks().renderModuleContainer" ); + } else { + moduleSourcePostContainer = moduleSourcePostContent; } + return tryRunOrWebpackError( + () => + hooks.renderModulePackage.call( + moduleSourcePostContainer, + module, + renderContext + ), + "JavascriptModulesPlugin.getCompilationHooks().renderModulePackage" + ); + } catch (e) { + e.module = module; + throw e; } - return { - name: /** @type {string=} */ (name) - }; } /** - * @param {Source} source source - * @param {RenderContext} renderContext render context - * @param {LibraryContext} libraryContext context - * @returns {Source} source with library export + * @param {RenderContext} renderContext the render context + * @param {CompilationHooks} hooks hooks + * @returns {Source} the rendered source */ - render( - source, - { chunkGraph, chunk, runtimeTemplate }, - { options, compilation } - ) { - const modern = runtimeTemplate.supportsArrowFunction(); - const modules = chunkGraph - .getChunkModules(chunk) - .filter(m => m instanceof ExternalModule); - const externals = /** @type {ExternalModule[]} */ (modules); - const externalsDepsArray = JSON.stringify( - externals.map(m => - typeof m.request === "object" && !Array.isArray(m.request) - ? m.request.amd - : m.request - ) + renderChunk(renderContext, hooks) { + const { chunk, chunkGraph } = renderContext; + const modules = chunkGraph.getOrderedChunkModulesIterableBySourceType( + chunk, + "javascript", + compareModulesByIdentifier ); - const externalsArguments = externals - .map( - m => - `__WEBPACK_EXTERNAL_MODULE_${Template.toIdentifier( - `${chunkGraph.getModuleId(m)}` - )}__` - ) - .join(", "); - - const iife = runtimeTemplate.isIIFE(); - const fnStart = - (modern - ? `(${externalsArguments}) => {` - : `function(${externalsArguments}) {`) + - (iife || !chunk.hasRuntime() ? " return " : "\n"); - const fnEnd = iife ? ";\n}" : "\n}"; - - if (this.requireAsWrapper) { - return new ConcatSource( - `require(${externalsDepsArray}, ${fnStart}`, - source, - `${fnEnd});` - ); - } else if (options.name) { - const name = compilation.getPath(options.name, { - chunk - }); - - return new ConcatSource( - `define(${JSON.stringify(name)}, ${externalsDepsArray}, ${fnStart}`, - source, - `${fnEnd});` + const allModules = modules ? Array.from(modules) : []; + let strictHeader; + let allStrict = renderContext.strictMode; + if (!allStrict && allModules.every(m => m.buildInfo.strict)) { + const strictBailout = hooks.strictRuntimeBailout.call(renderContext); + strictHeader = strictBailout + ? `// runtime can't be in strict mode because ${strictBailout}.\n` + : '"use strict";\n'; + if (!strictBailout) allStrict = true; + } + /** @type {ChunkRenderContext} */ + const chunkRenderContext = { + ...renderContext, + chunkInitFragments: [], + strictMode: allStrict + }; + const moduleSources = + Template.renderChunkModules(chunkRenderContext, allModules, module => + this.renderModule(module, chunkRenderContext, hooks, true) + ) || new RawSource("{}"); + let source = tryRunOrWebpackError( + () => hooks.renderChunk.call(moduleSources, chunkRenderContext), + "JavascriptModulesPlugin.getCompilationHooks().renderChunk" + ); + source = tryRunOrWebpackError( + () => hooks.renderContent.call(source, chunkRenderContext), + "JavascriptModulesPlugin.getCompilationHooks().renderContent" + ); + if (!source) { + throw new Error( + "JavascriptModulesPlugin error: JavascriptModulesPlugin.getCompilationHooks().renderContent plugins should return something" ); - } else if (externalsArguments) { - return new ConcatSource( - `define(${externalsDepsArray}, ${fnStart}`, - source, - `${fnEnd});` + } + source = InitFragment.addToSource( + source, + chunkRenderContext.chunkInitFragments, + chunkRenderContext + ); + source = tryRunOrWebpackError( + () => hooks.render.call(source, chunkRenderContext), + "JavascriptModulesPlugin.getCompilationHooks().render" + ); + if (!source) { + throw new Error( + "JavascriptModulesPlugin error: JavascriptModulesPlugin.getCompilationHooks().render plugins should return something" ); - } else { - return new ConcatSource(`define(${fnStart}`, source, `${fnEnd});`); } + chunk.rendered = true; + return strictHeader + ? new ConcatSource(strictHeader, source, ";") + : renderContext.runtimeTemplate.isModule() + ? source + : new ConcatSource(source, ";"); } /** - * @param {Chunk} chunk the chunk - * @param {Hash} hash hash - * @param {ChunkHashContext} chunkHashContext chunk hash context - * @param {LibraryContext} libraryContext context - * @returns {void} + * @param {MainRenderContext} renderContext options object + * @param {CompilationHooks} hooks hooks + * @param {Compilation} compilation the compilation + * @returns {Source} the newly generated source from rendering */ - chunkHash(chunk, hash, chunkHashContext, { options, compilation }) { - hash.update("AmdLibraryPlugin"); - if (this.requireAsWrapper) { - hash.update("requireAsWrapper"); - } else if (options.name) { - hash.update("named"); - const name = compilation.getPath(options.name, { - chunk - }); - hash.update(name); - } - } -} - -module.exports = AmdLibraryPlugin; - - -/***/ }), - -/***/ 20909: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ - - - -const { ConcatSource } = __webpack_require__(96192); -const { UsageState } = __webpack_require__(4295); -const Template = __webpack_require__(92066); -const propertyAccess = __webpack_require__(86709); -const { getEntryRuntime } = __webpack_require__(19655); -const AbstractLibraryPlugin = __webpack_require__(94051); - -/** @typedef {import("webpack-sources").Source} Source */ -/** @typedef {import("../../declarations/WebpackOptions").LibraryOptions} LibraryOptions */ -/** @typedef {import("../../declarations/WebpackOptions").LibraryType} LibraryType */ -/** @typedef {import("../Chunk")} Chunk */ -/** @typedef {import("../Compilation").ChunkHashContext} ChunkHashContext */ -/** @typedef {import("../Compiler")} Compiler */ -/** @typedef {import("../Module")} Module */ -/** @typedef {import("../javascript/JavascriptModulesPlugin").RenderContext} RenderContext */ -/** @typedef {import("../javascript/JavascriptModulesPlugin").StartupRenderContext} StartupRenderContext */ -/** @typedef {import("../util/Hash")} Hash */ -/** @template T @typedef {import("./AbstractLibraryPlugin").LibraryContext} LibraryContext */ - -const KEYWORD_REGEX = - /^(await|break|case|catch|class|const|continue|debugger|default|delete|do|else|enum|export|extends|false|finally|for|function|if|implements|import|in|instanceof|interface|let|new|null|package|private|protected|public|return|super|switch|static|this|throw|try|true|typeof|var|void|while|with|yield)$/; -const IDENTIFIER_REGEX = - /^[\p{L}\p{Nl}$_][\p{L}\p{Nl}$\p{Mn}\p{Mc}\p{Nd}\p{Pc}]*$/iu; - -/** - * Validates the library name by checking for keywords and valid characters - * @param {string} name name to be validated - * @returns {boolean} true, when valid - */ -const isNameValid = name => { - return !KEYWORD_REGEX.test(name) && IDENTIFIER_REGEX.test(name); -}; - -/** - * @param {string[]} accessor variable plus properties - * @param {number} existingLength items of accessor that are existing already - * @param {boolean=} initLast if the last property should also be initialized to an object - * @returns {string} code to access the accessor while initializing - */ -const accessWithInit = (accessor, existingLength, initLast = false) => { - // This generates for [a, b, c, d]: - // (((a = typeof a === "undefined" ? {} : a).b = a.b || {}).c = a.b.c || {}).d - const base = accessor[0]; - if (accessor.length === 1 && !initLast) return base; - let current = - existingLength > 0 - ? base - : `(${base} = typeof ${base} === "undefined" ? {} : ${base})`; + renderMain(renderContext, hooks, compilation) { + const { chunk, chunkGraph, runtimeTemplate } = renderContext; - // i is the current position in accessor that has been printed - let i = 1; + const runtimeRequirements = chunkGraph.getTreeRuntimeRequirements(chunk); + const iife = runtimeTemplate.isIIFE(); - // all properties printed so far (excluding base) - let propsSoFar; + const bootstrap = this.renderBootstrap(renderContext, hooks); + const useSourceMap = hooks.useSourceMap.call(chunk, renderContext); - // if there is existingLength, print all properties until this position as property access - if (existingLength > i) { - propsSoFar = accessor.slice(1, existingLength); - i = existingLength; - current += propertyAccess(propsSoFar); - } else { - propsSoFar = []; - } + const allModules = Array.from( + chunkGraph.getOrderedChunkModulesIterableBySourceType( + chunk, + "javascript", + compareModulesByIdentifier + ) || [] + ); - // all remaining properties (except the last one when initLast is not set) - // should be printed as initializer - const initUntil = initLast ? accessor.length : accessor.length - 1; - for (; i < initUntil; i++) { - const prop = accessor[i]; - propsSoFar.push(prop); - current = `(${current}${propertyAccess([prop])} = ${base}${propertyAccess( - propsSoFar - )} || {})`; - } + const hasEntryModules = chunkGraph.getNumberOfEntryModules(chunk) > 0; + let inlinedModules; + if (bootstrap.allowInlineStartup && hasEntryModules) { + inlinedModules = new Set(chunkGraph.getChunkEntryModulesIterable(chunk)); + } - // print the last property as property access if not yet printed - if (i < accessor.length) - current = `${current}${propertyAccess([accessor[accessor.length - 1]])}`; + let source = new ConcatSource(); + let prefix; + if (iife) { + if (runtimeTemplate.supportsArrowFunction()) { + source.add("/******/ (() => { // webpackBootstrap\n"); + } else { + source.add("/******/ (function() { // webpackBootstrap\n"); + } + prefix = "/******/ \t"; + } else { + prefix = "/******/ "; + } + let allStrict = renderContext.strictMode; + if (!allStrict && allModules.every(m => m.buildInfo.strict)) { + const strictBailout = hooks.strictRuntimeBailout.call(renderContext); + if (strictBailout) { + source.add( + prefix + + `// runtime can't be in strict mode because ${strictBailout}.\n` + ); + } else { + allStrict = true; + source.add(prefix + '"use strict";\n'); + } + } - return current; -}; + /** @type {ChunkRenderContext} */ + const chunkRenderContext = { + ...renderContext, + chunkInitFragments: [], + strictMode: allStrict + }; -/** - * @typedef {Object} AssignLibraryPluginOptions - * @property {LibraryType} type - * @property {string[] | "global"} prefix name prefix - * @property {string | false} declare declare name as variable - * @property {"error"|"copy"|"assign"} unnamed behavior for unnamed library name - * @property {"copy"|"assign"=} named behavior for named library name - */ + const chunkModules = Template.renderChunkModules( + chunkRenderContext, + inlinedModules + ? allModules.filter(m => !inlinedModules.has(m)) + : allModules, + module => this.renderModule(module, chunkRenderContext, hooks, true), + prefix + ); + if ( + chunkModules || + runtimeRequirements.has(RuntimeGlobals.moduleFactories) || + runtimeRequirements.has(RuntimeGlobals.moduleFactoriesAddOnly) || + runtimeRequirements.has(RuntimeGlobals.require) + ) { + source.add(prefix + "var __webpack_modules__ = ("); + source.add(chunkModules || "{}"); + source.add(");\n"); + source.add( + "/************************************************************************/\n" + ); + } -/** - * @typedef {Object} AssignLibraryPluginParsed - * @property {string | string[]} name - * @property {string | string[] | undefined} export - */ + if (bootstrap.header.length > 0) { + const header = Template.asString(bootstrap.header) + "\n"; + source.add( + new PrefixSource( + prefix, + useSourceMap + ? new OriginalSource(header, "webpack/bootstrap") + : new RawSource(header) + ) + ); + source.add( + "/************************************************************************/\n" + ); + } -/** - * @typedef {AssignLibraryPluginParsed} T - * @extends {AbstractLibraryPlugin} - */ -class AssignLibraryPlugin extends AbstractLibraryPlugin { - /** - * @param {AssignLibraryPluginOptions} options the plugin options - */ - constructor(options) { - super({ - pluginName: "AssignLibraryPlugin", - type: options.type - }); - this.prefix = options.prefix; - this.declare = options.declare; - this.unnamed = options.unnamed; - this.named = options.named || "assign"; - } + const runtimeModules = + renderContext.chunkGraph.getChunkRuntimeModulesInOrder(chunk); - /** - * @param {LibraryOptions} library normalized library option - * @returns {T | false} preprocess as needed by overriding - */ - parseOptions(library) { - const { name } = library; - if (this.unnamed === "error") { - if (typeof name !== "string" && !Array.isArray(name)) { - throw new Error( - `Library name must be a string or string array. ${AbstractLibraryPlugin.COMMON_LIBRARY_NAME_MESSAGE}` + if (runtimeModules.length > 0) { + source.add( + new PrefixSource( + prefix, + Template.renderRuntimeModules(runtimeModules, chunkRenderContext) + ) + ); + source.add( + "/************************************************************************/\n" + ); + // runtimeRuntimeModules calls codeGeneration + for (const module of runtimeModules) { + compilation.codeGeneratedModules.add(module); + } + } + if (inlinedModules) { + if (bootstrap.beforeStartup.length > 0) { + const beforeStartup = Template.asString(bootstrap.beforeStartup) + "\n"; + source.add( + new PrefixSource( + prefix, + useSourceMap + ? new OriginalSource(beforeStartup, "webpack/before-startup") + : new RawSource(beforeStartup) + ) ); } - } else { - if (name && typeof name !== "string" && !Array.isArray(name)) { - throw new Error( - `Library name must be a string, string array or unset. ${AbstractLibraryPlugin.COMMON_LIBRARY_NAME_MESSAGE}` + const lastInlinedModule = last(inlinedModules); + const startupSource = new ConcatSource(); + startupSource.add(`var __webpack_exports__ = {};\n`); + for (const m of inlinedModules) { + const renderedModule = this.renderModule( + m, + chunkRenderContext, + hooks, + false + ); + if (renderedModule) { + const innerStrict = !allStrict && m.buildInfo.strict; + const runtimeRequirements = chunkGraph.getModuleRuntimeRequirements( + m, + chunk.runtime + ); + const exports = runtimeRequirements.has(RuntimeGlobals.exports); + const webpackExports = + exports && m.exportsArgument === "__webpack_exports__"; + let iife = innerStrict + ? "it need to be in strict mode." + : inlinedModules.size > 1 + ? // TODO check globals and top-level declarations of other entries and chunk modules + // to make a better decision + "it need to be isolated against other entry modules." + : chunkModules + ? "it need to be isolated against other modules in the chunk." + : exports && !webpackExports + ? `it uses a non-standard name for the exports (${m.exportsArgument}).` + : hooks.embedInRuntimeBailout.call(m, renderContext); + let footer; + if (iife !== undefined) { + startupSource.add( + `// This entry need to be wrapped in an IIFE because ${iife}\n` + ); + const arrow = runtimeTemplate.supportsArrowFunction(); + if (arrow) { + startupSource.add("(() => {\n"); + footer = "\n})();\n\n"; + } else { + startupSource.add("!function() {\n"); + footer = "\n}();\n"; + } + if (innerStrict) startupSource.add('"use strict";\n'); + } else { + footer = "\n"; + } + if (exports) { + if (m !== lastInlinedModule) + startupSource.add(`var ${m.exportsArgument} = {};\n`); + else if (m.exportsArgument !== "__webpack_exports__") + startupSource.add( + `var ${m.exportsArgument} = __webpack_exports__;\n` + ); + } + startupSource.add(renderedModule); + startupSource.add(footer); + } + } + if (runtimeRequirements.has(RuntimeGlobals.onChunksLoaded)) { + startupSource.add( + `__webpack_exports__ = ${RuntimeGlobals.onChunksLoaded}(__webpack_exports__);\n` + ); + } + source.add( + hooks.renderStartup.call(startupSource, lastInlinedModule, { + ...renderContext, + inlined: true + }) + ); + if (bootstrap.afterStartup.length > 0) { + const afterStartup = Template.asString(bootstrap.afterStartup) + "\n"; + source.add( + new PrefixSource( + prefix, + useSourceMap + ? new OriginalSource(afterStartup, "webpack/after-startup") + : new RawSource(afterStartup) + ) ); } + } else { + const lastEntryModule = last( + chunkGraph.getChunkEntryModulesIterable(chunk) + ); + const toSource = useSourceMap + ? (content, name) => + new OriginalSource(Template.asString(content), name) + : content => new RawSource(Template.asString(content)); + source.add( + new PrefixSource( + prefix, + new ConcatSource( + toSource(bootstrap.beforeStartup, "webpack/before-startup"), + "\n", + hooks.renderStartup.call( + toSource(bootstrap.startup.concat(""), "webpack/startup"), + lastEntryModule, + { + ...renderContext, + inlined: false + } + ), + toSource(bootstrap.afterStartup, "webpack/after-startup"), + "\n" + ) + ) + ); + } + if ( + hasEntryModules && + runtimeRequirements.has(RuntimeGlobals.returnExportsFromRuntime) + ) { + source.add(`${prefix}return __webpack_exports__;\n`); + } + if (iife) { + source.add("/******/ })()\n"); } - return { - name: /** @type {string|string[]=} */ (name), - export: library.export - }; - } - /** - * @param {Module} module the exporting entry module - * @param {string} entryName the name of the entrypoint - * @param {LibraryContext} libraryContext context - * @returns {void} - */ - finishEntryModule( - module, - entryName, - { options, compilation, compilation: { moduleGraph } } - ) { - const runtime = getEntryRuntime(compilation, entryName); - if (options.export) { - const exportsInfo = moduleGraph.getExportInfo( - module, - Array.isArray(options.export) ? options.export[0] : options.export + /** @type {Source} */ + let finalSource = tryRunOrWebpackError( + () => hooks.renderMain.call(source, renderContext), + "JavascriptModulesPlugin.getCompilationHooks().renderMain" + ); + if (!finalSource) { + throw new Error( + "JavascriptModulesPlugin error: JavascriptModulesPlugin.getCompilationHooks().renderMain plugins should return something" ); - exportsInfo.setUsed(UsageState.Used, runtime); - exportsInfo.canMangleUse = false; - } else { - const exportsInfo = moduleGraph.getExportsInfo(module); - exportsInfo.setUsedInUnknownWay(runtime); } - moduleGraph.addExtraReason(module, "used as library export"); - } - - _getPrefix(compilation) { - return this.prefix === "global" - ? [compilation.outputOptions.globalObject] - : this.prefix; - } - - _getResolvedFullName(options, chunk, compilation) { - const prefix = this._getPrefix(compilation); - const fullName = options.name ? prefix.concat(options.name) : prefix; - return fullName.map(n => - compilation.getPath(n, { - chunk - }) + finalSource = tryRunOrWebpackError( + () => hooks.renderContent.call(finalSource, renderContext), + "JavascriptModulesPlugin.getCompilationHooks().renderContent" + ); + if (!finalSource) { + throw new Error( + "JavascriptModulesPlugin error: JavascriptModulesPlugin.getCompilationHooks().renderContent plugins should return something" + ); + } + finalSource = InitFragment.addToSource( + finalSource, + chunkRenderContext.chunkInitFragments, + chunkRenderContext + ); + finalSource = tryRunOrWebpackError( + () => hooks.render.call(finalSource, renderContext), + "JavascriptModulesPlugin.getCompilationHooks().render" ); + if (!finalSource) { + throw new Error( + "JavascriptModulesPlugin error: JavascriptModulesPlugin.getCompilationHooks().render plugins should return something" + ); + } + chunk.rendered = true; + return iife ? new ConcatSource(finalSource, ";") : finalSource; } /** - * @param {Source} source source - * @param {RenderContext} renderContext render context - * @param {LibraryContext} libraryContext context - * @returns {Source} source with library export + * @param {Hash} hash the hash to be updated + * @param {RenderBootstrapContext} renderContext options object + * @param {CompilationHooks} hooks hooks */ - render(source, { chunk }, { options, compilation }) { - const fullNameResolved = this._getResolvedFullName( - options, - chunk, - compilation - ); - if (this.declare) { - const base = fullNameResolved[0]; - if (!isNameValid(base)) { - throw new Error( - `Library name base (${base}) must be a valid identifier when using a var declaring library type. Either use a valid identifier (e. g. ${Template.toIdentifier( - base - )}) or use a different library type (e. g. 'type: "global"', which assign a property on the global scope instead of declaring a variable). ${ - AbstractLibraryPlugin.COMMON_LIBRARY_NAME_MESSAGE - }` - ); + updateHashWithBootstrap(hash, renderContext, hooks) { + const bootstrap = this.renderBootstrap(renderContext, hooks); + for (const key of Object.keys(bootstrap)) { + hash.update(key); + if (Array.isArray(bootstrap[key])) { + for (const line of bootstrap[key]) { + hash.update(line); + } + } else { + hash.update(JSON.stringify(bootstrap[key])); } - source = new ConcatSource(`${this.declare} ${base};\n`, source); } - return source; } /** - * @param {Module} module the exporting entry module - * @param {RenderContext} renderContext render context - * @param {LibraryContext} libraryContext context - * @returns {string | undefined} bailout reason + * @param {RenderBootstrapContext} renderContext options object + * @param {CompilationHooks} hooks hooks + * @returns {{ header: string[], beforeStartup: string[], startup: string[], afterStartup: string[], allowInlineStartup: boolean }} the generated source of the bootstrap code */ - embedInRuntimeBailout(module, { chunk }, { options, compilation }) { - const topLevelDeclarations = - module.buildInfo && module.buildInfo.topLevelDeclarations; - if (!topLevelDeclarations) - return "it doesn't tell about top level declarations."; - const fullNameResolved = this._getResolvedFullName( - options, - chunk, - compilation + renderBootstrap(renderContext, hooks) { + const { chunkGraph, moduleGraph, chunk, runtimeTemplate } = renderContext; + + const runtimeRequirements = chunkGraph.getTreeRuntimeRequirements(chunk); + + const requireFunction = runtimeRequirements.has(RuntimeGlobals.require); + const moduleCache = runtimeRequirements.has(RuntimeGlobals.moduleCache); + const moduleFactories = runtimeRequirements.has( + RuntimeGlobals.moduleFactories + ); + const moduleUsed = runtimeRequirements.has(RuntimeGlobals.module); + const requireScopeUsed = runtimeRequirements.has( + RuntimeGlobals.requireScope + ); + const interceptModuleExecution = runtimeRequirements.has( + RuntimeGlobals.interceptModuleExecution ); - const base = fullNameResolved[0]; - if (topLevelDeclarations.has(base)) - return `it declares '${base}' on top-level, which conflicts with the current library output.`; - } - /** - * @param {RenderContext} renderContext render context - * @param {LibraryContext} libraryContext context - * @returns {string | undefined} bailout reason - */ - strictRuntimeBailout({ chunk }, { options, compilation }) { + const useRequire = + requireFunction || interceptModuleExecution || moduleUsed; + + const result = { + header: [], + beforeStartup: [], + startup: [], + afterStartup: [], + allowInlineStartup: true + }; + + let { header: buf, startup, beforeStartup, afterStartup } = result; + + if (result.allowInlineStartup && moduleFactories) { + startup.push( + "// module factories are used so entry inlining is disabled" + ); + result.allowInlineStartup = false; + } + if (result.allowInlineStartup && moduleCache) { + startup.push("// module cache are used so entry inlining is disabled"); + result.allowInlineStartup = false; + } + if (result.allowInlineStartup && interceptModuleExecution) { + startup.push( + "// module execution is intercepted so entry inlining is disabled" + ); + result.allowInlineStartup = false; + } + + if (useRequire || moduleCache) { + buf.push("// The module cache"); + buf.push("var __webpack_module_cache__ = {};"); + buf.push(""); + } + + if (useRequire) { + buf.push("// The require function"); + buf.push(`function __webpack_require__(moduleId) {`); + buf.push(Template.indent(this.renderRequire(renderContext, hooks))); + buf.push("}"); + buf.push(""); + } else if (runtimeRequirements.has(RuntimeGlobals.requireScope)) { + buf.push("// The require scope"); + buf.push("var __webpack_require__ = {};"); + buf.push(""); + } + if ( - this.declare || - this.prefix === "global" || - this.prefix.length > 0 || - !options.name + moduleFactories || + runtimeRequirements.has(RuntimeGlobals.moduleFactoriesAddOnly) ) { - return; + buf.push("// expose the modules object (__webpack_modules__)"); + buf.push(`${RuntimeGlobals.moduleFactories} = __webpack_modules__;`); + buf.push(""); } - return "a global variable is assign and maybe created"; - } - /** - * @param {Source} source source - * @param {Module} module module - * @param {StartupRenderContext} renderContext render context - * @param {LibraryContext} libraryContext context - * @returns {Source} source with library export - */ - renderStartup(source, module, { chunk }, { options, compilation }) { - const fullNameResolved = this._getResolvedFullName( - options, - chunk, - compilation - ); - const exportAccess = options.export - ? propertyAccess( - Array.isArray(options.export) ? options.export : [options.export] - ) - : ""; - const result = new ConcatSource(source); - if (options.name ? this.named === "copy" : this.unnamed === "copy") { - result.add( - `var __webpack_export_target__ = ${accessWithInit( - fullNameResolved, - this._getPrefix(compilation).length, - true - )};\n` - ); - let exports = "__webpack_exports__"; - if (exportAccess) { - result.add( - `var __webpack_exports_export__ = __webpack_exports__${exportAccess};\n` + if (moduleCache) { + buf.push("// expose the module cache"); + buf.push(`${RuntimeGlobals.moduleCache} = __webpack_module_cache__;`); + buf.push(""); + } + + if (interceptModuleExecution) { + buf.push("// expose the module execution interceptor"); + buf.push(`${RuntimeGlobals.interceptModuleExecution} = [];`); + buf.push(""); + } + + if (!runtimeRequirements.has(RuntimeGlobals.startupNoDefault)) { + if (chunkGraph.getNumberOfEntryModules(chunk) > 0) { + /** @type {string[]} */ + const buf2 = []; + const runtimeRequirements = + chunkGraph.getTreeRuntimeRequirements(chunk); + buf2.push("// Load entry module and return exports"); + let i = chunkGraph.getNumberOfEntryModules(chunk); + for (const [ + entryModule, + entrypoint + ] of chunkGraph.getChunkEntryModulesWithChunkGroupIterable(chunk)) { + const chunks = entrypoint.chunks.filter(c => c !== chunk); + if (result.allowInlineStartup && chunks.length > 0) { + buf2.push( + "// This entry module depends on other loaded chunks and execution need to be delayed" + ); + result.allowInlineStartup = false; + } + if ( + result.allowInlineStartup && + someInIterable( + moduleGraph.getIncomingConnectionsByOriginModule(entryModule), + ([originModule, connections]) => + originModule && + connections.some(c => c.isTargetActive(chunk.runtime)) && + someInIterable( + chunkGraph.getModuleRuntimes(originModule), + runtime => + intersectRuntime(runtime, chunk.runtime) !== undefined + ) + ) + ) { + buf2.push( + "// This entry module is referenced by other modules so it can't be inlined" + ); + result.allowInlineStartup = false; + } + if ( + result.allowInlineStartup && + (!entryModule.buildInfo || + !entryModule.buildInfo.topLevelDeclarations) + ) { + buf2.push( + "// This entry module doesn't tell about it's top-level declarations so it can't be inlined" + ); + result.allowInlineStartup = false; + } + if (result.allowInlineStartup) { + const bailout = hooks.inlineInRuntimeBailout.call( + entryModule, + renderContext + ); + if (bailout !== undefined) { + buf2.push( + `// This entry module can't be inlined because ${bailout}` + ); + result.allowInlineStartup = false; + } + } + i--; + const moduleId = chunkGraph.getModuleId(entryModule); + const entryRuntimeRequirements = + chunkGraph.getModuleRuntimeRequirements(entryModule, chunk.runtime); + let moduleIdExpr = JSON.stringify(moduleId); + if (runtimeRequirements.has(RuntimeGlobals.entryModuleId)) { + moduleIdExpr = `${RuntimeGlobals.entryModuleId} = ${moduleIdExpr}`; + } + if ( + result.allowInlineStartup && + entryRuntimeRequirements.has(RuntimeGlobals.module) + ) { + result.allowInlineStartup = false; + buf2.push( + "// This entry module used 'module' so it can't be inlined" + ); + } + if (chunks.length > 0) { + buf2.push( + `${i === 0 ? "var __webpack_exports__ = " : ""}${ + RuntimeGlobals.onChunksLoaded + }(undefined, ${JSON.stringify( + chunks.map(c => c.id) + )}, ${runtimeTemplate.returningFunction( + `__webpack_require__(${moduleIdExpr})` + )})` + ); + } else if (useRequire) { + buf2.push( + `${ + i === 0 ? "var __webpack_exports__ = " : "" + }__webpack_require__(${moduleIdExpr});` + ); + } else { + if (i === 0) buf2.push("var __webpack_exports__ = {};"); + if (requireScopeUsed) { + buf2.push( + `__webpack_modules__[${moduleIdExpr}](0, ${ + i === 0 ? "__webpack_exports__" : "{}" + }, __webpack_require__);` + ); + } else if (entryRuntimeRequirements.has(RuntimeGlobals.exports)) { + buf2.push( + `__webpack_modules__[${moduleIdExpr}](0, ${ + i === 0 ? "__webpack_exports__" : "{}" + });` + ); + } else { + buf2.push(`__webpack_modules__[${moduleIdExpr}]();`); + } + } + } + if (runtimeRequirements.has(RuntimeGlobals.onChunksLoaded)) { + buf2.push( + `__webpack_exports__ = ${RuntimeGlobals.onChunksLoaded}(__webpack_exports__);` + ); + } + if ( + runtimeRequirements.has(RuntimeGlobals.startup) || + (runtimeRequirements.has(RuntimeGlobals.startupOnlyBefore) && + runtimeRequirements.has(RuntimeGlobals.startupOnlyAfter)) + ) { + result.allowInlineStartup = false; + buf.push("// the startup function"); + buf.push( + `${RuntimeGlobals.startup} = ${runtimeTemplate.basicFunction("", [ + ...buf2, + "return __webpack_exports__;" + ])};` + ); + buf.push(""); + startup.push("// run startup"); + startup.push( + `var __webpack_exports__ = ${RuntimeGlobals.startup}();` + ); + } else if (runtimeRequirements.has(RuntimeGlobals.startupOnlyBefore)) { + buf.push("// the startup function"); + buf.push( + `${RuntimeGlobals.startup} = ${runtimeTemplate.emptyFunction()};` + ); + beforeStartup.push("// run runtime startup"); + beforeStartup.push(`${RuntimeGlobals.startup}();`); + startup.push("// startup"); + startup.push(Template.asString(buf2)); + } else if (runtimeRequirements.has(RuntimeGlobals.startupOnlyAfter)) { + buf.push("// the startup function"); + buf.push( + `${RuntimeGlobals.startup} = ${runtimeTemplate.emptyFunction()};` + ); + startup.push("// startup"); + startup.push(Template.asString(buf2)); + afterStartup.push("// run runtime startup"); + afterStartup.push(`${RuntimeGlobals.startup}();`); + } else { + startup.push("// startup"); + startup.push(Template.asString(buf2)); + } + } else if ( + runtimeRequirements.has(RuntimeGlobals.startup) || + runtimeRequirements.has(RuntimeGlobals.startupOnlyBefore) || + runtimeRequirements.has(RuntimeGlobals.startupOnlyAfter) + ) { + buf.push( + "// the startup function", + "// It's empty as no entry modules are in this chunk", + `${RuntimeGlobals.startup} = ${runtimeTemplate.emptyFunction()};`, + "" ); - exports = "__webpack_exports_export__"; } - result.add( - `for(var i in ${exports}) __webpack_export_target__[i] = ${exports}[i];\n` - ); - result.add( - `if(${exports}.__esModule) Object.defineProperty(__webpack_export_target__, "__esModule", { value: true });\n` - ); - } else { - result.add( - `${accessWithInit( - fullNameResolved, - this._getPrefix(compilation).length, - false - )} = __webpack_exports__${exportAccess};\n` + } else if ( + runtimeRequirements.has(RuntimeGlobals.startup) || + runtimeRequirements.has(RuntimeGlobals.startupOnlyBefore) || + runtimeRequirements.has(RuntimeGlobals.startupOnlyAfter) + ) { + result.allowInlineStartup = false; + buf.push( + "// the startup function", + "// It's empty as some runtime module handles the default behavior", + `${RuntimeGlobals.startup} = ${runtimeTemplate.emptyFunction()};` ); + startup.push("// run startup"); + startup.push(`var __webpack_exports__ = ${RuntimeGlobals.startup}();`); } return result; } /** - * @param {Chunk} chunk the chunk - * @param {Set} set runtime requirements - * @param {LibraryContext} libraryContext context - * @returns {void} - */ - runtimeRequirements(chunk, set, libraryContext) { - // we don't need to return exports from runtime - } - - /** - * @param {Chunk} chunk the chunk - * @param {Hash} hash hash - * @param {ChunkHashContext} chunkHashContext chunk hash context - * @param {LibraryContext} libraryContext context - * @returns {void} + * @param {RenderBootstrapContext} renderContext options object + * @param {CompilationHooks} hooks hooks + * @returns {string} the generated source of the require function */ - chunkHash(chunk, hash, chunkHashContext, { options, compilation }) { - hash.update("AssignLibraryPlugin"); - const prefix = - this.prefix === "global" - ? [compilation.outputOptions.globalObject] - : this.prefix; - const fullName = options.name ? prefix.concat(options.name) : prefix; - const fullNameResolved = fullName.map(n => - compilation.getPath(n, { - chunk - }) + renderRequire(renderContext, hooks) { + const { + chunk, + chunkGraph, + runtimeTemplate: { outputOptions } + } = renderContext; + const runtimeRequirements = chunkGraph.getTreeRuntimeRequirements(chunk); + const moduleExecution = runtimeRequirements.has( + RuntimeGlobals.interceptModuleExecution + ) + ? Template.asString([ + "var execOptions = { id: moduleId, module: module, factory: __webpack_modules__[moduleId], require: __webpack_require__ };", + `${RuntimeGlobals.interceptModuleExecution}.forEach(function(handler) { handler(execOptions); });`, + "module = execOptions.module;", + "execOptions.factory.call(module.exports, module, module.exports, execOptions.require);" + ]) + : runtimeRequirements.has(RuntimeGlobals.thisAsExports) + ? Template.asString([ + "__webpack_modules__[moduleId].call(module.exports, module, module.exports, __webpack_require__);" + ]) + : Template.asString([ + "__webpack_modules__[moduleId](module, module.exports, __webpack_require__);" + ]); + const needModuleId = runtimeRequirements.has(RuntimeGlobals.moduleId); + const needModuleLoaded = runtimeRequirements.has( + RuntimeGlobals.moduleLoaded + ); + const content = Template.asString([ + "// Check if module is in cache", + "var cachedModule = __webpack_module_cache__[moduleId];", + "if (cachedModule !== undefined) {", + outputOptions.strictModuleErrorHandling + ? Template.indent([ + "if (cachedModule.error !== undefined) throw cachedModule.error;", + "return cachedModule.exports;" + ]) + : Template.indent("return cachedModule.exports;"), + "}", + "// Create a new module (and put it into the cache)", + "var module = __webpack_module_cache__[moduleId] = {", + Template.indent([ + needModuleId ? "id: moduleId," : "// no module.id needed", + needModuleLoaded ? "loaded: false," : "// no module.loaded needed", + "exports: {}" + ]), + "};", + "", + outputOptions.strictModuleExceptionHandling + ? Template.asString([ + "// Execute the module function", + "var threw = true;", + "try {", + Template.indent([moduleExecution, "threw = false;"]), + "} finally {", + Template.indent([ + "if(threw) delete __webpack_module_cache__[moduleId];" + ]), + "}" + ]) + : outputOptions.strictModuleErrorHandling + ? Template.asString([ + "// Execute the module function", + "try {", + Template.indent(moduleExecution), + "} catch(e) {", + Template.indent(["module.error = e;", "throw e;"]), + "}" + ]) + : Template.asString([ + "// Execute the module function", + moduleExecution + ]), + needModuleLoaded + ? Template.asString([ + "", + "// Flag the module as loaded", + "module.loaded = true;", + "" + ]) + : "", + "// Return the exports of the module", + "return module.exports;" + ]); + return tryRunOrWebpackError( + () => hooks.renderRequire.call(content, renderContext), + "JavascriptModulesPlugin.getCompilationHooks().renderRequire" ); - if (options.name ? this.named === "copy" : this.unnamed === "copy") { - hash.update("copy"); - } - if (this.declare) { - hash.update(this.declare); - } - hash.update(fullNameResolved.join(".")); - if (options.export) { - hash.update(`${options.export}`); - } } } -module.exports = AssignLibraryPlugin; +module.exports = JavascriptModulesPlugin; +module.exports.chunkHasJs = chunkHasJs; /***/ }), -/***/ 35613: +/***/ 42060: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; @@ -97872,2525 +94461,3773 @@ module.exports = AssignLibraryPlugin; -/** @typedef {import("../../declarations/WebpackOptions").LibraryOptions} LibraryOptions */ -/** @typedef {import("../../declarations/WebpackOptions").LibraryType} LibraryType */ -/** @typedef {import("../Compiler")} Compiler */ +const { Parser: AcornParser } = __webpack_require__(29089); +const { importAssertions } = __webpack_require__(10666); +const { SyncBailHook, HookMap } = __webpack_require__(34718); +const vm = __webpack_require__(92184); +const Parser = __webpack_require__(68214); +const StackedMap = __webpack_require__(60798); +const binarySearchBounds = __webpack_require__(44795); +const memoize = __webpack_require__(84297); +const BasicEvaluatedExpression = __webpack_require__(2412); -/** @type {WeakMap>} */ -const enabledTypes = new WeakMap(); +/** @typedef {import("acorn").Options} AcornOptions */ +/** @typedef {import("estree").ArrayExpression} ArrayExpressionNode */ +/** @typedef {import("estree").BinaryExpression} BinaryExpressionNode */ +/** @typedef {import("estree").BlockStatement} BlockStatementNode */ +/** @typedef {import("estree").SequenceExpression} SequenceExpressionNode */ +/** @typedef {import("estree").CallExpression} CallExpressionNode */ +/** @typedef {import("estree").ClassDeclaration} ClassDeclarationNode */ +/** @typedef {import("estree").ClassExpression} ClassExpressionNode */ +/** @typedef {import("estree").Comment} CommentNode */ +/** @typedef {import("estree").ConditionalExpression} ConditionalExpressionNode */ +/** @typedef {import("estree").Declaration} DeclarationNode */ +/** @typedef {import("estree").PrivateIdentifier} PrivateIdentifierNode */ +/** @typedef {import("estree").PropertyDefinition} PropertyDefinitionNode */ +/** @typedef {import("estree").Expression} ExpressionNode */ +/** @typedef {import("estree").Identifier} IdentifierNode */ +/** @typedef {import("estree").IfStatement} IfStatementNode */ +/** @typedef {import("estree").LabeledStatement} LabeledStatementNode */ +/** @typedef {import("estree").Literal} LiteralNode */ +/** @typedef {import("estree").LogicalExpression} LogicalExpressionNode */ +/** @typedef {import("estree").ChainExpression} ChainExpressionNode */ +/** @typedef {import("estree").MemberExpression} MemberExpressionNode */ +/** @typedef {import("estree").MetaProperty} MetaPropertyNode */ +/** @typedef {import("estree").MethodDefinition} MethodDefinitionNode */ +/** @typedef {import("estree").ModuleDeclaration} ModuleDeclarationNode */ +/** @typedef {import("estree").NewExpression} NewExpressionNode */ +/** @typedef {import("estree").Node} AnyNode */ +/** @typedef {import("estree").Program} ProgramNode */ +/** @typedef {import("estree").Statement} StatementNode */ +/** @typedef {import("estree").ImportDeclaration} ImportDeclarationNode */ +/** @typedef {import("estree").ExportNamedDeclaration} ExportNamedDeclarationNode */ +/** @typedef {import("estree").ExportDefaultDeclaration} ExportDefaultDeclarationNode */ +/** @typedef {import("estree").ExportAllDeclaration} ExportAllDeclarationNode */ +/** @typedef {import("estree").Super} SuperNode */ +/** @typedef {import("estree").TaggedTemplateExpression} TaggedTemplateExpressionNode */ +/** @typedef {import("estree").TemplateLiteral} TemplateLiteralNode */ +/** @typedef {import("estree").ThisExpression} ThisExpressionNode */ +/** @typedef {import("estree").UnaryExpression} UnaryExpressionNode */ +/** @typedef {import("estree").VariableDeclarator} VariableDeclaratorNode */ +/** @template T @typedef {import("tapable").AsArray} AsArray */ +/** @typedef {import("../Parser").ParserState} ParserState */ +/** @typedef {import("../Parser").PreparsedAst} PreparsedAst */ +/** @typedef {{declaredScope: ScopeInfo, freeName: string | true, tagInfo: TagInfo | undefined}} VariableInfoInterface */ +/** @typedef {{ name: string | VariableInfo, rootInfo: string | VariableInfo, getMembers: () => string[] }} GetInfoResult */ -const getEnabledTypes = compiler => { - let set = enabledTypes.get(compiler); - if (set === undefined) { - set = new Set(); - enabledTypes.set(compiler, set); - } - return set; -}; +const EMPTY_ARRAY = []; +const ALLOWED_MEMBER_TYPES_CALL_EXPRESSION = 0b01; +const ALLOWED_MEMBER_TYPES_EXPRESSION = 0b10; +const ALLOWED_MEMBER_TYPES_ALL = 0b11; -class EnableLibraryPlugin { +// Syntax: https://developer.mozilla.org/en/SpiderMonkey/Parser_API + +const parser = AcornParser.extend(importAssertions); + +class VariableInfo { /** - * @param {LibraryType} type library type that should be available + * @param {ScopeInfo} declaredScope scope in which the variable is declared + * @param {string | true} freeName which free name the variable aliases, or true when none + * @param {TagInfo | undefined} tagInfo info about tags */ - constructor(type) { - this.type = type; + constructor(declaredScope, freeName, tagInfo) { + this.declaredScope = declaredScope; + this.freeName = freeName; + this.tagInfo = tagInfo; } +} - /** - * @param {Compiler} compiler the compiler instance - * @param {LibraryType} type type of library - * @returns {void} - */ - static setEnabled(compiler, type) { - getEnabledTypes(compiler).add(type); +/** @typedef {string | ScopeInfo | VariableInfo} ExportedVariableInfo */ +/** @typedef {LiteralNode | string | null | undefined} ImportSource */ +/** @typedef {Omit & { sourceType: "module" | "script" | "auto", ecmaVersion?: AcornOptions["ecmaVersion"] }} ParseOptions */ + +/** + * @typedef {Object} TagInfo + * @property {any} tag + * @property {any} data + * @property {TagInfo | undefined} next + */ + +/** + * @typedef {Object} ScopeInfo + * @property {StackedMap} definitions + * @property {boolean | "arrow"} topLevelScope + * @property {boolean} inShorthand + * @property {boolean} isStrict + * @property {boolean} isAsmJs + * @property {boolean} inTry + */ + +const joinRanges = (startRange, endRange) => { + if (!endRange) return startRange; + if (!startRange) return endRange; + return [startRange[0], endRange[1]]; +}; + +const objectAndMembersToName = (object, membersReversed) => { + let name = object; + for (let i = membersReversed.length - 1; i >= 0; i--) { + name = name + "." + membersReversed[i]; } + return name; +}; - /** - * @param {Compiler} compiler the compiler instance - * @param {LibraryType} type type of library - * @returns {void} - */ - static checkEnabled(compiler, type) { - if (!getEnabledTypes(compiler).has(type)) { - throw new Error( - `Library type "${type}" is not enabled. ` + - "EnableLibraryPlugin need to be used to enable this type of library. " + - 'This usually happens through the "output.enabledLibraryTypes" option. ' + - 'If you are using a function as entry which sets "library", you need to add all potential library types to "output.enabledLibraryTypes". ' + - "These types are enabled: " + - Array.from(getEnabledTypes(compiler)).join(", ") - ); - } +const getRootName = expression => { + switch (expression.type) { + case "Identifier": + return expression.name; + case "ThisExpression": + return "this"; + case "MetaProperty": + return `${expression.meta.name}.${expression.property.name}`; + default: + return undefined; } +}; + +/** @type {AcornOptions} */ +const defaultParserOptions = { + ranges: true, + locations: true, + ecmaVersion: "latest", + sourceType: "module", + // https://github.com/tc39/proposal-hashbang + allowHashBang: true, + onComment: null +}; + +// regexp to match at least one "magic comment" +const webpackCommentRegExp = new RegExp(/(^|\W)webpack[A-Z]{1,}[A-Za-z]{1,}:/); + +const EMPTY_COMMENT_OPTIONS = { + options: null, + errors: null +}; +class JavascriptParser extends Parser { /** - * Apply the plugin - * @param {Compiler} compiler the compiler instance - * @returns {void} + * @param {"module" | "script" | "auto"} sourceType default source type */ - apply(compiler) { - const { type } = this; - - // Only enable once - const enabled = getEnabledTypes(compiler); - if (enabled.has(type)) return; - enabled.add(type); + constructor(sourceType = "auto") { + super(); + this.hooks = Object.freeze({ + /** @type {HookMap>} */ + evaluateTypeof: new HookMap(() => new SyncBailHook(["expression"])), + /** @type {HookMap>} */ + evaluate: new HookMap(() => new SyncBailHook(["expression"])), + /** @type {HookMap>} */ + evaluateIdentifier: new HookMap(() => new SyncBailHook(["expression"])), + /** @type {HookMap>} */ + evaluateDefinedIdentifier: new HookMap( + () => new SyncBailHook(["expression"]) + ), + /** @type {HookMap>} */ + evaluateCallExpressionMember: new HookMap( + () => new SyncBailHook(["expression", "param"]) + ), + /** @type {HookMap>} */ + isPure: new HookMap( + () => new SyncBailHook(["expression", "commentsStartPosition"]) + ), + /** @type {SyncBailHook<[StatementNode | ModuleDeclarationNode], boolean | void>} */ + preStatement: new SyncBailHook(["statement"]), - if (typeof type === "string") { - const enableExportProperty = () => { - const ExportPropertyTemplatePlugin = __webpack_require__(84806); - new ExportPropertyTemplatePlugin({ - type, - nsObjectUsed: type !== "module" - }).apply(compiler); - }; - switch (type) { - case "var": { - //@ts-expect-error https://github.com/microsoft/TypeScript/issues/41697 - const AssignLibraryPlugin = __webpack_require__(20909); - new AssignLibraryPlugin({ - type, - prefix: [], - declare: "var", - unnamed: "error" - }).apply(compiler); - break; - } - case "assign-properties": { - //@ts-expect-error https://github.com/microsoft/TypeScript/issues/41697 - const AssignLibraryPlugin = __webpack_require__(20909); - new AssignLibraryPlugin({ - type, - prefix: [], - declare: false, - unnamed: "error", - named: "copy" - }).apply(compiler); - break; - } - case "assign": { - //@ts-expect-error https://github.com/microsoft/TypeScript/issues/41697 - const AssignLibraryPlugin = __webpack_require__(20909); - new AssignLibraryPlugin({ - type, - prefix: [], - declare: false, - unnamed: "error" - }).apply(compiler); - break; - } - case "this": { - //@ts-expect-error https://github.com/microsoft/TypeScript/issues/41697 - const AssignLibraryPlugin = __webpack_require__(20909); - new AssignLibraryPlugin({ - type, - prefix: ["this"], - declare: false, - unnamed: "copy" - }).apply(compiler); - break; - } - case "window": { - //@ts-expect-error https://github.com/microsoft/TypeScript/issues/41697 - const AssignLibraryPlugin = __webpack_require__(20909); - new AssignLibraryPlugin({ - type, - prefix: ["window"], - declare: false, - unnamed: "copy" - }).apply(compiler); - break; - } - case "self": { - //@ts-expect-error https://github.com/microsoft/TypeScript/issues/41697 - const AssignLibraryPlugin = __webpack_require__(20909); - new AssignLibraryPlugin({ - type, - prefix: ["self"], - declare: false, - unnamed: "copy" - }).apply(compiler); - break; - } - case "global": { - //@ts-expect-error https://github.com/microsoft/TypeScript/issues/41697 - const AssignLibraryPlugin = __webpack_require__(20909); - new AssignLibraryPlugin({ - type, - prefix: "global", - declare: false, - unnamed: "copy" - }).apply(compiler); - break; - } - case "commonjs": { - //@ts-expect-error https://github.com/microsoft/TypeScript/issues/41697 - const AssignLibraryPlugin = __webpack_require__(20909); - new AssignLibraryPlugin({ - type, - prefix: ["exports"], - declare: false, - unnamed: "copy" - }).apply(compiler); - break; - } - case "commonjs2": - case "commonjs-module": { - //@ts-expect-error https://github.com/microsoft/TypeScript/issues/41697 - const AssignLibraryPlugin = __webpack_require__(20909); - new AssignLibraryPlugin({ - type, - prefix: ["module", "exports"], - declare: false, - unnamed: "assign" - }).apply(compiler); - break; - } - case "amd": - case "amd-require": { - enableExportProperty(); - const AmdLibraryPlugin = __webpack_require__(4494); - new AmdLibraryPlugin({ - type, - requireAsWrapper: type === "amd-require" - }).apply(compiler); - break; - } - case "umd": - case "umd2": { - enableExportProperty(); - const UmdLibraryPlugin = __webpack_require__(59401); - new UmdLibraryPlugin({ - type, - optionalAmdExternalAsGlobal: type === "umd2" - }).apply(compiler); - break; - } - case "system": { - enableExportProperty(); - const SystemLibraryPlugin = __webpack_require__(36253); - new SystemLibraryPlugin({ - type - }).apply(compiler); - break; - } - case "jsonp": { - enableExportProperty(); - const JsonpLibraryPlugin = __webpack_require__(75773); - new JsonpLibraryPlugin({ - type - }).apply(compiler); - break; - } - case "module": { - enableExportProperty(); - const ModuleLibraryPlugin = __webpack_require__(88548); - new ModuleLibraryPlugin({ - type - }).apply(compiler); - break; - } - default: - throw new Error(`Unsupported library type ${type}. -Plugins which provide custom library types must call EnableLibraryPlugin.setEnabled(compiler, type) to disable this error.`); - } - } else { - // TODO support plugin instances here - // apply them to the compiler - } + /** @type {SyncBailHook<[StatementNode | ModuleDeclarationNode], boolean | void>} */ + blockPreStatement: new SyncBailHook(["declaration"]), + /** @type {SyncBailHook<[StatementNode | ModuleDeclarationNode], boolean | void>} */ + statement: new SyncBailHook(["statement"]), + /** @type {SyncBailHook<[IfStatementNode], boolean | void>} */ + statementIf: new SyncBailHook(["statement"]), + /** @type {SyncBailHook<[ExpressionNode, ClassExpressionNode | ClassDeclarationNode], boolean | void>} */ + classExtendsExpression: new SyncBailHook([ + "expression", + "classDefinition" + ]), + /** @type {SyncBailHook<[MethodDefinitionNode | PropertyDefinitionNode, ClassExpressionNode | ClassDeclarationNode], boolean | void>} */ + classBodyElement: new SyncBailHook(["element", "classDefinition"]), + /** @type {SyncBailHook<[ExpressionNode, MethodDefinitionNode | PropertyDefinitionNode, ClassExpressionNode | ClassDeclarationNode], boolean | void>} */ + classBodyValue: new SyncBailHook([ + "expression", + "element", + "classDefinition" + ]), + /** @type {HookMap>} */ + label: new HookMap(() => new SyncBailHook(["statement"])), + /** @type {SyncBailHook<[ImportDeclarationNode, ImportSource], boolean | void>} */ + import: new SyncBailHook(["statement", "source"]), + /** @type {SyncBailHook<[ImportDeclarationNode, ImportSource, string, string], boolean | void>} */ + importSpecifier: new SyncBailHook([ + "statement", + "source", + "exportName", + "identifierName" + ]), + /** @type {SyncBailHook<[ExportNamedDeclarationNode | ExportAllDeclarationNode], boolean | void>} */ + export: new SyncBailHook(["statement"]), + /** @type {SyncBailHook<[ExportNamedDeclarationNode | ExportAllDeclarationNode, ImportSource], boolean | void>} */ + exportImport: new SyncBailHook(["statement", "source"]), + /** @type {SyncBailHook<[ExportNamedDeclarationNode | ExportAllDeclarationNode, DeclarationNode], boolean | void>} */ + exportDeclaration: new SyncBailHook(["statement", "declaration"]), + /** @type {SyncBailHook<[ExportDefaultDeclarationNode, DeclarationNode], boolean | void>} */ + exportExpression: new SyncBailHook(["statement", "declaration"]), + /** @type {SyncBailHook<[ExportNamedDeclarationNode | ExportAllDeclarationNode, string, string, number | undefined], boolean | void>} */ + exportSpecifier: new SyncBailHook([ + "statement", + "identifierName", + "exportName", + "index" + ]), + /** @type {SyncBailHook<[ExportNamedDeclarationNode | ExportAllDeclarationNode, ImportSource, string, string, number | undefined], boolean | void>} */ + exportImportSpecifier: new SyncBailHook([ + "statement", + "source", + "identifierName", + "exportName", + "index" + ]), + /** @type {SyncBailHook<[VariableDeclaratorNode, StatementNode], boolean | void>} */ + preDeclarator: new SyncBailHook(["declarator", "statement"]), + /** @type {SyncBailHook<[VariableDeclaratorNode, StatementNode], boolean | void>} */ + declarator: new SyncBailHook(["declarator", "statement"]), + /** @type {HookMap>} */ + varDeclaration: new HookMap(() => new SyncBailHook(["declaration"])), + /** @type {HookMap>} */ + varDeclarationLet: new HookMap(() => new SyncBailHook(["declaration"])), + /** @type {HookMap>} */ + varDeclarationConst: new HookMap(() => new SyncBailHook(["declaration"])), + /** @type {HookMap>} */ + varDeclarationVar: new HookMap(() => new SyncBailHook(["declaration"])), + /** @type {HookMap>} */ + pattern: new HookMap(() => new SyncBailHook(["pattern"])), + /** @type {HookMap>} */ + canRename: new HookMap(() => new SyncBailHook(["initExpression"])), + /** @type {HookMap>} */ + rename: new HookMap(() => new SyncBailHook(["initExpression"])), + /** @type {HookMap>} */ + assign: new HookMap(() => new SyncBailHook(["expression"])), + /** @type {HookMap>} */ + assignMemberChain: new HookMap( + () => new SyncBailHook(["expression", "members"]) + ), + /** @type {HookMap>} */ + typeof: new HookMap(() => new SyncBailHook(["expression"])), + /** @type {SyncBailHook<[ExpressionNode], boolean | void>} */ + importCall: new SyncBailHook(["expression"]), + /** @type {SyncBailHook<[ExpressionNode], boolean | void>} */ + topLevelAwait: new SyncBailHook(["expression"]), + /** @type {HookMap>} */ + call: new HookMap(() => new SyncBailHook(["expression"])), + /** Something like "a.b()" */ + /** @type {HookMap>} */ + callMemberChain: new HookMap( + () => new SyncBailHook(["expression", "members"]) + ), + /** Something like "a.b().c.d" */ + /** @type {HookMap>} */ + memberChainOfCallMemberChain: new HookMap( + () => + new SyncBailHook([ + "expression", + "calleeMembers", + "callExpression", + "members" + ]) + ), + /** Something like "a.b().c.d()"" */ + /** @type {HookMap>} */ + callMemberChainOfCallMemberChain: new HookMap( + () => + new SyncBailHook([ + "expression", + "calleeMembers", + "innerCallExpression", + "members" + ]) + ), + /** @type {SyncBailHook<[ChainExpressionNode], boolean | void>} */ + optionalChaining: new SyncBailHook(["optionalChaining"]), + /** @type {HookMap>} */ + new: new HookMap(() => new SyncBailHook(["expression"])), + /** @type {HookMap>} */ + expression: new HookMap(() => new SyncBailHook(["expression"])), + /** @type {HookMap>} */ + expressionMemberChain: new HookMap( + () => new SyncBailHook(["expression", "members"]) + ), + /** @type {HookMap>} */ + unhandledExpressionMemberChain: new HookMap( + () => new SyncBailHook(["expression", "members"]) + ), + /** @type {SyncBailHook<[ExpressionNode], boolean | void>} */ + expressionConditionalOperator: new SyncBailHook(["expression"]), + /** @type {SyncBailHook<[ExpressionNode], boolean | void>} */ + expressionLogicalOperator: new SyncBailHook(["expression"]), + /** @type {SyncBailHook<[ProgramNode, CommentNode[]], boolean | void>} */ + program: new SyncBailHook(["ast", "comments"]), + /** @type {SyncBailHook<[ProgramNode, CommentNode[]], boolean | void>} */ + finish: new SyncBailHook(["ast", "comments"]) + }); + this.sourceType = sourceType; + /** @type {ScopeInfo} */ + this.scope = undefined; + /** @type {ParserState} */ + this.state = undefined; + this.comments = undefined; + this.semicolons = undefined; + /** @type {(StatementNode|ExpressionNode)[]} */ + this.statementPath = undefined; + this.prevStatement = undefined; + this.currentTagData = undefined; + this._initializeEvaluating(); } -} - -module.exports = EnableLibraryPlugin; - - -/***/ }), - -/***/ 84806: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ + _initializeEvaluating() { + this.hooks.evaluate.for("Literal").tap("JavascriptParser", _expr => { + const expr = /** @type {LiteralNode} */ (_expr); + switch (typeof expr.value) { + case "number": + return new BasicEvaluatedExpression() + .setNumber(expr.value) + .setRange(expr.range); + case "bigint": + return new BasicEvaluatedExpression() + .setBigInt(expr.value) + .setRange(expr.range); + case "string": + return new BasicEvaluatedExpression() + .setString(expr.value) + .setRange(expr.range); + case "boolean": + return new BasicEvaluatedExpression() + .setBoolean(expr.value) + .setRange(expr.range); + } + if (expr.value === null) { + return new BasicEvaluatedExpression().setNull().setRange(expr.range); + } + if (expr.value instanceof RegExp) { + return new BasicEvaluatedExpression() + .setRegExp(expr.value) + .setRange(expr.range); + } + }); + this.hooks.evaluate.for("NewExpression").tap("JavascriptParser", _expr => { + const expr = /** @type {NewExpressionNode} */ (_expr); + const callee = expr.callee; + if ( + callee.type !== "Identifier" || + callee.name !== "RegExp" || + expr.arguments.length > 2 || + this.getVariableInfo("RegExp") !== "RegExp" + ) + return; -const { ConcatSource } = __webpack_require__(96192); -const { UsageState } = __webpack_require__(4295); -const propertyAccess = __webpack_require__(86709); -const { getEntryRuntime } = __webpack_require__(19655); -const AbstractLibraryPlugin = __webpack_require__(94051); + let regExp, flags; + const arg1 = expr.arguments[0]; -/** @typedef {import("webpack-sources").Source} Source */ -/** @typedef {import("../../declarations/WebpackOptions").LibraryOptions} LibraryOptions */ -/** @typedef {import("../../declarations/WebpackOptions").LibraryType} LibraryType */ -/** @typedef {import("../Chunk")} Chunk */ -/** @typedef {import("../Compiler")} Compiler */ -/** @typedef {import("../Module")} Module */ -/** @typedef {import("../javascript/JavascriptModulesPlugin").StartupRenderContext} StartupRenderContext */ -/** @template T @typedef {import("./AbstractLibraryPlugin").LibraryContext} LibraryContext */ + if (arg1) { + if (arg1.type === "SpreadElement") return; -/** - * @typedef {Object} ExportPropertyLibraryPluginParsed - * @property {string | string[]} export - */ + const evaluatedRegExp = this.evaluateExpression(arg1); -/** - * @typedef {Object} ExportPropertyLibraryPluginOptions - * @property {LibraryType} type - * @property {boolean} nsObjectUsed the namespace object is used - */ -/** - * @typedef {ExportPropertyLibraryPluginParsed} T - * @extends {AbstractLibraryPlugin} - */ -class ExportPropertyLibraryPlugin extends AbstractLibraryPlugin { - /** - * @param {ExportPropertyLibraryPluginOptions} options options - */ - constructor({ type, nsObjectUsed }) { - super({ - pluginName: "ExportPropertyLibraryPlugin", - type - }); - this.nsObjectUsed = nsObjectUsed; - } + if (!evaluatedRegExp) return; - /** - * @param {LibraryOptions} library normalized library option - * @returns {T | false} preprocess as needed by overriding - */ - parseOptions(library) { - return { - export: library.export - }; - } + regExp = evaluatedRegExp.asString(); - /** - * @param {Module} module the exporting entry module - * @param {string} entryName the name of the entrypoint - * @param {LibraryContext} libraryContext context - * @returns {void} - */ - finishEntryModule( - module, - entryName, - { options, compilation, compilation: { moduleGraph } } - ) { - const runtime = getEntryRuntime(compilation, entryName); - if (options.export) { - const exportsInfo = moduleGraph.getExportInfo( - module, - Array.isArray(options.export) ? options.export[0] : options.export - ); - exportsInfo.setUsed(UsageState.Used, runtime); - exportsInfo.canMangleUse = false; - } else { - const exportsInfo = moduleGraph.getExportsInfo(module); - if (this.nsObjectUsed) { - exportsInfo.setUsedInUnknownWay(runtime); + if (!regExp) return; } else { - exportsInfo.setAllKnownExportsUsed(runtime); + return new BasicEvaluatedExpression() + .setRegExp(new RegExp("")) + .setRange(expr.range); } - } - moduleGraph.addExtraReason(module, "used as library export"); - } - /** - * @param {Chunk} chunk the chunk - * @param {Set} set runtime requirements - * @param {LibraryContext} libraryContext context - * @returns {void} - */ - runtimeRequirements(chunk, set, libraryContext) {} + const arg2 = expr.arguments[1]; - /** - * @param {Source} source source - * @param {Module} module module - * @param {StartupRenderContext} renderContext render context - * @param {LibraryContext} libraryContext context - * @returns {Source} source with library export - */ - renderStartup(source, module, renderContext, { options }) { - if (!options.export) return source; - const postfix = `__webpack_exports__ = __webpack_exports__${propertyAccess( - Array.isArray(options.export) ? options.export : [options.export] - )};\n`; - return new ConcatSource(source, postfix); - } -} + if (arg2) { + if (arg2.type === "SpreadElement") return; -module.exports = ExportPropertyLibraryPlugin; + const evaluatedFlags = this.evaluateExpression(arg2); + if (!evaluatedFlags) return; -/***/ }), + if (!evaluatedFlags.isUndefined()) { + flags = evaluatedFlags.asString(); -/***/ 75773: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + if ( + flags === undefined || + !BasicEvaluatedExpression.isValidRegExpFlags(flags) + ) + return; + } + } -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ + return new BasicEvaluatedExpression() + .setRegExp(flags ? new RegExp(regExp, flags) : new RegExp(regExp)) + .setRange(expr.range); + }); + this.hooks.evaluate + .for("LogicalExpression") + .tap("JavascriptParser", _expr => { + const expr = /** @type {LogicalExpressionNode} */ (_expr); + const left = this.evaluateExpression(expr.left); + if (!left) return; + let returnRight = false; + /** @type {boolean|undefined} */ + let allowedRight; + if (expr.operator === "&&") { + const leftAsBool = left.asBool(); + if (leftAsBool === false) return left.setRange(expr.range); + returnRight = leftAsBool === true; + allowedRight = false; + } else if (expr.operator === "||") { + const leftAsBool = left.asBool(); + if (leftAsBool === true) return left.setRange(expr.range); + returnRight = leftAsBool === false; + allowedRight = true; + } else if (expr.operator === "??") { + const leftAsNullish = left.asNullish(); + if (leftAsNullish === false) return left.setRange(expr.range); + if (leftAsNullish !== true) return; + returnRight = true; + } else return; + const right = this.evaluateExpression(expr.right); + if (!right) return; + if (returnRight) { + if (left.couldHaveSideEffects()) right.setSideEffects(); + return right.setRange(expr.range); + } + const asBool = right.asBool(); -const { ConcatSource } = __webpack_require__(96192); -const AbstractLibraryPlugin = __webpack_require__(94051); + if (allowedRight === true && asBool === true) { + return new BasicEvaluatedExpression() + .setRange(expr.range) + .setTruthy(); + } else if (allowedRight === false && asBool === false) { + return new BasicEvaluatedExpression().setRange(expr.range).setFalsy(); + } + }); -/** @typedef {import("webpack-sources").Source} Source */ -/** @typedef {import("../../declarations/WebpackOptions").LibraryOptions} LibraryOptions */ -/** @typedef {import("../../declarations/WebpackOptions").LibraryType} LibraryType */ -/** @typedef {import("../Chunk")} Chunk */ -/** @typedef {import("../Compilation").ChunkHashContext} ChunkHashContext */ -/** @typedef {import("../Compiler")} Compiler */ -/** @typedef {import("../javascript/JavascriptModulesPlugin").RenderContext} RenderContext */ -/** @typedef {import("../util/Hash")} Hash */ -/** @template T @typedef {import("./AbstractLibraryPlugin").LibraryContext} LibraryContext */ + const valueAsExpression = (value, expr, sideEffects) => { + switch (typeof value) { + case "boolean": + return new BasicEvaluatedExpression() + .setBoolean(value) + .setSideEffects(sideEffects) + .setRange(expr.range); + case "number": + return new BasicEvaluatedExpression() + .setNumber(value) + .setSideEffects(sideEffects) + .setRange(expr.range); + case "bigint": + return new BasicEvaluatedExpression() + .setBigInt(value) + .setSideEffects(sideEffects) + .setRange(expr.range); + case "string": + return new BasicEvaluatedExpression() + .setString(value) + .setSideEffects(sideEffects) + .setRange(expr.range); + } + }; -/** - * @typedef {Object} JsonpLibraryPluginOptions - * @property {LibraryType} type - */ + this.hooks.evaluate + .for("BinaryExpression") + .tap("JavascriptParser", _expr => { + const expr = /** @type {BinaryExpressionNode} */ (_expr); -/** - * @typedef {Object} JsonpLibraryPluginParsed - * @property {string} name - */ + const handleConstOperation = fn => { + const left = this.evaluateExpression(expr.left); + if (!left || !left.isCompileTimeValue()) return; -/** - * @typedef {JsonpLibraryPluginParsed} T - * @extends {AbstractLibraryPlugin} - */ -class JsonpLibraryPlugin extends AbstractLibraryPlugin { - /** - * @param {JsonpLibraryPluginOptions} options the plugin options - */ - constructor(options) { - super({ - pluginName: "JsonpLibraryPlugin", - type: options.type - }); - } + const right = this.evaluateExpression(expr.right); + if (!right || !right.isCompileTimeValue()) return; - /** - * @param {LibraryOptions} library normalized library option - * @returns {T | false} preprocess as needed by overriding - */ - parseOptions(library) { - const { name } = library; - if (typeof name !== "string") { - throw new Error( - `Jsonp library name must be a simple string. ${AbstractLibraryPlugin.COMMON_LIBRARY_NAME_MESSAGE}` - ); - } - return { - name: /** @type {string} */ (name) - }; - } + const result = fn( + left.asCompileTimeValue(), + right.asCompileTimeValue() + ); + return valueAsExpression( + result, + expr, + left.couldHaveSideEffects() || right.couldHaveSideEffects() + ); + }; - /** - * @param {Source} source source - * @param {RenderContext} renderContext render context - * @param {LibraryContext} libraryContext context - * @returns {Source} source with library export - */ - render(source, { chunk }, { options, compilation }) { - const name = compilation.getPath(options.name, { - chunk - }); - return new ConcatSource(`${name}(`, source, ")"); - } + const isAlwaysDifferent = (a, b) => + (a === true && b === false) || (a === false && b === true); - /** - * @param {Chunk} chunk the chunk - * @param {Hash} hash hash - * @param {ChunkHashContext} chunkHashContext chunk hash context - * @param {LibraryContext} libraryContext context - * @returns {void} - */ - chunkHash(chunk, hash, chunkHashContext, { options, compilation }) { - hash.update("JsonpLibraryPlugin"); - hash.update(compilation.getPath(options.name, { chunk })); - } -} + const handleTemplateStringCompare = (left, right, res, eql) => { + const getPrefix = parts => { + let value = ""; + for (const p of parts) { + const v = p.asString(); + if (v !== undefined) value += v; + else break; + } + return value; + }; + const getSuffix = parts => { + let value = ""; + for (let i = parts.length - 1; i >= 0; i--) { + const v = parts[i].asString(); + if (v !== undefined) value = v + value; + else break; + } + return value; + }; + const leftPrefix = getPrefix(left.parts); + const rightPrefix = getPrefix(right.parts); + const leftSuffix = getSuffix(left.parts); + const rightSuffix = getSuffix(right.parts); + const lenPrefix = Math.min(leftPrefix.length, rightPrefix.length); + const lenSuffix = Math.min(leftSuffix.length, rightSuffix.length); + if ( + leftPrefix.slice(0, lenPrefix) !== + rightPrefix.slice(0, lenPrefix) || + leftSuffix.slice(-lenSuffix) !== rightSuffix.slice(-lenSuffix) + ) { + return res + .setBoolean(!eql) + .setSideEffects( + left.couldHaveSideEffects() || right.couldHaveSideEffects() + ); + } + }; -module.exports = JsonpLibraryPlugin; + const handleStrictEqualityComparison = eql => { + const left = this.evaluateExpression(expr.left); + if (!left) return; + const right = this.evaluateExpression(expr.right); + if (!right) return; + const res = new BasicEvaluatedExpression(); + res.setRange(expr.range); + const leftConst = left.isCompileTimeValue(); + const rightConst = right.isCompileTimeValue(); -/***/ }), + if (leftConst && rightConst) { + return res + .setBoolean( + eql === + (left.asCompileTimeValue() === right.asCompileTimeValue()) + ) + .setSideEffects( + left.couldHaveSideEffects() || right.couldHaveSideEffects() + ); + } -/***/ 88548: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + if (left.isArray() && right.isArray()) { + return res + .setBoolean(!eql) + .setSideEffects( + left.couldHaveSideEffects() || right.couldHaveSideEffects() + ); + } + if (left.isTemplateString() && right.isTemplateString()) { + return handleTemplateStringCompare(left, right, res, eql); + } -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ + const leftPrimitive = left.isPrimitiveType(); + const rightPrimitive = right.isPrimitiveType(); + + if ( + // Primitive !== Object or + // compile-time object types are never equal to something at runtime + (leftPrimitive === false && + (leftConst || rightPrimitive === true)) || + (rightPrimitive === false && + (rightConst || leftPrimitive === true)) || + // Different nullish or boolish status also means not equal + isAlwaysDifferent(left.asBool(), right.asBool()) || + isAlwaysDifferent(left.asNullish(), right.asNullish()) + ) { + return res + .setBoolean(!eql) + .setSideEffects( + left.couldHaveSideEffects() || right.couldHaveSideEffects() + ); + } + }; + const handleAbstractEqualityComparison = eql => { + const left = this.evaluateExpression(expr.left); + if (!left) return; + const right = this.evaluateExpression(expr.right); + if (!right) return; + const res = new BasicEvaluatedExpression(); + res.setRange(expr.range); + const leftConst = left.isCompileTimeValue(); + const rightConst = right.isCompileTimeValue(); -const { ConcatSource } = __webpack_require__(96192); -const Template = __webpack_require__(92066); -const propertyAccess = __webpack_require__(86709); -const AbstractLibraryPlugin = __webpack_require__(94051); + if (leftConst && rightConst) { + return res + .setBoolean( + eql === + // eslint-disable-next-line eqeqeq + (left.asCompileTimeValue() == right.asCompileTimeValue()) + ) + .setSideEffects( + left.couldHaveSideEffects() || right.couldHaveSideEffects() + ); + } -/** @typedef {import("webpack-sources").Source} Source */ -/** @typedef {import("../../declarations/WebpackOptions").LibraryOptions} LibraryOptions */ -/** @typedef {import("../../declarations/WebpackOptions").LibraryType} LibraryType */ -/** @typedef {import("../Chunk")} Chunk */ -/** @typedef {import("../Compilation").ChunkHashContext} ChunkHashContext */ -/** @typedef {import("../Compiler")} Compiler */ -/** @typedef {import("../Module")} Module */ -/** @typedef {import("../javascript/JavascriptModulesPlugin").StartupRenderContext} StartupRenderContext */ -/** @typedef {import("../util/Hash")} Hash */ -/** @template T @typedef {import("./AbstractLibraryPlugin").LibraryContext} LibraryContext */ + if (left.isArray() && right.isArray()) { + return res + .setBoolean(!eql) + .setSideEffects( + left.couldHaveSideEffects() || right.couldHaveSideEffects() + ); + } + if (left.isTemplateString() && right.isTemplateString()) { + return handleTemplateStringCompare(left, right, res, eql); + } + }; -/** - * @typedef {Object} ModuleLibraryPluginOptions - * @property {LibraryType} type - */ + if (expr.operator === "+") { + const left = this.evaluateExpression(expr.left); + if (!left) return; + const right = this.evaluateExpression(expr.right); + if (!right) return; + const res = new BasicEvaluatedExpression(); + if (left.isString()) { + if (right.isString()) { + res.setString(left.string + right.string); + } else if (right.isNumber()) { + res.setString(left.string + right.number); + } else if ( + right.isWrapped() && + right.prefix && + right.prefix.isString() + ) { + // "left" + ("prefix" + inner + "postfix") + // => ("leftPrefix" + inner + "postfix") + res.setWrapped( + new BasicEvaluatedExpression() + .setString(left.string + right.prefix.string) + .setRange(joinRanges(left.range, right.prefix.range)), + right.postfix, + right.wrappedInnerExpressions + ); + } else if (right.isWrapped()) { + // "left" + ([null] + inner + "postfix") + // => ("left" + inner + "postfix") + res.setWrapped( + left, + right.postfix, + right.wrappedInnerExpressions + ); + } else { + // "left" + expr + // => ("left" + expr + "") + res.setWrapped(left, null, [right]); + } + } else if (left.isNumber()) { + if (right.isString()) { + res.setString(left.number + right.string); + } else if (right.isNumber()) { + res.setNumber(left.number + right.number); + } else { + return; + } + } else if (left.isBigInt()) { + if (right.isBigInt()) { + res.setBigInt(left.bigint + right.bigint); + } + } else if (left.isWrapped()) { + if (left.postfix && left.postfix.isString() && right.isString()) { + // ("prefix" + inner + "postfix") + "right" + // => ("prefix" + inner + "postfixRight") + res.setWrapped( + left.prefix, + new BasicEvaluatedExpression() + .setString(left.postfix.string + right.string) + .setRange(joinRanges(left.postfix.range, right.range)), + left.wrappedInnerExpressions + ); + } else if ( + left.postfix && + left.postfix.isString() && + right.isNumber() + ) { + // ("prefix" + inner + "postfix") + 123 + // => ("prefix" + inner + "postfix123") + res.setWrapped( + left.prefix, + new BasicEvaluatedExpression() + .setString(left.postfix.string + right.number) + .setRange(joinRanges(left.postfix.range, right.range)), + left.wrappedInnerExpressions + ); + } else if (right.isString()) { + // ("prefix" + inner + [null]) + "right" + // => ("prefix" + inner + "right") + res.setWrapped(left.prefix, right, left.wrappedInnerExpressions); + } else if (right.isNumber()) { + // ("prefix" + inner + [null]) + 123 + // => ("prefix" + inner + "123") + res.setWrapped( + left.prefix, + new BasicEvaluatedExpression() + .setString(right.number + "") + .setRange(right.range), + left.wrappedInnerExpressions + ); + } else if (right.isWrapped()) { + // ("prefix1" + inner1 + "postfix1") + ("prefix2" + inner2 + "postfix2") + // ("prefix1" + inner1 + "postfix1" + "prefix2" + inner2 + "postfix2") + res.setWrapped( + left.prefix, + right.postfix, + left.wrappedInnerExpressions && + right.wrappedInnerExpressions && + left.wrappedInnerExpressions + .concat(left.postfix ? [left.postfix] : []) + .concat(right.prefix ? [right.prefix] : []) + .concat(right.wrappedInnerExpressions) + ); + } else { + // ("prefix" + inner + postfix) + expr + // => ("prefix" + inner + postfix + expr + [null]) + res.setWrapped( + left.prefix, + null, + left.wrappedInnerExpressions && + left.wrappedInnerExpressions.concat( + left.postfix ? [left.postfix, right] : [right] + ) + ); + } + } else { + if (right.isString()) { + // left + "right" + // => ([null] + left + "right") + res.setWrapped(null, right, [left]); + } else if (right.isWrapped()) { + // left + (prefix + inner + "postfix") + // => ([null] + left + prefix + inner + "postfix") + res.setWrapped( + null, + right.postfix, + right.wrappedInnerExpressions && + (right.prefix ? [left, right.prefix] : [left]).concat( + right.wrappedInnerExpressions + ) + ); + } else { + return; + } + } + if (left.couldHaveSideEffects() || right.couldHaveSideEffects()) + res.setSideEffects(); + res.setRange(expr.range); + return res; + } else if (expr.operator === "-") { + return handleConstOperation((l, r) => l - r); + } else if (expr.operator === "*") { + return handleConstOperation((l, r) => l * r); + } else if (expr.operator === "/") { + return handleConstOperation((l, r) => l / r); + } else if (expr.operator === "**") { + return handleConstOperation((l, r) => l ** r); + } else if (expr.operator === "===") { + return handleStrictEqualityComparison(true); + } else if (expr.operator === "==") { + return handleAbstractEqualityComparison(true); + } else if (expr.operator === "!==") { + return handleStrictEqualityComparison(false); + } else if (expr.operator === "!=") { + return handleAbstractEqualityComparison(false); + } else if (expr.operator === "&") { + return handleConstOperation((l, r) => l & r); + } else if (expr.operator === "|") { + return handleConstOperation((l, r) => l | r); + } else if (expr.operator === "^") { + return handleConstOperation((l, r) => l ^ r); + } else if (expr.operator === ">>>") { + return handleConstOperation((l, r) => l >>> r); + } else if (expr.operator === ">>") { + return handleConstOperation((l, r) => l >> r); + } else if (expr.operator === "<<") { + return handleConstOperation((l, r) => l << r); + } else if (expr.operator === "<") { + return handleConstOperation((l, r) => l < r); + } else if (expr.operator === ">") { + return handleConstOperation((l, r) => l > r); + } else if (expr.operator === "<=") { + return handleConstOperation((l, r) => l <= r); + } else if (expr.operator === ">=") { + return handleConstOperation((l, r) => l >= r); + } + }); + this.hooks.evaluate + .for("UnaryExpression") + .tap("JavascriptParser", _expr => { + const expr = /** @type {UnaryExpressionNode} */ (_expr); -/** - * @typedef {Object} ModuleLibraryPluginParsed - * @property {string} name - */ + const handleConstOperation = fn => { + const argument = this.evaluateExpression(expr.argument); + if (!argument || !argument.isCompileTimeValue()) return; + const result = fn(argument.asCompileTimeValue()); + return valueAsExpression( + result, + expr, + argument.couldHaveSideEffects() + ); + }; -/** - * @typedef {ModuleLibraryPluginParsed} T - * @extends {AbstractLibraryPlugin} - */ -class ModuleLibraryPlugin extends AbstractLibraryPlugin { - /** - * @param {ModuleLibraryPluginOptions} options the plugin options - */ - constructor(options) { - super({ - pluginName: "ModuleLibraryPlugin", - type: options.type + if (expr.operator === "typeof") { + switch (expr.argument.type) { + case "Identifier": { + const res = this.callHooksForName( + this.hooks.evaluateTypeof, + expr.argument.name, + expr + ); + if (res !== undefined) return res; + break; + } + case "MetaProperty": { + const res = this.callHooksForName( + this.hooks.evaluateTypeof, + getRootName(expr.argument), + expr + ); + if (res !== undefined) return res; + break; + } + case "MemberExpression": { + const res = this.callHooksForExpression( + this.hooks.evaluateTypeof, + expr.argument, + expr + ); + if (res !== undefined) return res; + break; + } + case "ChainExpression": { + const res = this.callHooksForExpression( + this.hooks.evaluateTypeof, + expr.argument.expression, + expr + ); + if (res !== undefined) return res; + break; + } + case "FunctionExpression": { + return new BasicEvaluatedExpression() + .setString("function") + .setRange(expr.range); + } + } + const arg = this.evaluateExpression(expr.argument); + if (arg.isUnknown()) return; + if (arg.isString()) { + return new BasicEvaluatedExpression() + .setString("string") + .setRange(expr.range); + } + if (arg.isWrapped()) { + return new BasicEvaluatedExpression() + .setString("string") + .setSideEffects() + .setRange(expr.range); + } + if (arg.isUndefined()) { + return new BasicEvaluatedExpression() + .setString("undefined") + .setRange(expr.range); + } + if (arg.isNumber()) { + return new BasicEvaluatedExpression() + .setString("number") + .setRange(expr.range); + } + if (arg.isBigInt()) { + return new BasicEvaluatedExpression() + .setString("bigint") + .setRange(expr.range); + } + if (arg.isBoolean()) { + return new BasicEvaluatedExpression() + .setString("boolean") + .setRange(expr.range); + } + if (arg.isConstArray() || arg.isRegExp() || arg.isNull()) { + return new BasicEvaluatedExpression() + .setString("object") + .setRange(expr.range); + } + if (arg.isArray()) { + return new BasicEvaluatedExpression() + .setString("object") + .setSideEffects(arg.couldHaveSideEffects()) + .setRange(expr.range); + } + } else if (expr.operator === "!") { + const argument = this.evaluateExpression(expr.argument); + if (!argument) return; + const bool = argument.asBool(); + if (typeof bool !== "boolean") return; + return new BasicEvaluatedExpression() + .setBoolean(!bool) + .setSideEffects(argument.couldHaveSideEffects()) + .setRange(expr.range); + } else if (expr.operator === "~") { + return handleConstOperation(v => ~v); + } else if (expr.operator === "+") { + return handleConstOperation(v => +v); + } else if (expr.operator === "-") { + return handleConstOperation(v => -v); + } + }); + this.hooks.evaluateTypeof.for("undefined").tap("JavascriptParser", expr => { + return new BasicEvaluatedExpression() + .setString("undefined") + .setRange(expr.range); }); - } + /** + * @param {string} exprType expression type name + * @param {function(ExpressionNode): GetInfoResult | undefined} getInfo get info + * @returns {void} + */ + const tapEvaluateWithVariableInfo = (exprType, getInfo) => { + /** @type {ExpressionNode | undefined} */ + let cachedExpression = undefined; + /** @type {GetInfoResult | undefined} */ + let cachedInfo = undefined; + this.hooks.evaluate.for(exprType).tap("JavascriptParser", expr => { + const expression = /** @type {MemberExpressionNode} */ (expr); - /** - * @param {LibraryOptions} library normalized library option - * @returns {T | false} preprocess as needed by overriding - */ - parseOptions(library) { - const { name } = library; - if (name) { - throw new Error( - `Library name must be unset. ${AbstractLibraryPlugin.COMMON_LIBRARY_NAME_MESSAGE}` - ); - } - return { - name: /** @type {string} */ (name) + const info = getInfo(expr); + if (info !== undefined) { + return this.callHooksForInfoWithFallback( + this.hooks.evaluateIdentifier, + info.name, + name => { + cachedExpression = expression; + cachedInfo = info; + }, + name => { + const hook = this.hooks.evaluateDefinedIdentifier.get(name); + if (hook !== undefined) { + return hook.call(expression); + } + }, + expression + ); + } + }); + this.hooks.evaluate + .for(exprType) + .tap({ name: "JavascriptParser", stage: 100 }, expr => { + const info = cachedExpression === expr ? cachedInfo : getInfo(expr); + if (info !== undefined) { + return new BasicEvaluatedExpression() + .setIdentifier(info.name, info.rootInfo, info.getMembers) + .setRange(expr.range); + } + }); + this.hooks.finish.tap("JavascriptParser", () => { + // Cleanup for GC + cachedExpression = cachedInfo = undefined; + }); }; - } - - /** - * @param {Source} source source - * @param {Module} module module - * @param {StartupRenderContext} renderContext render context - * @param {LibraryContext} libraryContext context - * @returns {Source} source with library export - */ - renderStartup( - source, - module, - { moduleGraph, chunk }, - { options, compilation } - ) { - const result = new ConcatSource(source); - const exportsInfo = moduleGraph.getExportsInfo(module); - const exports = []; - const isAsync = moduleGraph.isAsync(module); - if (isAsync) { - result.add(`__webpack_exports__ = await __webpack_exports__;\n`); - } - for (const exportInfo of exportsInfo.orderedExports) { - if (!exportInfo.provided) continue; - const varName = `__webpack_exports__${Template.toIdentifier( - exportInfo.name - )}`; - result.add( - `var ${varName} = __webpack_exports__${propertyAccess([ - exportInfo.getUsedName(exportInfo.name, chunk.runtime) - ])};\n` + tapEvaluateWithVariableInfo("Identifier", expr => { + const info = this.getVariableInfo( + /** @type {IdentifierNode} */ (expr).name ); - exports.push(`${varName} as ${exportInfo.name}`); - } - if (exports.length > 0) { - result.add(`export { ${exports.join(", ")} };\n`); - } - return result; - } -} - -module.exports = ModuleLibraryPlugin; - + if ( + typeof info === "string" || + (info instanceof VariableInfo && typeof info.freeName === "string") + ) { + return { name: info, rootInfo: info, getMembers: () => [] }; + } + }); + tapEvaluateWithVariableInfo("ThisExpression", expr => { + const info = this.getVariableInfo("this"); + if ( + typeof info === "string" || + (info instanceof VariableInfo && typeof info.freeName === "string") + ) { + return { name: info, rootInfo: info, getMembers: () => [] }; + } + }); + this.hooks.evaluate.for("MetaProperty").tap("JavascriptParser", expr => { + const metaProperty = /** @type {MetaPropertyNode} */ (expr); -/***/ }), + return this.callHooksForName( + this.hooks.evaluateIdentifier, + getRootName(expr), + metaProperty + ); + }); + tapEvaluateWithVariableInfo("MemberExpression", expr => + this.getMemberExpressionInfo( + /** @type {MemberExpressionNode} */ (expr), + ALLOWED_MEMBER_TYPES_EXPRESSION + ) + ); -/***/ 36253: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + this.hooks.evaluate.for("CallExpression").tap("JavascriptParser", _expr => { + const expr = /** @type {CallExpressionNode} */ (_expr); + if ( + expr.callee.type !== "MemberExpression" || + expr.callee.property.type !== + (expr.callee.computed ? "Literal" : "Identifier") + ) { + return; + } -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Joel Denning @joeldenning -*/ + // type Super also possible here + const param = this.evaluateExpression( + /** @type {ExpressionNode} */ (expr.callee.object) + ); + if (!param) return; + const property = + expr.callee.property.type === "Literal" + ? `${expr.callee.property.value}` + : expr.callee.property.name; + const hook = this.hooks.evaluateCallExpressionMember.get(property); + if (hook !== undefined) { + return hook.call(expr, param); + } + }); + this.hooks.evaluateCallExpressionMember + .for("indexOf") + .tap("JavascriptParser", (expr, param) => { + if (!param.isString()) return; + if (expr.arguments.length === 0) return; + const [arg1, arg2] = expr.arguments; + if (arg1.type === "SpreadElement") return; + const arg1Eval = this.evaluateExpression(arg1); + if (!arg1Eval.isString()) return; + const arg1Value = arg1Eval.string; + let result; + if (arg2) { + if (arg2.type === "SpreadElement") return; + const arg2Eval = this.evaluateExpression(arg2); + if (!arg2Eval.isNumber()) return; + result = param.string.indexOf(arg1Value, arg2Eval.number); + } else { + result = param.string.indexOf(arg1Value); + } + return new BasicEvaluatedExpression() + .setNumber(result) + .setSideEffects(param.couldHaveSideEffects()) + .setRange(expr.range); + }); + this.hooks.evaluateCallExpressionMember + .for("replace") + .tap("JavascriptParser", (expr, param) => { + if (!param.isString()) return; + if (expr.arguments.length !== 2) return; + if (expr.arguments[0].type === "SpreadElement") return; + if (expr.arguments[1].type === "SpreadElement") return; + let arg1 = this.evaluateExpression(expr.arguments[0]); + let arg2 = this.evaluateExpression(expr.arguments[1]); + if (!arg1.isString() && !arg1.isRegExp()) return; + const arg1Value = arg1.regExp || arg1.string; + if (!arg2.isString()) return; + const arg2Value = arg2.string; + return new BasicEvaluatedExpression() + .setString(param.string.replace(arg1Value, arg2Value)) + .setSideEffects(param.couldHaveSideEffects()) + .setRange(expr.range); + }); + ["substr", "substring", "slice"].forEach(fn => { + this.hooks.evaluateCallExpressionMember + .for(fn) + .tap("JavascriptParser", (expr, param) => { + if (!param.isString()) return; + let arg1; + let result, + str = param.string; + switch (expr.arguments.length) { + case 1: + if (expr.arguments[0].type === "SpreadElement") return; + arg1 = this.evaluateExpression(expr.arguments[0]); + if (!arg1.isNumber()) return; + result = str[fn](arg1.number); + break; + case 2: { + if (expr.arguments[0].type === "SpreadElement") return; + if (expr.arguments[1].type === "SpreadElement") return; + arg1 = this.evaluateExpression(expr.arguments[0]); + const arg2 = this.evaluateExpression(expr.arguments[1]); + if (!arg1.isNumber()) return; + if (!arg2.isNumber()) return; + result = str[fn](arg1.number, arg2.number); + break; + } + default: + return; + } + return new BasicEvaluatedExpression() + .setString(result) + .setSideEffects(param.couldHaveSideEffects()) + .setRange(expr.range); + }); + }); + /** + * @param {"cooked" | "raw"} kind kind of values to get + * @param {TemplateLiteralNode} templateLiteralExpr TemplateLiteral expr + * @returns {{quasis: BasicEvaluatedExpression[], parts: BasicEvaluatedExpression[]}} Simplified template + */ + const getSimplifiedTemplateResult = (kind, templateLiteralExpr) => { + /** @type {BasicEvaluatedExpression[]} */ + const quasis = []; + /** @type {BasicEvaluatedExpression[]} */ + const parts = []; -const { ConcatSource } = __webpack_require__(96192); -const { UsageState } = __webpack_require__(4295); -const ExternalModule = __webpack_require__(89805); -const Template = __webpack_require__(92066); -const propertyAccess = __webpack_require__(86709); -const AbstractLibraryPlugin = __webpack_require__(94051); + for (let i = 0; i < templateLiteralExpr.quasis.length; i++) { + const quasiExpr = templateLiteralExpr.quasis[i]; + const quasi = quasiExpr.value[kind]; -/** @typedef {import("webpack-sources").Source} Source */ -/** @typedef {import("../../declarations/WebpackOptions").LibraryOptions} LibraryOptions */ -/** @typedef {import("../../declarations/WebpackOptions").LibraryType} LibraryType */ -/** @typedef {import("../Chunk")} Chunk */ -/** @typedef {import("../Compilation").ChunkHashContext} ChunkHashContext */ -/** @typedef {import("../Compiler")} Compiler */ -/** @typedef {import("../javascript/JavascriptModulesPlugin").RenderContext} RenderContext */ -/** @typedef {import("../util/Hash")} Hash */ -/** @template T @typedef {import("./AbstractLibraryPlugin").LibraryContext} LibraryContext */ + if (i > 0) { + const prevExpr = parts[parts.length - 1]; + const expr = this.evaluateExpression( + templateLiteralExpr.expressions[i - 1] + ); + const exprAsString = expr.asString(); + if ( + typeof exprAsString === "string" && + !expr.couldHaveSideEffects() + ) { + // We can merge quasi + expr + quasi when expr + // is a const string -/** - * @typedef {Object} SystemLibraryPluginOptions - * @property {LibraryType} type - */ + prevExpr.setString(prevExpr.string + exprAsString + quasi); + prevExpr.setRange([prevExpr.range[0], quasiExpr.range[1]]); + // We unset the expression as it doesn't match to a single expression + prevExpr.setExpression(undefined); + continue; + } + parts.push(expr); + } -/** - * @typedef {Object} SystemLibraryPluginParsed - * @property {string} name - */ + const part = new BasicEvaluatedExpression() + .setString(quasi) + .setRange(quasiExpr.range) + .setExpression(quasiExpr); + quasis.push(part); + parts.push(part); + } + return { + quasis, + parts + }; + }; -/** - * @typedef {SystemLibraryPluginParsed} T - * @extends {AbstractLibraryPlugin} - */ -class SystemLibraryPlugin extends AbstractLibraryPlugin { - /** - * @param {SystemLibraryPluginOptions} options the plugin options - */ - constructor(options) { - super({ - pluginName: "SystemLibraryPlugin", - type: options.type - }); - } + this.hooks.evaluate + .for("TemplateLiteral") + .tap("JavascriptParser", _node => { + const node = /** @type {TemplateLiteralNode} */ (_node); - /** - * @param {LibraryOptions} library normalized library option - * @returns {T | false} preprocess as needed by overriding - */ - parseOptions(library) { - const { name } = library; - if (name && typeof name !== "string") { - throw new Error( - `System.js library name must be a simple string or unset. ${AbstractLibraryPlugin.COMMON_LIBRARY_NAME_MESSAGE}` - ); - } - return { - name: /** @type {string=} */ (name) - }; - } + const { quasis, parts } = getSimplifiedTemplateResult("cooked", node); + if (parts.length === 1) { + return parts[0].setRange(node.range); + } + return new BasicEvaluatedExpression() + .setTemplateString(quasis, parts, "cooked") + .setRange(node.range); + }); + this.hooks.evaluate + .for("TaggedTemplateExpression") + .tap("JavascriptParser", _node => { + const node = /** @type {TaggedTemplateExpressionNode} */ (_node); + const tag = this.evaluateExpression(node.tag); - /** - * @param {Source} source source - * @param {RenderContext} renderContext render context - * @param {LibraryContext} libraryContext context - * @returns {Source} source with library export - */ - render(source, { chunkGraph, moduleGraph, chunk }, { options, compilation }) { - const modules = chunkGraph - .getChunkModules(chunk) - .filter(m => m instanceof ExternalModule && m.externalType === "system"); - const externals = /** @type {ExternalModule[]} */ (modules); + if (tag.isIdentifier() && tag.identifier !== "String.raw") return; + const { quasis, parts } = getSimplifiedTemplateResult( + "raw", + node.quasi + ); + return new BasicEvaluatedExpression() + .setTemplateString(quasis, parts, "raw") + .setRange(node.range); + }); - // The name this bundle should be registered as with System - const name = options.name - ? `${JSON.stringify(compilation.getPath(options.name, { chunk }))}, ` - : ""; + this.hooks.evaluateCallExpressionMember + .for("concat") + .tap("JavascriptParser", (expr, param) => { + if (!param.isString() && !param.isWrapped()) return; - // The array of dependencies that are external to webpack and will be provided by System - const systemDependencies = JSON.stringify( - externals.map(m => - typeof m.request === "object" && !Array.isArray(m.request) - ? m.request.amd - : m.request - ) - ); + let stringSuffix = null; + let hasUnknownParams = false; + const innerExpressions = []; + for (let i = expr.arguments.length - 1; i >= 0; i--) { + const arg = expr.arguments[i]; + if (arg.type === "SpreadElement") return; + const argExpr = this.evaluateExpression(arg); + if ( + hasUnknownParams || + (!argExpr.isString() && !argExpr.isNumber()) + ) { + hasUnknownParams = true; + innerExpressions.push(argExpr); + continue; + } - // The name of the variable provided by System for exporting - const dynamicExport = "__WEBPACK_DYNAMIC_EXPORT__"; + const value = argExpr.isString() + ? argExpr.string + : "" + argExpr.number; - // An array of the internal variable names for the webpack externals - const externalWebpackNames = externals.map( - m => - `__WEBPACK_EXTERNAL_MODULE_${Template.toIdentifier( - `${chunkGraph.getModuleId(m)}` - )}__` - ); + const newString = value + (stringSuffix ? stringSuffix.string : ""); + const newRange = [ + argExpr.range[0], + (stringSuffix || argExpr).range[1] + ]; + stringSuffix = new BasicEvaluatedExpression() + .setString(newString) + .setSideEffects( + (stringSuffix && stringSuffix.couldHaveSideEffects()) || + argExpr.couldHaveSideEffects() + ) + .setRange(newRange); + } - // Declaring variables for the internal variable names for the webpack externals - const externalVarDeclarations = externalWebpackNames - .map(name => `var ${name} = {};`) - .join("\n"); + if (hasUnknownParams) { + const prefix = param.isString() ? param : param.prefix; + const inner = + param.isWrapped() && param.wrappedInnerExpressions + ? param.wrappedInnerExpressions.concat(innerExpressions.reverse()) + : innerExpressions.reverse(); + return new BasicEvaluatedExpression() + .setWrapped(prefix, stringSuffix, inner) + .setRange(expr.range); + } else if (param.isWrapped()) { + const postfix = stringSuffix || param.postfix; + const inner = param.wrappedInnerExpressions + ? param.wrappedInnerExpressions.concat(innerExpressions.reverse()) + : innerExpressions.reverse(); + return new BasicEvaluatedExpression() + .setWrapped(param.prefix, postfix, inner) + .setRange(expr.range); + } else { + const newString = + param.string + (stringSuffix ? stringSuffix.string : ""); + return new BasicEvaluatedExpression() + .setString(newString) + .setSideEffects( + (stringSuffix && stringSuffix.couldHaveSideEffects()) || + param.couldHaveSideEffects() + ) + .setRange(expr.range); + } + }); + this.hooks.evaluateCallExpressionMember + .for("split") + .tap("JavascriptParser", (expr, param) => { + if (!param.isString()) return; + if (expr.arguments.length !== 1) return; + if (expr.arguments[0].type === "SpreadElement") return; + let result; + const arg = this.evaluateExpression(expr.arguments[0]); + if (arg.isString()) { + result = param.string.split(arg.string); + } else if (arg.isRegExp()) { + result = param.string.split(arg.regExp); + } else { + return; + } + return new BasicEvaluatedExpression() + .setArray(result) + .setSideEffects(param.couldHaveSideEffects()) + .setRange(expr.range); + }); + this.hooks.evaluate + .for("ConditionalExpression") + .tap("JavascriptParser", _expr => { + const expr = /** @type {ConditionalExpressionNode} */ (_expr); - // Define __esModule flag on all internal variables and helpers - const externalVarInitialization = []; + const condition = this.evaluateExpression(expr.test); + const conditionValue = condition.asBool(); + let res; + if (conditionValue === undefined) { + const consequent = this.evaluateExpression(expr.consequent); + const alternate = this.evaluateExpression(expr.alternate); + if (!consequent || !alternate) return; + res = new BasicEvaluatedExpression(); + if (consequent.isConditional()) { + res.setOptions(consequent.options); + } else { + res.setOptions([consequent]); + } + if (alternate.isConditional()) { + res.addOptions(alternate.options); + } else { + res.addOptions([alternate]); + } + } else { + res = this.evaluateExpression( + conditionValue ? expr.consequent : expr.alternate + ); + if (condition.couldHaveSideEffects()) res.setSideEffects(); + } + res.setRange(expr.range); + return res; + }); + this.hooks.evaluate + .for("ArrayExpression") + .tap("JavascriptParser", _expr => { + const expr = /** @type {ArrayExpressionNode} */ (_expr); - // The system.register format requires an array of setter functions for externals. - const setters = - externalWebpackNames.length === 0 - ? "" - : Template.asString([ - "setters: [", - Template.indent( - externals - .map((module, i) => { - const external = externalWebpackNames[i]; - const exportsInfo = moduleGraph.getExportsInfo(module); - const otherUnused = - exportsInfo.otherExportsInfo.getUsed(chunk.runtime) === - UsageState.Unused; - const instructions = []; - const handledNames = []; - for (const exportInfo of exportsInfo.orderedExports) { - const used = exportInfo.getUsedName( - undefined, - chunk.runtime - ); - if (used) { - if (otherUnused || used !== exportInfo.name) { - instructions.push( - `${external}${propertyAccess([ - used - ])} = module${propertyAccess([exportInfo.name])};` - ); - handledNames.push(exportInfo.name); - } - } else { - handledNames.push(exportInfo.name); - } - } - if (!otherUnused) { - if ( - !Array.isArray(module.request) || - module.request.length === 1 - ) { - externalVarInitialization.push( - `Object.defineProperty(${external}, "__esModule", { value: true });` - ); - } - if (handledNames.length > 0) { - const name = `${external}handledNames`; - externalVarInitialization.push( - `var ${name} = ${JSON.stringify(handledNames)};` - ); - instructions.push( - Template.asString([ - "Object.keys(module).forEach(function(key) {", - Template.indent([ - `if(${name}.indexOf(key) >= 0)`, - Template.indent(`${external}[key] = module[key];`) - ]), - "});" - ]) - ); - } else { - instructions.push( - Template.asString([ - "Object.keys(module).forEach(function(key) {", - Template.indent([`${external}[key] = module[key];`]), - "});" - ]) - ); - } - } - if (instructions.length === 0) return "function() {}"; - return Template.asString([ - "function(module) {", - Template.indent(instructions), - "}" - ]); - }) - .join(",\n") - ), - "]," - ]); + const items = expr.elements.map(element => { + return ( + element !== null && + element.type !== "SpreadElement" && + this.evaluateExpression(element) + ); + }); + if (!items.every(Boolean)) return; + return new BasicEvaluatedExpression() + .setItems(items) + .setRange(expr.range); + }); + this.hooks.evaluate + .for("ChainExpression") + .tap("JavascriptParser", _expr => { + const expr = /** @type {ChainExpressionNode} */ (_expr); + /** @type {ExpressionNode[]} */ + const optionalExpressionsStack = []; + /** @type {ExpressionNode|SuperNode} */ + let next = expr.expression; - return new ConcatSource( - Template.asString([ - `System.register(${name}${systemDependencies}, function(${dynamicExport}, __system_context__) {`, - Template.indent([ - externalVarDeclarations, - Template.asString(externalVarInitialization), - "return {", - Template.indent([ - setters, - "execute: function() {", - Template.indent(`${dynamicExport}(`) - ]) - ]), - "" - ]), - source, - Template.asString([ - "", - Template.indent([ - Template.indent([Template.indent([");"]), "}"]), - "};" - ]), - "})" - ]) - ); + while ( + next.type === "MemberExpression" || + next.type === "CallExpression" + ) { + if (next.type === "MemberExpression") { + if (next.optional) { + // SuperNode can not be optional + optionalExpressionsStack.push( + /** @type {ExpressionNode} */ (next.object) + ); + } + next = next.object; + } else { + if (next.optional) { + // SuperNode can not be optional + optionalExpressionsStack.push( + /** @type {ExpressionNode} */ (next.callee) + ); + } + next = next.callee; + } + } + + while (optionalExpressionsStack.length > 0) { + const expression = optionalExpressionsStack.pop(); + const evaluated = this.evaluateExpression(expression); + + if (evaluated && evaluated.asNullish()) { + return evaluated.setRange(_expr.range); + } + } + return this.evaluateExpression(expr.expression); + }); + } + + getRenameIdentifier(expr) { + const result = this.evaluateExpression(expr); + if (result && result.isIdentifier()) { + return result.identifier; + } } /** - * @param {Chunk} chunk the chunk - * @param {Hash} hash hash - * @param {ChunkHashContext} chunkHashContext chunk hash context - * @param {LibraryContext} libraryContext context + * @param {ClassExpressionNode | ClassDeclarationNode} classy a class node * @returns {void} */ - chunkHash(chunk, hash, chunkHashContext, { options, compilation }) { - hash.update("SystemLibraryPlugin"); - if (options.name) { - hash.update(compilation.getPath(options.name, { chunk })); + walkClass(classy) { + if (classy.superClass) { + if (!this.hooks.classExtendsExpression.call(classy.superClass, classy)) { + this.walkExpression(classy.superClass); + } + } + if (classy.body && classy.body.type === "ClassBody") { + for (const classElement of /** @type {TODO} */ (classy.body.body)) { + if (!this.hooks.classBodyElement.call(classElement, classy)) { + if (classElement.computed && classElement.key) { + this.walkExpression(classElement.key); + } + if (classElement.value) { + if ( + !this.hooks.classBodyValue.call( + classElement.value, + classElement, + classy + ) + ) { + const wasTopLevel = this.scope.topLevelScope; + this.scope.topLevelScope = false; + this.walkExpression(classElement.value); + this.scope.topLevelScope = wasTopLevel; + } + } + } + } } } -} - -module.exports = SystemLibraryPlugin; - - -/***/ }), - -/***/ 59401: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ - + // Pre walking iterates the scope for variable declarations + preWalkStatements(statements) { + for (let index = 0, len = statements.length; index < len; index++) { + const statement = statements[index]; + this.preWalkStatement(statement); + } + } -const { ConcatSource, OriginalSource } = __webpack_require__(96192); -const ExternalModule = __webpack_require__(89805); -const Template = __webpack_require__(92066); -const AbstractLibraryPlugin = __webpack_require__(94051); - -/** @typedef {import("webpack-sources").Source} Source */ -/** @typedef {import("../../declarations/WebpackOptions").LibraryCustomUmdCommentObject} LibraryCustomUmdCommentObject */ -/** @typedef {import("../../declarations/WebpackOptions").LibraryCustomUmdObject} LibraryCustomUmdObject */ -/** @typedef {import("../../declarations/WebpackOptions").LibraryName} LibraryName */ -/** @typedef {import("../../declarations/WebpackOptions").LibraryOptions} LibraryOptions */ -/** @typedef {import("../../declarations/WebpackOptions").LibraryType} LibraryType */ -/** @typedef {import("../Compiler")} Compiler */ -/** @typedef {import("../javascript/JavascriptModulesPlugin").RenderContext} RenderContext */ -/** @typedef {import("../util/Hash")} Hash */ -/** @template T @typedef {import("./AbstractLibraryPlugin").LibraryContext} LibraryContext */ - -/** - * @param {string[]} accessor the accessor to convert to path - * @returns {string} the path - */ -const accessorToObjectAccess = accessor => { - return accessor.map(a => `[${JSON.stringify(a)}]`).join(""); -}; + // Block pre walking iterates the scope for block variable declarations + blockPreWalkStatements(statements) { + for (let index = 0, len = statements.length; index < len; index++) { + const statement = statements[index]; + this.blockPreWalkStatement(statement); + } + } -/** - * @param {string|undefined} base the path prefix - * @param {string|string[]} accessor the accessor - * @param {string=} joinWith the element separator - * @returns {string} the path - */ -const accessorAccess = (base, accessor, joinWith = ", ") => { - const accessors = Array.isArray(accessor) ? accessor : [accessor]; - return accessors - .map((_, idx) => { - const a = base - ? base + accessorToObjectAccess(accessors.slice(0, idx + 1)) - : accessors[0] + accessorToObjectAccess(accessors.slice(1, idx + 1)); - if (idx === accessors.length - 1) return a; - if (idx === 0 && base === undefined) - return `${a} = typeof ${a} === "object" ? ${a} : {}`; - return `${a} = ${a} || {}`; - }) - .join(joinWith); -}; + // Walking iterates the statements and expressions and processes them + walkStatements(statements) { + for (let index = 0, len = statements.length; index < len; index++) { + const statement = statements[index]; + this.walkStatement(statement); + } + } -/** @typedef {string | string[] | LibraryCustomUmdObject} UmdLibraryPluginName */ + preWalkStatement(statement) { + this.statementPath.push(statement); + if (this.hooks.preStatement.call(statement)) { + this.prevStatement = this.statementPath.pop(); + return; + } + switch (statement.type) { + case "BlockStatement": + this.preWalkBlockStatement(statement); + break; + case "DoWhileStatement": + this.preWalkDoWhileStatement(statement); + break; + case "ForInStatement": + this.preWalkForInStatement(statement); + break; + case "ForOfStatement": + this.preWalkForOfStatement(statement); + break; + case "ForStatement": + this.preWalkForStatement(statement); + break; + case "FunctionDeclaration": + this.preWalkFunctionDeclaration(statement); + break; + case "IfStatement": + this.preWalkIfStatement(statement); + break; + case "LabeledStatement": + this.preWalkLabeledStatement(statement); + break; + case "SwitchStatement": + this.preWalkSwitchStatement(statement); + break; + case "TryStatement": + this.preWalkTryStatement(statement); + break; + case "VariableDeclaration": + this.preWalkVariableDeclaration(statement); + break; + case "WhileStatement": + this.preWalkWhileStatement(statement); + break; + case "WithStatement": + this.preWalkWithStatement(statement); + break; + } + this.prevStatement = this.statementPath.pop(); + } -/** - * @typedef {Object} UmdLibraryPluginOptions - * @property {LibraryType} type - * @property {boolean=} optionalAmdExternalAsGlobal - */ + blockPreWalkStatement(statement) { + this.statementPath.push(statement); + if (this.hooks.blockPreStatement.call(statement)) { + this.prevStatement = this.statementPath.pop(); + return; + } + switch (statement.type) { + case "ImportDeclaration": + this.blockPreWalkImportDeclaration(statement); + break; + case "ExportAllDeclaration": + this.blockPreWalkExportAllDeclaration(statement); + break; + case "ExportDefaultDeclaration": + this.blockPreWalkExportDefaultDeclaration(statement); + break; + case "ExportNamedDeclaration": + this.blockPreWalkExportNamedDeclaration(statement); + break; + case "VariableDeclaration": + this.blockPreWalkVariableDeclaration(statement); + break; + case "ClassDeclaration": + this.blockPreWalkClassDeclaration(statement); + break; + } + this.prevStatement = this.statementPath.pop(); + } -/** - * @typedef {Object} UmdLibraryPluginParsed - * @property {string | string[]} name - * @property {LibraryCustomUmdObject} names - * @property {string | LibraryCustomUmdCommentObject} auxiliaryComment - * @property {boolean} namedDefine - */ + walkStatement(statement) { + this.statementPath.push(statement); + if (this.hooks.statement.call(statement) !== undefined) { + this.prevStatement = this.statementPath.pop(); + return; + } + switch (statement.type) { + case "BlockStatement": + this.walkBlockStatement(statement); + break; + case "ClassDeclaration": + this.walkClassDeclaration(statement); + break; + case "DoWhileStatement": + this.walkDoWhileStatement(statement); + break; + case "ExportDefaultDeclaration": + this.walkExportDefaultDeclaration(statement); + break; + case "ExportNamedDeclaration": + this.walkExportNamedDeclaration(statement); + break; + case "ExpressionStatement": + this.walkExpressionStatement(statement); + break; + case "ForInStatement": + this.walkForInStatement(statement); + break; + case "ForOfStatement": + this.walkForOfStatement(statement); + break; + case "ForStatement": + this.walkForStatement(statement); + break; + case "FunctionDeclaration": + this.walkFunctionDeclaration(statement); + break; + case "IfStatement": + this.walkIfStatement(statement); + break; + case "LabeledStatement": + this.walkLabeledStatement(statement); + break; + case "ReturnStatement": + this.walkReturnStatement(statement); + break; + case "SwitchStatement": + this.walkSwitchStatement(statement); + break; + case "ThrowStatement": + this.walkThrowStatement(statement); + break; + case "TryStatement": + this.walkTryStatement(statement); + break; + case "VariableDeclaration": + this.walkVariableDeclaration(statement); + break; + case "WhileStatement": + this.walkWhileStatement(statement); + break; + case "WithStatement": + this.walkWithStatement(statement); + break; + } + this.prevStatement = this.statementPath.pop(); + } -/** - * @typedef {UmdLibraryPluginParsed} T - * @extends {AbstractLibraryPlugin} - */ -class UmdLibraryPlugin extends AbstractLibraryPlugin { /** - * @param {UmdLibraryPluginOptions} options the plugin option + * Walks a statements that is nested within a parent statement + * and can potentially be a non-block statement. + * This enforces the nested statement to never be in ASI position. + * @param {StatementNode} statement the nested statement + * @returns {void} */ - constructor(options) { - super({ - pluginName: "UmdLibraryPlugin", - type: options.type + walkNestedStatement(statement) { + this.prevStatement = undefined; + this.walkStatement(statement); + } + + // Real Statements + preWalkBlockStatement(statement) { + this.preWalkStatements(statement.body); + } + + walkBlockStatement(statement) { + this.inBlockScope(() => { + const body = statement.body; + const prev = this.prevStatement; + this.blockPreWalkStatements(body); + this.prevStatement = prev; + this.walkStatements(body); }); + } - this.optionalAmdExternalAsGlobal = options.optionalAmdExternalAsGlobal; + walkExpressionStatement(statement) { + this.walkExpression(statement.expression); } - /** - * @param {LibraryOptions} library normalized library option - * @returns {T | false} preprocess as needed by overriding - */ - parseOptions(library) { - /** @type {LibraryName} */ - let name; - /** @type {LibraryCustomUmdObject} */ - let names; - if (typeof library.name === "object" && !Array.isArray(library.name)) { - name = library.name.root || library.name.amd || library.name.commonjs; - names = library.name; - } else { - name = library.name; - const singleName = Array.isArray(name) ? name[0] : name; - names = { - commonjs: singleName, - root: library.name, - amd: singleName - }; + preWalkIfStatement(statement) { + this.preWalkStatement(statement.consequent); + if (statement.alternate) { + this.preWalkStatement(statement.alternate); } - return { - name, - names, - auxiliaryComment: library.auxiliaryComment, - namedDefine: library.umdNamedDefine - }; } - /** - * @param {Source} source source - * @param {RenderContext} renderContext render context - * @param {LibraryContext} libraryContext context - * @returns {Source} source with library export - */ - render( - source, - { chunkGraph, runtimeTemplate, chunk, moduleGraph }, - { options, compilation } - ) { - const modules = chunkGraph - .getChunkModules(chunk) - .filter( - m => - m instanceof ExternalModule && - (m.externalType === "umd" || m.externalType === "umd2") - ); - let externals = /** @type {ExternalModule[]} */ (modules); - /** @type {ExternalModule[]} */ - const optionalExternals = []; - /** @type {ExternalModule[]} */ - let requiredExternals = []; - if (this.optionalAmdExternalAsGlobal) { - for (const m of externals) { - if (m.isOptional(moduleGraph)) { - optionalExternals.push(m); - } else { - requiredExternals.push(m); - } + walkIfStatement(statement) { + const result = this.hooks.statementIf.call(statement); + if (result === undefined) { + this.walkExpression(statement.test); + this.walkNestedStatement(statement.consequent); + if (statement.alternate) { + this.walkNestedStatement(statement.alternate); } - externals = requiredExternals.concat(optionalExternals); } else { - requiredExternals = externals; + if (result) { + this.walkNestedStatement(statement.consequent); + } else if (statement.alternate) { + this.walkNestedStatement(statement.alternate); + } } + } - const replaceKeys = str => { - return compilation.getPath(str, { - chunk - }); - }; + preWalkLabeledStatement(statement) { + this.preWalkStatement(statement.body); + } - const externalsDepsArray = modules => { - return `[${replaceKeys( - modules - .map(m => - JSON.stringify( - typeof m.request === "object" ? m.request.amd : m.request - ) - ) - .join(", ") - )}]`; - }; + walkLabeledStatement(statement) { + const hook = this.hooks.label.get(statement.label.name); + if (hook !== undefined) { + const result = hook.call(statement); + if (result === true) return; + } + this.walkNestedStatement(statement.body); + } - const externalsRootArray = modules => { - return replaceKeys( - modules - .map(m => { - let request = m.request; - if (typeof request === "object") request = request.root; - return `root${accessorToObjectAccess([].concat(request))}`; - }) - .join(", ") - ); - }; + preWalkWithStatement(statement) { + this.preWalkStatement(statement.body); + } - const externalsRequireArray = type => { - return replaceKeys( - externals - .map(m => { - let expr; - let request = m.request; - if (typeof request === "object") { - request = request[type]; - } - if (request === undefined) { - throw new Error( - "Missing external configuration for type:" + type - ); - } - if (Array.isArray(request)) { - expr = `require(${JSON.stringify( - request[0] - )})${accessorToObjectAccess(request.slice(1))}`; - } else { - expr = `require(${JSON.stringify(request)})`; - } - if (m.isOptional(moduleGraph)) { - expr = `(function webpackLoadOptionalExternalModule() { try { return ${expr}; } catch(e) {} }())`; - } - return expr; - }) - .join(", ") - ); - }; + walkWithStatement(statement) { + this.walkExpression(statement.object); + this.walkNestedStatement(statement.body); + } - const externalsArguments = modules => { - return modules - .map( - m => - `__WEBPACK_EXTERNAL_MODULE_${Template.toIdentifier( - `${chunkGraph.getModuleId(m)}` - )}__` - ) - .join(", "); - }; + preWalkSwitchStatement(statement) { + this.preWalkSwitchCases(statement.cases); + } + + walkSwitchStatement(statement) { + this.walkExpression(statement.discriminant); + this.walkSwitchCases(statement.cases); + } + + walkTerminatingStatement(statement) { + if (statement.argument) this.walkExpression(statement.argument); + } + + walkReturnStatement(statement) { + this.walkTerminatingStatement(statement); + } - const libraryName = library => { - return JSON.stringify(replaceKeys([].concat(library).pop())); - }; + walkThrowStatement(statement) { + this.walkTerminatingStatement(statement); + } - let amdFactory; - if (optionalExternals.length > 0) { - const wrapperArguments = externalsArguments(requiredExternals); - const factoryArguments = - requiredExternals.length > 0 - ? externalsArguments(requiredExternals) + - ", " + - externalsRootArray(optionalExternals) - : externalsRootArray(optionalExternals); - amdFactory = - `function webpackLoadOptionalExternalModuleAmd(${wrapperArguments}) {\n` + - ` return factory(${factoryArguments});\n` + - " }"; + preWalkTryStatement(statement) { + this.preWalkStatement(statement.block); + if (statement.handler) this.preWalkCatchClause(statement.handler); + if (statement.finializer) this.preWalkStatement(statement.finializer); + } + + walkTryStatement(statement) { + if (this.scope.inTry) { + this.walkStatement(statement.block); } else { - amdFactory = "factory"; + this.scope.inTry = true; + this.walkStatement(statement.block); + this.scope.inTry = false; } + if (statement.handler) this.walkCatchClause(statement.handler); + if (statement.finalizer) this.walkStatement(statement.finalizer); + } - const { auxiliaryComment, namedDefine, names } = options; + preWalkWhileStatement(statement) { + this.preWalkStatement(statement.body); + } - const getAuxiliaryComment = type => { - if (auxiliaryComment) { - if (typeof auxiliaryComment === "string") - return "\t//" + auxiliaryComment + "\n"; - if (auxiliaryComment[type]) - return "\t//" + auxiliaryComment[type] + "\n"; - } - return ""; - }; + walkWhileStatement(statement) { + this.walkExpression(statement.test); + this.walkNestedStatement(statement.body); + } - return new ConcatSource( - new OriginalSource( - "(function webpackUniversalModuleDefinition(root, factory) {\n" + - getAuxiliaryComment("commonjs2") + - " if(typeof exports === 'object' && typeof module === 'object')\n" + - " module.exports = factory(" + - externalsRequireArray("commonjs2") + - ");\n" + - getAuxiliaryComment("amd") + - " else if(typeof define === 'function' && define.amd)\n" + - (requiredExternals.length > 0 - ? names.amd && namedDefine === true - ? " define(" + - libraryName(names.amd) + - ", " + - externalsDepsArray(requiredExternals) + - ", " + - amdFactory + - ");\n" - : " define(" + - externalsDepsArray(requiredExternals) + - ", " + - amdFactory + - ");\n" - : names.amd && namedDefine === true - ? " define(" + - libraryName(names.amd) + - ", [], " + - amdFactory + - ");\n" - : " define([], " + amdFactory + ");\n") + - (names.root || names.commonjs - ? getAuxiliaryComment("commonjs") + - " else if(typeof exports === 'object')\n" + - " exports[" + - libraryName(names.commonjs || names.root) + - "] = factory(" + - externalsRequireArray("commonjs") + - ");\n" + - getAuxiliaryComment("root") + - " else\n" + - " " + - replaceKeys( - accessorAccess("root", names.root || names.commonjs) - ) + - " = factory(" + - externalsRootArray(externals) + - ");\n" - : " else {\n" + - (externals.length > 0 - ? " var a = typeof exports === 'object' ? factory(" + - externalsRequireArray("commonjs") + - ") : factory(" + - externalsRootArray(externals) + - ");\n" - : " var a = factory();\n") + - " for(var i in a) (typeof exports === 'object' ? exports : root)[i] = a[i];\n" + - " }\n") + - `})(${ - runtimeTemplate.outputOptions.globalObject - }, function(${externalsArguments(externals)}) {\nreturn `, - "webpack/universalModuleDefinition" - ), - source, - ";\n})" - ); + preWalkDoWhileStatement(statement) { + this.preWalkStatement(statement.body); } -} -module.exports = UmdLibraryPlugin; + walkDoWhileStatement(statement) { + this.walkNestedStatement(statement.body); + this.walkExpression(statement.test); + } + preWalkForStatement(statement) { + if (statement.init) { + if (statement.init.type === "VariableDeclaration") { + this.preWalkStatement(statement.init); + } + } + this.preWalkStatement(statement.body); + } -/***/ }), + walkForStatement(statement) { + this.inBlockScope(() => { + if (statement.init) { + if (statement.init.type === "VariableDeclaration") { + this.blockPreWalkVariableDeclaration(statement.init); + this.prevStatement = undefined; + this.walkStatement(statement.init); + } else { + this.walkExpression(statement.init); + } + } + if (statement.test) { + this.walkExpression(statement.test); + } + if (statement.update) { + this.walkExpression(statement.update); + } + const body = statement.body; + if (body.type === "BlockStatement") { + // no need to add additional scope + const prev = this.prevStatement; + this.blockPreWalkStatements(body.body); + this.prevStatement = prev; + this.walkStatements(body.body); + } else { + this.walkNestedStatement(body); + } + }); + } -/***/ 54667: -/***/ (function(__unused_webpack_module, exports) { + preWalkForInStatement(statement) { + if (statement.left.type === "VariableDeclaration") { + this.preWalkVariableDeclaration(statement.left); + } + this.preWalkStatement(statement.body); + } -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ + walkForInStatement(statement) { + this.inBlockScope(() => { + if (statement.left.type === "VariableDeclaration") { + this.blockPreWalkVariableDeclaration(statement.left); + this.walkVariableDeclaration(statement.left); + } else { + this.walkPattern(statement.left); + } + this.walkExpression(statement.right); + const body = statement.body; + if (body.type === "BlockStatement") { + // no need to add additional scope + const prev = this.prevStatement; + this.blockPreWalkStatements(body.body); + this.prevStatement = prev; + this.walkStatements(body.body); + } else { + this.walkNestedStatement(body); + } + }); + } + preWalkForOfStatement(statement) { + if (statement.await && this.scope.topLevelScope === true) { + this.hooks.topLevelAwait.call(statement); + } + if (statement.left.type === "VariableDeclaration") { + this.preWalkVariableDeclaration(statement.left); + } + this.preWalkStatement(statement.body); + } + walkForOfStatement(statement) { + this.inBlockScope(() => { + if (statement.left.type === "VariableDeclaration") { + this.blockPreWalkVariableDeclaration(statement.left); + this.walkVariableDeclaration(statement.left); + } else { + this.walkPattern(statement.left); + } + this.walkExpression(statement.right); + const body = statement.body; + if (body.type === "BlockStatement") { + // no need to add additional scope + const prev = this.prevStatement; + this.blockPreWalkStatements(body.body); + this.prevStatement = prev; + this.walkStatements(body.body); + } else { + this.walkNestedStatement(body); + } + }); + } -const LogType = Object.freeze({ - error: /** @type {"error"} */ ("error"), // message, c style arguments - warn: /** @type {"warn"} */ ("warn"), // message, c style arguments - info: /** @type {"info"} */ ("info"), // message, c style arguments - log: /** @type {"log"} */ ("log"), // message, c style arguments - debug: /** @type {"debug"} */ ("debug"), // message, c style arguments + // Declarations + preWalkFunctionDeclaration(statement) { + if (statement.id) { + this.defineVariable(statement.id.name); + } + } - trace: /** @type {"trace"} */ ("trace"), // no arguments + walkFunctionDeclaration(statement) { + const wasTopLevel = this.scope.topLevelScope; + this.scope.topLevelScope = false; + this.inFunctionScope(true, statement.params, () => { + for (const param of statement.params) { + this.walkPattern(param); + } + if (statement.body.type === "BlockStatement") { + this.detectMode(statement.body.body); + const prev = this.prevStatement; + this.preWalkStatement(statement.body); + this.prevStatement = prev; + this.walkStatement(statement.body); + } else { + this.walkExpression(statement.body); + } + }); + this.scope.topLevelScope = wasTopLevel; + } - group: /** @type {"group"} */ ("group"), // [label] - groupCollapsed: /** @type {"groupCollapsed"} */ ("groupCollapsed"), // [label] - groupEnd: /** @type {"groupEnd"} */ ("groupEnd"), // [label] + blockPreWalkImportDeclaration(statement) { + const source = statement.source.value; + this.hooks.import.call(statement, source); + for (const specifier of statement.specifiers) { + const name = specifier.local.name; + switch (specifier.type) { + case "ImportDefaultSpecifier": + if ( + !this.hooks.importSpecifier.call(statement, source, "default", name) + ) { + this.defineVariable(name); + } + break; + case "ImportSpecifier": + if ( + !this.hooks.importSpecifier.call( + statement, + source, + specifier.imported.name, + name + ) + ) { + this.defineVariable(name); + } + break; + case "ImportNamespaceSpecifier": + if (!this.hooks.importSpecifier.call(statement, source, null, name)) { + this.defineVariable(name); + } + break; + default: + this.defineVariable(name); + } + } + } - profile: /** @type {"profile"} */ ("profile"), // [profileName] - profileEnd: /** @type {"profileEnd"} */ ("profileEnd"), // [profileName] + enterDeclaration(declaration, onIdent) { + switch (declaration.type) { + case "VariableDeclaration": + for (const declarator of declaration.declarations) { + switch (declarator.type) { + case "VariableDeclarator": { + this.enterPattern(declarator.id, onIdent); + break; + } + } + } + break; + case "FunctionDeclaration": + this.enterPattern(declaration.id, onIdent); + break; + case "ClassDeclaration": + this.enterPattern(declaration.id, onIdent); + break; + } + } - time: /** @type {"time"} */ ("time"), // name, time as [seconds, nanoseconds] + blockPreWalkExportNamedDeclaration(statement) { + let source; + if (statement.source) { + source = statement.source.value; + this.hooks.exportImport.call(statement, source); + } else { + this.hooks.export.call(statement); + } + if (statement.declaration) { + if ( + !this.hooks.exportDeclaration.call(statement, statement.declaration) + ) { + const prev = this.prevStatement; + this.preWalkStatement(statement.declaration); + this.prevStatement = prev; + this.blockPreWalkStatement(statement.declaration); + let index = 0; + this.enterDeclaration(statement.declaration, def => { + this.hooks.exportSpecifier.call(statement, def, def, index++); + }); + } + } + if (statement.specifiers) { + for ( + let specifierIndex = 0; + specifierIndex < statement.specifiers.length; + specifierIndex++ + ) { + const specifier = statement.specifiers[specifierIndex]; + switch (specifier.type) { + case "ExportSpecifier": { + const name = specifier.exported.name; + if (source) { + this.hooks.exportImportSpecifier.call( + statement, + source, + specifier.local.name, + name, + specifierIndex + ); + } else { + this.hooks.exportSpecifier.call( + statement, + specifier.local.name, + name, + specifierIndex + ); + } + break; + } + } + } + } + } - clear: /** @type {"clear"} */ ("clear"), // no arguments - status: /** @type {"status"} */ ("status") // message, arguments -}); + walkExportNamedDeclaration(statement) { + if (statement.declaration) { + this.walkStatement(statement.declaration); + } + } -exports.LogType = LogType; + blockPreWalkExportDefaultDeclaration(statement) { + const prev = this.prevStatement; + this.preWalkStatement(statement.declaration); + this.prevStatement = prev; + this.blockPreWalkStatement(statement.declaration); + if ( + statement.declaration.id && + statement.declaration.type !== "FunctionExpression" && + statement.declaration.type !== "ClassExpression" + ) { + this.hooks.exportSpecifier.call( + statement, + statement.declaration.id.name, + "default", + undefined + ); + } + } -/** @typedef {typeof LogType[keyof typeof LogType]} LogTypeEnum */ + walkExportDefaultDeclaration(statement) { + this.hooks.export.call(statement); + if ( + statement.declaration.id && + statement.declaration.type !== "FunctionExpression" && + statement.declaration.type !== "ClassExpression" + ) { + if ( + !this.hooks.exportDeclaration.call(statement, statement.declaration) + ) { + this.walkStatement(statement.declaration); + } + } else { + // Acorn parses `export default function() {}` as `FunctionDeclaration` and + // `export default class {}` as `ClassDeclaration`, both with `id = null`. + // These nodes must be treated as expressions. + if ( + statement.declaration.type === "FunctionDeclaration" || + statement.declaration.type === "ClassDeclaration" + ) { + this.walkStatement(statement.declaration); + } else { + this.walkExpression(statement.declaration); + } + if (!this.hooks.exportExpression.call(statement, statement.declaration)) { + this.hooks.exportSpecifier.call( + statement, + statement.declaration, + "default", + undefined + ); + } + } + } -const LOG_SYMBOL = Symbol("webpack logger raw log method"); -const TIMERS_SYMBOL = Symbol("webpack logger times"); -const TIMERS_AGGREGATES_SYMBOL = Symbol("webpack logger aggregated times"); + blockPreWalkExportAllDeclaration(statement) { + const source = statement.source.value; + const name = statement.exported ? statement.exported.name : null; + this.hooks.exportImport.call(statement, source); + this.hooks.exportImportSpecifier.call(statement, source, null, name, 0); + } -class WebpackLogger { - /** - * @param {function(LogTypeEnum, any[]=): void} log log function - * @param {function(string | function(): string): WebpackLogger} getChildLogger function to create child logger - */ - constructor(log, getChildLogger) { - this[LOG_SYMBOL] = log; - this.getChildLogger = getChildLogger; + preWalkVariableDeclaration(statement) { + if (statement.kind !== "var") return; + this._preWalkVariableDeclaration(statement, this.hooks.varDeclarationVar); } - error(...args) { - this[LOG_SYMBOL](LogType.error, args); + blockPreWalkVariableDeclaration(statement) { + if (statement.kind === "var") return; + const hookMap = + statement.kind === "const" + ? this.hooks.varDeclarationConst + : this.hooks.varDeclarationLet; + this._preWalkVariableDeclaration(statement, hookMap); } - warn(...args) { - this[LOG_SYMBOL](LogType.warn, args); + _preWalkVariableDeclaration(statement, hookMap) { + for (const declarator of statement.declarations) { + switch (declarator.type) { + case "VariableDeclarator": { + if (!this.hooks.preDeclarator.call(declarator, statement)) { + this.enterPattern(declarator.id, (name, decl) => { + let hook = hookMap.get(name); + if (hook === undefined || !hook.call(decl)) { + hook = this.hooks.varDeclaration.get(name); + if (hook === undefined || !hook.call(decl)) { + this.defineVariable(name); + } + } + }); + } + break; + } + } + } } - info(...args) { - this[LOG_SYMBOL](LogType.info, args); + walkVariableDeclaration(statement) { + for (const declarator of statement.declarations) { + switch (declarator.type) { + case "VariableDeclarator": { + const renameIdentifier = + declarator.init && this.getRenameIdentifier(declarator.init); + if (renameIdentifier && declarator.id.type === "Identifier") { + const hook = this.hooks.canRename.get(renameIdentifier); + if (hook !== undefined && hook.call(declarator.init)) { + // renaming with "var a = b;" + const hook = this.hooks.rename.get(renameIdentifier); + if (hook === undefined || !hook.call(declarator.init)) { + this.setVariable(declarator.id.name, renameIdentifier); + } + break; + } + } + if (!this.hooks.declarator.call(declarator, statement)) { + this.walkPattern(declarator.id); + if (declarator.init) this.walkExpression(declarator.init); + } + break; + } + } + } } - log(...args) { - this[LOG_SYMBOL](LogType.log, args); + blockPreWalkClassDeclaration(statement) { + if (statement.id) { + this.defineVariable(statement.id.name); + } } - debug(...args) { - this[LOG_SYMBOL](LogType.debug, args); + walkClassDeclaration(statement) { + this.walkClass(statement); } - assert(assertion, ...args) { - if (!assertion) { - this[LOG_SYMBOL](LogType.error, args); + preWalkSwitchCases(switchCases) { + for (let index = 0, len = switchCases.length; index < len; index++) { + const switchCase = switchCases[index]; + this.preWalkStatements(switchCase.consequent); } } - trace() { - this[LOG_SYMBOL](LogType.trace, ["Trace"]); - } + walkSwitchCases(switchCases) { + this.inBlockScope(() => { + const len = switchCases.length; - clear() { - this[LOG_SYMBOL](LogType.clear); - } + // we need to pre walk all statements first since we can have invalid code + // import A from "module"; + // switch(1) { + // case 1: + // console.log(A); // should fail at runtime + // case 2: + // const A = 1; + // } + for (let index = 0; index < len; index++) { + const switchCase = switchCases[index]; - status(...args) { - this[LOG_SYMBOL](LogType.status, args); - } + if (switchCase.consequent.length > 0) { + const prev = this.prevStatement; + this.blockPreWalkStatements(switchCase.consequent); + this.prevStatement = prev; + } + } - group(...args) { - this[LOG_SYMBOL](LogType.group, args); - } + for (let index = 0; index < len; index++) { + const switchCase = switchCases[index]; - groupCollapsed(...args) { - this[LOG_SYMBOL](LogType.groupCollapsed, args); + if (switchCase.test) { + this.walkExpression(switchCase.test); + } + if (switchCase.consequent.length > 0) { + this.walkStatements(switchCase.consequent); + } + } + }); } - groupEnd(...args) { - this[LOG_SYMBOL](LogType.groupEnd, args); + preWalkCatchClause(catchClause) { + this.preWalkStatement(catchClause.body); } - profile(label) { - this[LOG_SYMBOL](LogType.profile, [label]); + walkCatchClause(catchClause) { + this.inBlockScope(() => { + // Error binding is optional in catch clause since ECMAScript 2019 + if (catchClause.param !== null) { + this.enterPattern(catchClause.param, ident => { + this.defineVariable(ident); + }); + this.walkPattern(catchClause.param); + } + const prev = this.prevStatement; + this.blockPreWalkStatement(catchClause.body); + this.prevStatement = prev; + this.walkStatement(catchClause.body); + }); } - profileEnd(label) { - this[LOG_SYMBOL](LogType.profileEnd, [label]); + walkPattern(pattern) { + switch (pattern.type) { + case "ArrayPattern": + this.walkArrayPattern(pattern); + break; + case "AssignmentPattern": + this.walkAssignmentPattern(pattern); + break; + case "MemberExpression": + this.walkMemberExpression(pattern); + break; + case "ObjectPattern": + this.walkObjectPattern(pattern); + break; + case "RestElement": + this.walkRestElement(pattern); + break; + } } - time(label) { - this[TIMERS_SYMBOL] = this[TIMERS_SYMBOL] || new Map(); - this[TIMERS_SYMBOL].set(label, process.hrtime()); + walkAssignmentPattern(pattern) { + this.walkExpression(pattern.right); + this.walkPattern(pattern.left); } - timeLog(label) { - const prev = this[TIMERS_SYMBOL] && this[TIMERS_SYMBOL].get(label); - if (!prev) { - throw new Error(`No such label '${label}' for WebpackLogger.timeLog()`); + walkObjectPattern(pattern) { + for (let i = 0, len = pattern.properties.length; i < len; i++) { + const prop = pattern.properties[i]; + if (prop) { + if (prop.computed) this.walkExpression(prop.key); + if (prop.value) this.walkPattern(prop.value); + } } - const time = process.hrtime(prev); - this[LOG_SYMBOL](LogType.time, [label, ...time]); } - timeEnd(label) { - const prev = this[TIMERS_SYMBOL] && this[TIMERS_SYMBOL].get(label); - if (!prev) { - throw new Error(`No such label '${label}' for WebpackLogger.timeEnd()`); + walkArrayPattern(pattern) { + for (let i = 0, len = pattern.elements.length; i < len; i++) { + const element = pattern.elements[i]; + if (element) this.walkPattern(element); } - const time = process.hrtime(prev); - this[TIMERS_SYMBOL].delete(label); - this[LOG_SYMBOL](LogType.time, [label, ...time]); } - timeAggregate(label) { - const prev = this[TIMERS_SYMBOL] && this[TIMERS_SYMBOL].get(label); - if (!prev) { - throw new Error( - `No such label '${label}' for WebpackLogger.timeAggregate()` - ); - } - const time = process.hrtime(prev); - this[TIMERS_SYMBOL].delete(label); - this[TIMERS_AGGREGATES_SYMBOL] = - this[TIMERS_AGGREGATES_SYMBOL] || new Map(); - const current = this[TIMERS_AGGREGATES_SYMBOL].get(label); - if (current !== undefined) { - if (time[1] + current[1] > 1e9) { - time[0] += current[0] + 1; - time[1] = time[1] - 1e9 + current[1]; - } else { - time[0] += current[0]; - time[1] += current[1]; + walkRestElement(pattern) { + this.walkPattern(pattern.argument); + } + + walkExpressions(expressions) { + for (const expression of expressions) { + if (expression) { + this.walkExpression(expression); } } - this[TIMERS_AGGREGATES_SYMBOL].set(label, time); } - timeAggregateEnd(label) { - if (this[TIMERS_AGGREGATES_SYMBOL] === undefined) return; - const time = this[TIMERS_AGGREGATES_SYMBOL].get(label); - if (time === undefined) return; - this[TIMERS_AGGREGATES_SYMBOL].delete(label); - this[LOG_SYMBOL](LogType.time, [label, ...time]); + walkExpression(expression) { + switch (expression.type) { + case "ArrayExpression": + this.walkArrayExpression(expression); + break; + case "ArrowFunctionExpression": + this.walkArrowFunctionExpression(expression); + break; + case "AssignmentExpression": + this.walkAssignmentExpression(expression); + break; + case "AwaitExpression": + this.walkAwaitExpression(expression); + break; + case "BinaryExpression": + this.walkBinaryExpression(expression); + break; + case "CallExpression": + this.walkCallExpression(expression); + break; + case "ChainExpression": + this.walkChainExpression(expression); + break; + case "ClassExpression": + this.walkClassExpression(expression); + break; + case "ConditionalExpression": + this.walkConditionalExpression(expression); + break; + case "FunctionExpression": + this.walkFunctionExpression(expression); + break; + case "Identifier": + this.walkIdentifier(expression); + break; + case "ImportExpression": + this.walkImportExpression(expression); + break; + case "LogicalExpression": + this.walkLogicalExpression(expression); + break; + case "MetaProperty": + this.walkMetaProperty(expression); + break; + case "MemberExpression": + this.walkMemberExpression(expression); + break; + case "NewExpression": + this.walkNewExpression(expression); + break; + case "ObjectExpression": + this.walkObjectExpression(expression); + break; + case "SequenceExpression": + this.walkSequenceExpression(expression); + break; + case "SpreadElement": + this.walkSpreadElement(expression); + break; + case "TaggedTemplateExpression": + this.walkTaggedTemplateExpression(expression); + break; + case "TemplateLiteral": + this.walkTemplateLiteral(expression); + break; + case "ThisExpression": + this.walkThisExpression(expression); + break; + case "UnaryExpression": + this.walkUnaryExpression(expression); + break; + case "UpdateExpression": + this.walkUpdateExpression(expression); + break; + case "YieldExpression": + this.walkYieldExpression(expression); + break; + } } -} - -exports.Logger = WebpackLogger; - - -/***/ }), - -/***/ 34820: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ + walkAwaitExpression(expression) { + if (this.scope.topLevelScope === true) + this.hooks.topLevelAwait.call(expression); + this.walkExpression(expression.argument); + } + walkArrayExpression(expression) { + if (expression.elements) { + this.walkExpressions(expression.elements); + } + } -const { LogType } = __webpack_require__(54667); + walkSpreadElement(expression) { + if (expression.argument) { + this.walkExpression(expression.argument); + } + } -/** @typedef {import("../../declarations/WebpackOptions").FilterItemTypes} FilterItemTypes */ -/** @typedef {import("../../declarations/WebpackOptions").FilterTypes} FilterTypes */ -/** @typedef {import("./Logger").LogTypeEnum} LogTypeEnum */ + walkObjectExpression(expression) { + for ( + let propIndex = 0, len = expression.properties.length; + propIndex < len; + propIndex++ + ) { + const prop = expression.properties[propIndex]; + this.walkProperty(prop); + } + } -/** @typedef {function(string): boolean} FilterFunction */ + walkProperty(prop) { + if (prop.type === "SpreadElement") { + this.walkExpression(prop.argument); + return; + } + if (prop.computed) { + this.walkExpression(prop.key); + } + if (prop.shorthand && prop.value && prop.value.type === "Identifier") { + this.scope.inShorthand = prop.value.name; + this.walkIdentifier(prop.value); + this.scope.inShorthand = false; + } else { + this.walkExpression(prop.value); + } + } -/** - * @typedef {Object} LoggerConsole - * @property {function(): void} clear - * @property {function(): void} trace - * @property {(...args: any[]) => void} info - * @property {(...args: any[]) => void} log - * @property {(...args: any[]) => void} warn - * @property {(...args: any[]) => void} error - * @property {(...args: any[]) => void=} debug - * @property {(...args: any[]) => void=} group - * @property {(...args: any[]) => void=} groupCollapsed - * @property {(...args: any[]) => void=} groupEnd - * @property {(...args: any[]) => void=} status - * @property {(...args: any[]) => void=} profile - * @property {(...args: any[]) => void=} profileEnd - * @property {(...args: any[]) => void=} logTime - */ + walkFunctionExpression(expression) { + const wasTopLevel = this.scope.topLevelScope; + this.scope.topLevelScope = false; + const scopeParams = expression.params; -/** - * @typedef {Object} LoggerOptions - * @property {false|true|"none"|"error"|"warn"|"info"|"log"|"verbose"} level loglevel - * @property {FilterTypes|boolean} debug filter for debug logging - * @property {LoggerConsole} console the console to log to - */ + // Add function name in scope for recursive calls + if (expression.id) { + scopeParams.push(expression.id.name); + } -/** - * @param {FilterItemTypes} item an input item - * @returns {FilterFunction} filter function - */ -const filterToFunction = item => { - if (typeof item === "string") { - const regExp = new RegExp( - `[\\\\/]${item.replace( - // eslint-disable-next-line no-useless-escape - /[-[\]{}()*+?.\\^$|]/g, - "\\$&" - )}([\\\\/]|$|!|\\?)` - ); - return ident => regExp.test(ident); - } - if (item && typeof item === "object" && typeof item.test === "function") { - return ident => item.test(ident); - } - if (typeof item === "function") { - return item; - } - if (typeof item === "boolean") { - return () => item; + this.inFunctionScope(true, scopeParams, () => { + for (const param of expression.params) { + this.walkPattern(param); + } + if (expression.body.type === "BlockStatement") { + this.detectMode(expression.body.body); + const prev = this.prevStatement; + this.preWalkStatement(expression.body); + this.prevStatement = prev; + this.walkStatement(expression.body); + } else { + this.walkExpression(expression.body); + } + }); + this.scope.topLevelScope = wasTopLevel; } -}; - -/** - * @enum {number} - */ -const LogLevel = { - none: 6, - false: 6, - error: 5, - warn: 4, - info: 3, - log: 2, - true: 2, - verbose: 1 -}; -/** - * @param {LoggerOptions} options options object - * @returns {function(string, LogTypeEnum, any[]): void} logging function - */ -module.exports = ({ level = "info", debug = false, console }) => { - const debugFilters = - typeof debug === "boolean" - ? [() => debug] - : /** @type {FilterItemTypes[]} */ ([]) - .concat(debug) - .map(filterToFunction); - /** @type {number} */ - const loglevel = LogLevel[`${level}`] || 0; + walkArrowFunctionExpression(expression) { + const wasTopLevel = this.scope.topLevelScope; + this.scope.topLevelScope = wasTopLevel ? "arrow" : false; + this.inFunctionScope(false, expression.params, () => { + for (const param of expression.params) { + this.walkPattern(param); + } + if (expression.body.type === "BlockStatement") { + this.detectMode(expression.body.body); + const prev = this.prevStatement; + this.preWalkStatement(expression.body); + this.prevStatement = prev; + this.walkStatement(expression.body); + } else { + this.walkExpression(expression.body); + } + }); + this.scope.topLevelScope = wasTopLevel; + } /** - * @param {string} name name of the logger - * @param {LogTypeEnum} type type of the log entry - * @param {any[]} args arguments of the log entry - * @returns {void} + * @param {SequenceExpressionNode} expression the sequence */ - const logger = (name, type, args) => { - const labeledArgs = () => { - if (Array.isArray(args)) { - if (args.length > 0 && typeof args[0] === "string") { - return [`[${name}] ${args[0]}`, ...args.slice(1)]; - } else { - return [`[${name}]`, ...args]; - } - } else { - return []; - } - }; - const debug = debugFilters.some(f => f(name)); - switch (type) { - case LogType.debug: - if (!debug) return; - // eslint-disable-next-line node/no-unsupported-features/node-builtins - if (typeof console.debug === "function") { - // eslint-disable-next-line node/no-unsupported-features/node-builtins - console.debug(...labeledArgs()); - } else { - console.log(...labeledArgs()); - } - break; - case LogType.log: - if (!debug && loglevel > LogLevel.log) return; - console.log(...labeledArgs()); - break; - case LogType.info: - if (!debug && loglevel > LogLevel.info) return; - console.info(...labeledArgs()); - break; - case LogType.warn: - if (!debug && loglevel > LogLevel.warn) return; - console.warn(...labeledArgs()); - break; - case LogType.error: - if (!debug && loglevel > LogLevel.error) return; - console.error(...labeledArgs()); - break; - case LogType.trace: - if (!debug) return; - console.trace(); - break; - case LogType.groupCollapsed: - if (!debug && loglevel > LogLevel.log) return; - if (!debug && loglevel > LogLevel.verbose) { - // eslint-disable-next-line node/no-unsupported-features/node-builtins - if (typeof console.groupCollapsed === "function") { - // eslint-disable-next-line node/no-unsupported-features/node-builtins - console.groupCollapsed(...labeledArgs()); - } else { - console.log(...labeledArgs()); - } - break; - } - // falls through - case LogType.group: - if (!debug && loglevel > LogLevel.log) return; - // eslint-disable-next-line node/no-unsupported-features/node-builtins - if (typeof console.group === "function") { - // eslint-disable-next-line node/no-unsupported-features/node-builtins - console.group(...labeledArgs()); - } else { - console.log(...labeledArgs()); - } - break; - case LogType.groupEnd: - if (!debug && loglevel > LogLevel.log) return; - // eslint-disable-next-line node/no-unsupported-features/node-builtins - if (typeof console.groupEnd === "function") { - // eslint-disable-next-line node/no-unsupported-features/node-builtins - console.groupEnd(); - } - break; - case LogType.time: { - if (!debug && loglevel > LogLevel.log) return; - const ms = args[1] * 1000 + args[2] / 1000000; - const msg = `[${name}] ${args[0]}: ${ms} ms`; - if (typeof console.logTime === "function") { - console.logTime(msg); - } else { - console.log(msg); - } - break; + walkSequenceExpression(expression) { + if (!expression.expressions) return; + // We treat sequence expressions like statements when they are one statement level + // This has some benefits for optimizations that only work on statement level + const currentStatement = this.statementPath[this.statementPath.length - 1]; + if ( + currentStatement === expression || + (currentStatement.type === "ExpressionStatement" && + currentStatement.expression === expression) + ) { + const old = this.statementPath.pop(); + for (const expr of expression.expressions) { + this.statementPath.push(expr); + this.walkExpression(expr); + this.statementPath.pop(); } - case LogType.profile: - // eslint-disable-next-line node/no-unsupported-features/node-builtins - if (typeof console.profile === "function") { - // eslint-disable-next-line node/no-unsupported-features/node-builtins - console.profile(...labeledArgs()); - } - break; - case LogType.profileEnd: - // eslint-disable-next-line node/no-unsupported-features/node-builtins - if (typeof console.profileEnd === "function") { - // eslint-disable-next-line node/no-unsupported-features/node-builtins - console.profileEnd(...labeledArgs()); - } - break; - case LogType.clear: - if (!debug && loglevel > LogLevel.log) return; - // eslint-disable-next-line node/no-unsupported-features/node-builtins - if (typeof console.clear === "function") { - // eslint-disable-next-line node/no-unsupported-features/node-builtins - console.clear(); - } - break; - case LogType.status: - if (!debug && loglevel > LogLevel.info) return; - if (typeof console.status === "function") { - if (args.length === 0) { - console.status(); - } else { - console.status(...labeledArgs()); - } - } else { - if (args.length !== 0) { - console.info(...labeledArgs()); - } - } - break; - default: - throw new Error(`Unexpected LogType ${type}`); + this.statementPath.push(old); + } else { + this.walkExpressions(expression.expressions); } - }; - return logger; -}; + } + walkUpdateExpression(expression) { + this.walkExpression(expression.argument); + } -/***/ }), + walkUnaryExpression(expression) { + if (expression.operator === "typeof") { + const result = this.callHooksForExpression( + this.hooks.typeof, + expression.argument, + expression + ); + if (result === true) return; + if (expression.argument.type === "ChainExpression") { + const result = this.callHooksForExpression( + this.hooks.typeof, + expression.argument.expression, + expression + ); + if (result === true) return; + } + } + this.walkExpression(expression.argument); + } -/***/ 10072: -/***/ (function(module) { + walkLeftRightExpression(expression) { + this.walkExpression(expression.left); + this.walkExpression(expression.right); + } -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ + walkBinaryExpression(expression) { + this.walkLeftRightExpression(expression); + } + walkLogicalExpression(expression) { + const result = this.hooks.expressionLogicalOperator.call(expression); + if (result === undefined) { + this.walkLeftRightExpression(expression); + } else { + if (result) { + this.walkExpression(expression.right); + } + } + } + walkAssignmentExpression(expression) { + if (expression.left.type === "Identifier") { + const renameIdentifier = this.getRenameIdentifier(expression.right); + if (renameIdentifier) { + if ( + this.callHooksForInfo( + this.hooks.canRename, + renameIdentifier, + expression.right + ) + ) { + // renaming "a = b;" + if ( + !this.callHooksForInfo( + this.hooks.rename, + renameIdentifier, + expression.right + ) + ) { + this.setVariable( + expression.left.name, + this.getVariableInfo(renameIdentifier) + ); + } + return; + } + } + this.walkExpression(expression.right); + this.enterPattern(expression.left, (name, decl) => { + if (!this.callHooksForName(this.hooks.assign, name, expression)) { + this.walkExpression(expression.left); + } + }); + return; + } + if (expression.left.type.endsWith("Pattern")) { + this.walkExpression(expression.right); + this.enterPattern(expression.left, (name, decl) => { + if (!this.callHooksForName(this.hooks.assign, name, expression)) { + this.defineVariable(name); + } + }); + this.walkPattern(expression.left); + } else if (expression.left.type === "MemberExpression") { + const exprName = this.getMemberExpressionInfo( + expression.left, + ALLOWED_MEMBER_TYPES_EXPRESSION + ); + if (exprName) { + if ( + this.callHooksForInfo( + this.hooks.assignMemberChain, + exprName.rootInfo, + expression, + exprName.getMembers() + ) + ) { + return; + } + } + this.walkExpression(expression.right); + this.walkExpression(expression.left); + } else { + this.walkExpression(expression.right); + this.walkExpression(expression.left); + } + } -const arraySum = array => { - let sum = 0; - for (const item of array) sum += item; - return sum; -}; + walkConditionalExpression(expression) { + const result = this.hooks.expressionConditionalOperator.call(expression); + if (result === undefined) { + this.walkExpression(expression.test); + this.walkExpression(expression.consequent); + if (expression.alternate) { + this.walkExpression(expression.alternate); + } + } else { + if (result) { + this.walkExpression(expression.consequent); + } else if (expression.alternate) { + this.walkExpression(expression.alternate); + } + } + } -/** - * @param {any[]} args items to be truncated - * @param {number} maxLength maximum length of args including spaces between - * @returns {string[]} truncated args - */ -const truncateArgs = (args, maxLength) => { - const lengths = args.map(a => `${a}`.length); - const availableLength = maxLength - lengths.length + 1; + walkNewExpression(expression) { + const result = this.callHooksForExpression( + this.hooks.new, + expression.callee, + expression + ); + if (result === true) return; + this.walkExpression(expression.callee); + if (expression.arguments) { + this.walkExpressions(expression.arguments); + } + } - if (availableLength > 0 && args.length === 1) { - if (availableLength >= args[0].length) { - return args; - } else if (availableLength > 3) { - return ["..." + args[0].slice(-availableLength + 3)]; - } else { - return [args[0].slice(-availableLength)]; + walkYieldExpression(expression) { + if (expression.argument) { + this.walkExpression(expression.argument); } } - // Check if there is space for at least 4 chars per arg - if (availableLength < arraySum(lengths.map(i => Math.min(i, 6)))) { - // remove args - if (args.length > 1) - return truncateArgs(args.slice(0, args.length - 1), maxLength); - return []; + walkTemplateLiteral(expression) { + if (expression.expressions) { + this.walkExpressions(expression.expressions); + } } - let currentLength = arraySum(lengths); + walkTaggedTemplateExpression(expression) { + if (expression.tag) { + this.walkExpression(expression.tag); + } + if (expression.quasi && expression.quasi.expressions) { + this.walkExpressions(expression.quasi.expressions); + } + } - // Check if all fits into maxLength - if (currentLength <= availableLength) return args; + walkClassExpression(expression) { + this.walkClass(expression); + } - // Try to remove chars from the longest items until it fits - while (currentLength > availableLength) { - const maxLength = Math.max(...lengths); - const shorterItems = lengths.filter(l => l !== maxLength); - const nextToMaxLength = - shorterItems.length > 0 ? Math.max(...shorterItems) : 0; - const maxReduce = maxLength - nextToMaxLength; - let maxItems = lengths.length - shorterItems.length; - let overrun = currentLength - availableLength; - for (let i = 0; i < lengths.length; i++) { - if (lengths[i] === maxLength) { - const reduce = Math.min(Math.floor(overrun / maxItems), maxReduce); - lengths[i] -= reduce; - currentLength -= reduce; - overrun -= reduce; - maxItems--; + /** + * @param {ChainExpressionNode} expression expression + */ + walkChainExpression(expression) { + const result = this.hooks.optionalChaining.call(expression); + + if (result === undefined) { + if (expression.expression.type === "CallExpression") { + this.walkCallExpression(expression.expression); + } else { + this.walkMemberExpression(expression.expression); } } } - // Return args reduced to length in lengths - return args.map((a, i) => { - const str = `${a}`; - const length = lengths[i]; - if (str.length === length) { - return str; - } else if (length > 5) { - return "..." + str.slice(-length + 3); - } else if (length > 0) { - return str.slice(-length); - } else { - return ""; - } - }); -}; + _walkIIFE(functionExpression, options, currentThis) { + const getVarInfo = argOrThis => { + const renameIdentifier = this.getRenameIdentifier(argOrThis); + if (renameIdentifier) { + if ( + this.callHooksForInfo( + this.hooks.canRename, + renameIdentifier, + argOrThis + ) + ) { + if ( + !this.callHooksForInfo( + this.hooks.rename, + renameIdentifier, + argOrThis + ) + ) { + return this.getVariableInfo(renameIdentifier); + } + } + } + this.walkExpression(argOrThis); + }; + const { params, type } = functionExpression; + const arrow = type === "ArrowFunctionExpression"; + const renameThis = currentThis ? getVarInfo(currentThis) : null; + const varInfoForArgs = options.map(getVarInfo); + const wasTopLevel = this.scope.topLevelScope; + this.scope.topLevelScope = wasTopLevel && arrow ? "arrow" : false; + const scopeParams = params.filter( + (identifier, idx) => !varInfoForArgs[idx] + ); -module.exports = truncateArgs; + // Add function name in scope for recursive calls + if (functionExpression.id) { + scopeParams.push(functionExpression.id.name); + } + this.inFunctionScope(true, scopeParams, () => { + if (renameThis && !arrow) { + this.setVariable("this", renameThis); + } + for (let i = 0; i < varInfoForArgs.length; i++) { + const varInfo = varInfoForArgs[i]; + if (!varInfo) continue; + if (!params[i] || params[i].type !== "Identifier") continue; + this.setVariable(params[i].name, varInfo); + } + if (functionExpression.body.type === "BlockStatement") { + this.detectMode(functionExpression.body.body); + const prev = this.prevStatement; + this.preWalkStatement(functionExpression.body); + this.prevStatement = prev; + this.walkStatement(functionExpression.body); + } else { + this.walkExpression(functionExpression.body); + } + }); + this.scope.topLevelScope = wasTopLevel; + } -/***/ }), + walkImportExpression(expression) { + let result = this.hooks.importCall.call(expression); + if (result === true) return; -/***/ 32610: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + this.walkExpression(expression.source); + } -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ + walkCallExpression(expression) { + const isSimpleFunction = fn => { + return fn.params.every(p => p.type === "Identifier"); + }; + if ( + expression.callee.type === "MemberExpression" && + expression.callee.object.type.endsWith("FunctionExpression") && + !expression.callee.computed && + (expression.callee.property.name === "call" || + expression.callee.property.name === "bind") && + expression.arguments.length > 0 && + isSimpleFunction(expression.callee.object) + ) { + // (function(…) { }.call/bind(?, …)) + this._walkIIFE( + expression.callee.object, + expression.arguments.slice(1), + expression.arguments[0] + ); + } else if ( + expression.callee.type.endsWith("FunctionExpression") && + isSimpleFunction(expression.callee) + ) { + // (function(…) { }(…)) + this._walkIIFE(expression.callee, expression.arguments, null); + } else { + if (expression.callee.type === "MemberExpression") { + const exprInfo = this.getMemberExpressionInfo( + expression.callee, + ALLOWED_MEMBER_TYPES_CALL_EXPRESSION + ); + if (exprInfo && exprInfo.type === "call") { + const result = this.callHooksForInfo( + this.hooks.callMemberChainOfCallMemberChain, + exprInfo.rootInfo, + expression, + exprInfo.getCalleeMembers(), + exprInfo.call, + exprInfo.getMembers() + ); + if (result === true) return; + } + } + const callee = this.evaluateExpression(expression.callee); + if (callee.isIdentifier()) { + const result1 = this.callHooksForInfo( + this.hooks.callMemberChain, + callee.rootInfo, + expression, + callee.getMembers() + ); + if (result1 === true) return; + const result2 = this.callHooksForInfo( + this.hooks.call, + callee.identifier, + expression + ); + if (result2 === true) return; + } + if (expression.callee) { + if (expression.callee.type === "MemberExpression") { + // because of call context we need to walk the call context as expression + this.walkExpression(expression.callee.object); + if (expression.callee.computed === true) + this.walkExpression(expression.callee.property); + } else { + this.walkExpression(expression.callee); + } + } + if (expression.arguments) this.walkExpressions(expression.arguments); + } + } + walkMemberExpression(expression) { + const exprInfo = this.getMemberExpressionInfo( + expression, + ALLOWED_MEMBER_TYPES_ALL + ); + if (exprInfo) { + switch (exprInfo.type) { + case "expression": { + const result1 = this.callHooksForInfo( + this.hooks.expression, + exprInfo.name, + expression + ); + if (result1 === true) return; + const members = exprInfo.getMembers(); + const result2 = this.callHooksForInfo( + this.hooks.expressionMemberChain, + exprInfo.rootInfo, + expression, + members + ); + if (result2 === true) return; + this.walkMemberExpressionWithExpressionName( + expression, + exprInfo.name, + exprInfo.rootInfo, + members.slice(), + () => + this.callHooksForInfo( + this.hooks.unhandledExpressionMemberChain, + exprInfo.rootInfo, + expression, + members + ) + ); + return; + } + case "call": { + const result = this.callHooksForInfo( + this.hooks.memberChainOfCallMemberChain, + exprInfo.rootInfo, + expression, + exprInfo.getCalleeMembers(), + exprInfo.call, + exprInfo.getMembers() + ); + if (result === true) return; + // Fast skip over the member chain as we already called memberChainOfCallMemberChain + // and call computed property are literals anyway + this.walkExpression(exprInfo.call); + return; + } + } + } + this.walkExpression(expression.object); + if (expression.computed === true) this.walkExpression(expression.property); + } -const RuntimeGlobals = __webpack_require__(49404); -const StartupChunkDependenciesPlugin = __webpack_require__(23613); + walkMemberExpressionWithExpressionName( + expression, + name, + rootInfo, + members, + onUnhandled + ) { + if (expression.object.type === "MemberExpression") { + // optimize the case where expression.object is a MemberExpression too. + // we can keep info here when calling walkMemberExpression directly + const property = + expression.property.name || `${expression.property.value}`; + name = name.slice(0, -property.length - 1); + members.pop(); + const result = this.callHooksForInfo( + this.hooks.expression, + name, + expression.object + ); + if (result === true) return; + this.walkMemberExpressionWithExpressionName( + expression.object, + name, + rootInfo, + members, + onUnhandled + ); + } else if (!onUnhandled || !onUnhandled()) { + this.walkExpression(expression.object); + } + if (expression.computed === true) this.walkExpression(expression.property); + } -/** @typedef {import("../Compiler")} Compiler */ + walkThisExpression(expression) { + this.callHooksForName(this.hooks.expression, "this", expression); + } -class CommonJsChunkLoadingPlugin { - constructor(options) { - options = options || {}; - this._asyncChunkLoading = options.asyncChunkLoading; + walkIdentifier(expression) { + this.callHooksForName(this.hooks.expression, expression.name, expression); } /** - * Apply the plugin - * @param {Compiler} compiler the compiler instance - * @returns {void} + * @param {MetaPropertyNode} metaProperty meta property */ - apply(compiler) { - const ChunkLoadingRuntimeModule = this._asyncChunkLoading - ? __webpack_require__(71842) - : __webpack_require__(37181); - const chunkLoadingValue = this._asyncChunkLoading - ? "async-node" - : "require"; - new StartupChunkDependenciesPlugin({ - chunkLoading: chunkLoadingValue, - asyncChunkLoading: this._asyncChunkLoading - }).apply(compiler); - compiler.hooks.thisCompilation.tap( - "CommonJsChunkLoadingPlugin", - compilation => { - const globalChunkLoading = compilation.outputOptions.chunkLoading; - const isEnabledForChunk = chunk => { - const options = chunk.getEntryOptions(); - const chunkLoading = - options && options.chunkLoading !== undefined - ? options.chunkLoading - : globalChunkLoading; - return chunkLoading === chunkLoadingValue; - }; - const onceForChunkSet = new WeakSet(); - const handler = (chunk, set) => { - if (onceForChunkSet.has(chunk)) return; - onceForChunkSet.add(chunk); - if (!isEnabledForChunk(chunk)) return; - set.add(RuntimeGlobals.moduleFactoriesAddOnly); - set.add(RuntimeGlobals.hasOwnProperty); - compilation.addRuntimeModule( - chunk, - new ChunkLoadingRuntimeModule(set) - ); - }; - - compilation.hooks.runtimeRequirementInTree - .for(RuntimeGlobals.ensureChunkHandlers) - .tap("CommonJsChunkLoadingPlugin", handler); - compilation.hooks.runtimeRequirementInTree - .for(RuntimeGlobals.hmrDownloadUpdateHandlers) - .tap("CommonJsChunkLoadingPlugin", handler); - compilation.hooks.runtimeRequirementInTree - .for(RuntimeGlobals.hmrDownloadManifest) - .tap("CommonJsChunkLoadingPlugin", handler); - compilation.hooks.runtimeRequirementInTree - .for(RuntimeGlobals.baseURI) - .tap("CommonJsChunkLoadingPlugin", handler); - compilation.hooks.runtimeRequirementInTree - .for(RuntimeGlobals.externalInstallChunk) - .tap("CommonJsChunkLoadingPlugin", handler); - compilation.hooks.runtimeRequirementInTree - .for(RuntimeGlobals.onChunksLoaded) - .tap("CommonJsChunkLoadingPlugin", handler); + walkMetaProperty(metaProperty) { + this.hooks.expression.for(getRootName(metaProperty)).call(metaProperty); + } - compilation.hooks.runtimeRequirementInTree - .for(RuntimeGlobals.ensureChunkHandlers) - .tap("CommonJsChunkLoadingPlugin", (chunk, set) => { - if (!isEnabledForChunk(chunk)) return; - set.add(RuntimeGlobals.getChunkScriptFilename); - }); - compilation.hooks.runtimeRequirementInTree - .for(RuntimeGlobals.hmrDownloadUpdateHandlers) - .tap("CommonJsChunkLoadingPlugin", (chunk, set) => { - if (!isEnabledForChunk(chunk)) return; - set.add(RuntimeGlobals.getChunkUpdateScriptFilename); - set.add(RuntimeGlobals.moduleCache); - set.add(RuntimeGlobals.hmrModuleData); - set.add(RuntimeGlobals.moduleFactoriesAddOnly); - }); - compilation.hooks.runtimeRequirementInTree - .for(RuntimeGlobals.hmrDownloadManifest) - .tap("CommonJsChunkLoadingPlugin", (chunk, set) => { - if (!isEnabledForChunk(chunk)) return; - set.add(RuntimeGlobals.getUpdateManifestFilename); - }); - } + callHooksForExpression(hookMap, expr, ...args) { + return this.callHooksForExpressionWithFallback( + hookMap, + expr, + undefined, + undefined, + ...args ); } -} - -module.exports = CommonJsChunkLoadingPlugin; - - -/***/ }), - -/***/ 38857: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ - - - -const CachedInputFileSystem = __webpack_require__(26785); -const fs = __webpack_require__(82161); -const createConsoleLogger = __webpack_require__(34820); -const NodeWatchFileSystem = __webpack_require__(31495); -const nodeConsole = __webpack_require__(10152); - -/** @typedef {import("../../declarations/WebpackOptions").InfrastructureLogging} InfrastructureLogging */ -/** @typedef {import("../Compiler")} Compiler */ -class NodeEnvironmentPlugin { /** - * @param {Object} options options - * @param {InfrastructureLogging} options.infrastructureLogging infrastructure logging options + * @template T + * @template R + * @param {HookMap>} hookMap hooks the should be called + * @param {MemberExpressionNode} expr expression info + * @param {function(string, string | ScopeInfo | VariableInfo, function(): string[]): any} fallback callback when variable in not handled by hooks + * @param {function(string): any} defined callback when variable is defined + * @param {AsArray} args args for the hook + * @returns {R} result of hook */ - constructor(options) { - this.options = options; + callHooksForExpressionWithFallback( + hookMap, + expr, + fallback, + defined, + ...args + ) { + const exprName = this.getMemberExpressionInfo( + expr, + ALLOWED_MEMBER_TYPES_EXPRESSION + ); + if (exprName !== undefined) { + const members = exprName.getMembers(); + return this.callHooksForInfoWithFallback( + hookMap, + members.length === 0 ? exprName.rootInfo : exprName.name, + fallback && + (name => fallback(name, exprName.rootInfo, exprName.getMembers)), + defined && (() => defined(exprName.name)), + ...args + ); + } } /** - * Apply the plugin - * @param {Compiler} compiler the compiler instance - * @returns {void} + * @template T + * @template R + * @param {HookMap>} hookMap hooks the should be called + * @param {string} name key in map + * @param {AsArray} args args for the hook + * @returns {R} result of hook */ - apply(compiler) { - const { infrastructureLogging } = this.options; - compiler.infrastructureLogger = createConsoleLogger({ - level: infrastructureLogging.level || "info", - debug: infrastructureLogging.debug || false, - console: - infrastructureLogging.console || - nodeConsole({ - colors: infrastructureLogging.colors, - appendOnly: infrastructureLogging.appendOnly, - stream: infrastructureLogging.stream - }) - }); - compiler.inputFileSystem = new CachedInputFileSystem(fs, 60000); - const inputFileSystem = compiler.inputFileSystem; - compiler.outputFileSystem = fs; - compiler.intermediateFileSystem = fs; - compiler.watchFileSystem = new NodeWatchFileSystem( - compiler.inputFileSystem + callHooksForName(hookMap, name, ...args) { + return this.callHooksForNameWithFallback( + hookMap, + name, + undefined, + undefined, + ...args ); - compiler.hooks.beforeRun.tap("NodeEnvironmentPlugin", compiler => { - if (compiler.inputFileSystem === inputFileSystem) { - compiler.fsStartTime = Date.now(); - inputFileSystem.purge(); - } - }); } -} - -module.exports = NodeEnvironmentPlugin; - - -/***/ }), - -/***/ 13313: -/***/ (function(module) { - -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ + /** + * @template T + * @template R + * @param {HookMap>} hookMap hooks that should be called + * @param {ExportedVariableInfo} info variable info + * @param {AsArray} args args for the hook + * @returns {R} result of hook + */ + callHooksForInfo(hookMap, info, ...args) { + return this.callHooksForInfoWithFallback( + hookMap, + info, + undefined, + undefined, + ...args + ); + } + /** + * @template T + * @template R + * @param {HookMap>} hookMap hooks the should be called + * @param {ExportedVariableInfo} info variable info + * @param {function(string): any} fallback callback when variable in not handled by hooks + * @param {function(): any} defined callback when variable is defined + * @param {AsArray} args args for the hook + * @returns {R} result of hook + */ + callHooksForInfoWithFallback(hookMap, info, fallback, defined, ...args) { + let name; + if (typeof info === "string") { + name = info; + } else { + if (!(info instanceof VariableInfo)) { + if (defined !== undefined) { + return defined(); + } + return; + } + let tagInfo = info.tagInfo; + while (tagInfo !== undefined) { + const hook = hookMap.get(tagInfo.tag); + if (hook !== undefined) { + this.currentTagData = tagInfo.data; + const result = hook.call(...args); + this.currentTagData = undefined; + if (result !== undefined) return result; + } + tagInfo = tagInfo.next; + } + if (info.freeName === true) { + if (defined !== undefined) { + return defined(); + } + return; + } + name = info.freeName; + } + const hook = hookMap.get(name); + if (hook !== undefined) { + const result = hook.call(...args); + if (result !== undefined) return result; + } + if (fallback !== undefined) { + return fallback(name); + } + } -/** @typedef {import("../Compiler")} Compiler */ + /** + * @template T + * @template R + * @param {HookMap>} hookMap hooks the should be called + * @param {string} name key in map + * @param {function(string): any} fallback callback when variable in not handled by hooks + * @param {function(): any} defined callback when variable is defined + * @param {AsArray} args args for the hook + * @returns {R} result of hook + */ + callHooksForNameWithFallback(hookMap, name, fallback, defined, ...args) { + return this.callHooksForInfoWithFallback( + hookMap, + this.getVariableInfo(name), + fallback, + defined, + ...args + ); + } -class NodeSourcePlugin { /** - * Apply the plugin - * @param {Compiler} compiler the compiler instance + * @deprecated + * @param {any} params scope params + * @param {function(): void} fn inner function * @returns {void} */ - apply(compiler) {} -} - -module.exports = NodeSourcePlugin; - - -/***/ }), + inScope(params, fn) { + const oldScope = this.scope; + this.scope = { + topLevelScope: oldScope.topLevelScope, + inTry: false, + inShorthand: false, + isStrict: oldScope.isStrict, + isAsmJs: oldScope.isAsmJs, + definitions: oldScope.definitions.createChild() + }; -/***/ 28037: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + this.undefineVariable("this"); -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ + this.enterPatterns(params, (ident, pattern) => { + this.defineVariable(ident); + }); + fn(); + this.scope = oldScope; + } -const ExternalsPlugin = __webpack_require__(361); + inFunctionScope(hasThis, params, fn) { + const oldScope = this.scope; + this.scope = { + topLevelScope: oldScope.topLevelScope, + inTry: false, + inShorthand: false, + isStrict: oldScope.isStrict, + isAsmJs: oldScope.isAsmJs, + definitions: oldScope.definitions.createChild() + }; -/** @typedef {import("../Compiler")} Compiler */ + if (hasThis) { + this.undefineVariable("this"); + } -const builtins = [ - "assert", - "async_hooks", - "buffer", - "child_process", - "cluster", - "console", - "constants", - "crypto", - "dgram", - "diagnostics_channel", - "dns", - "dns/promises", - "domain", - "events", - "fs", - "fs/promises", - "http", - "http2", - "https", - "inspector", - "module", - "net", - "os", - "path", - "path/posix", - "path/win32", - "perf_hooks", - "process", - "punycode", - "querystring", - "readline", - "repl", - "stream", - "stream/promises", - "stream/web", - "string_decoder", - "sys", - "timers", - "timers/promises", - "tls", - "trace_events", - "tty", - "url", - "util", - "v8", - "vm", - "wasi", - "worker_threads", - "zlib", - /^node:/, + this.enterPatterns(params, (ident, pattern) => { + this.defineVariable(ident); + }); - // cspell:word pnpapi - // Yarn PnP adds pnpapi as "builtin" - "pnpapi" -]; + fn(); -class NodeTargetPlugin { - /** - * Apply the plugin - * @param {Compiler} compiler the compiler instance - * @returns {void} - */ - apply(compiler) { - new ExternalsPlugin("node-commonjs", builtins).apply(compiler); + this.scope = oldScope; } -} - -module.exports = NodeTargetPlugin; + inBlockScope(fn) { + const oldScope = this.scope; + this.scope = { + topLevelScope: oldScope.topLevelScope, + inTry: oldScope.inTry, + inShorthand: false, + isStrict: oldScope.isStrict, + isAsmJs: oldScope.isAsmJs, + definitions: oldScope.definitions.createChild() + }; -/***/ }), - -/***/ 47087: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ - + fn(); + this.scope = oldScope; + } -const CommonJsChunkFormatPlugin = __webpack_require__(57634); -const EnableChunkLoadingPlugin = __webpack_require__(34726); + detectMode(statements) { + const isLiteral = + statements.length >= 1 && + statements[0].type === "ExpressionStatement" && + statements[0].expression.type === "Literal"; + if (isLiteral && statements[0].expression.value === "use strict") { + this.scope.isStrict = true; + } + if (isLiteral && statements[0].expression.value === "use asm") { + this.scope.isAsmJs = true; + } + } -/** @typedef {import("../Compiler")} Compiler */ + enterPatterns(patterns, onIdent) { + for (const pattern of patterns) { + if (typeof pattern !== "string") { + this.enterPattern(pattern, onIdent); + } else if (pattern) { + onIdent(pattern); + } + } + } -class NodeTemplatePlugin { - constructor(options) { - this._options = options || {}; + enterPattern(pattern, onIdent) { + if (!pattern) return; + switch (pattern.type) { + case "ArrayPattern": + this.enterArrayPattern(pattern, onIdent); + break; + case "AssignmentPattern": + this.enterAssignmentPattern(pattern, onIdent); + break; + case "Identifier": + this.enterIdentifier(pattern, onIdent); + break; + case "ObjectPattern": + this.enterObjectPattern(pattern, onIdent); + break; + case "RestElement": + this.enterRestElement(pattern, onIdent); + break; + case "Property": + if (pattern.shorthand && pattern.value.type === "Identifier") { + this.scope.inShorthand = pattern.value.name; + this.enterIdentifier(pattern.value, onIdent); + this.scope.inShorthand = false; + } else { + this.enterPattern(pattern.value, onIdent); + } + break; + } } - /** - * Apply the plugin - * @param {Compiler} compiler the compiler instance - * @returns {void} - */ - apply(compiler) { - const chunkLoading = this._options.asyncChunkLoading - ? "async-node" - : "require"; - compiler.options.output.chunkLoading = chunkLoading; - new CommonJsChunkFormatPlugin().apply(compiler); - new EnableChunkLoadingPlugin(chunkLoading).apply(compiler); + enterIdentifier(pattern, onIdent) { + if (!this.callHooksForName(this.hooks.pattern, pattern.name, pattern)) { + onIdent(pattern.name, pattern); + } } -} - -module.exports = NodeTemplatePlugin; - - -/***/ }), - -/***/ 31495: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ - + enterObjectPattern(pattern, onIdent) { + for ( + let propIndex = 0, len = pattern.properties.length; + propIndex < len; + propIndex++ + ) { + const prop = pattern.properties[propIndex]; + this.enterPattern(prop, onIdent); + } + } -const Watchpack = __webpack_require__(98342); + enterArrayPattern(pattern, onIdent) { + for ( + let elementIndex = 0, len = pattern.elements.length; + elementIndex < len; + elementIndex++ + ) { + const element = pattern.elements[elementIndex]; + this.enterPattern(element, onIdent); + } + } -/** @typedef {import("../../declarations/WebpackOptions").WatchOptions} WatchOptions */ -/** @typedef {import("../FileSystemInfo").FileSystemInfoEntry} FileSystemInfoEntry */ -/** @typedef {import("../util/fs").WatchFileSystem} WatchFileSystem */ -/** @typedef {import("../util/fs").WatchMethod} WatchMethod */ -/** @typedef {import("../util/fs").Watcher} Watcher */ + enterRestElement(pattern, onIdent) { + this.enterPattern(pattern.argument, onIdent); + } -class NodeWatchFileSystem { - constructor(inputFileSystem) { - this.inputFileSystem = inputFileSystem; - this.watcherOptions = { - aggregateTimeout: 0 - }; - this.watcher = new Watchpack(this.watcherOptions); + enterAssignmentPattern(pattern, onIdent) { + this.enterPattern(pattern.left, onIdent); } /** - * @param {Iterable} files watched files - * @param {Iterable} directories watched directories - * @param {Iterable} missing watched exitance entries - * @param {number} startTime timestamp of start time - * @param {WatchOptions} options options object - * @param {function(Error=, Map, Map, Set, Set): void} callback aggregated callback - * @param {function(string, number): void} callbackUndelayed callback when the first change was detected - * @returns {Watcher} a watcher + * @param {ExpressionNode} expression expression node + * @returns {BasicEvaluatedExpression | undefined} evaluation result */ - watch( - files, - directories, - missing, - startTime, - options, - callback, - callbackUndelayed - ) { - if (!files || typeof files[Symbol.iterator] !== "function") { - throw new Error("Invalid arguments: 'files'"); - } - if (!directories || typeof directories[Symbol.iterator] !== "function") { - throw new Error("Invalid arguments: 'directories'"); - } - if (!missing || typeof missing[Symbol.iterator] !== "function") { - throw new Error("Invalid arguments: 'missing'"); - } - if (typeof callback !== "function") { - throw new Error("Invalid arguments: 'callback'"); - } - if (typeof startTime !== "number" && startTime) { - throw new Error("Invalid arguments: 'startTime'"); - } - if (typeof options !== "object") { - throw new Error("Invalid arguments: 'options'"); - } - if (typeof callbackUndelayed !== "function" && callbackUndelayed) { - throw new Error("Invalid arguments: 'callbackUndelayed'"); - } - const oldWatcher = this.watcher; - this.watcher = new Watchpack(options); - - if (callbackUndelayed) { - this.watcher.once("change", callbackUndelayed); - } - this.watcher.once("aggregated", (changes, removals) => { - if (this.inputFileSystem && this.inputFileSystem.purge) { - const fs = this.inputFileSystem; - for (const item of changes) { - fs.purge(item); - } - for (const item of removals) { - fs.purge(item); + evaluateExpression(expression) { + try { + const hook = this.hooks.evaluate.get(expression.type); + if (hook !== undefined) { + const result = hook.call(expression); + if (result !== undefined) { + if (result) { + result.setExpression(expression); + } + return result; } } - const times = this.watcher.getTimeInfoEntries(); - callback(null, times, times, changes, removals); - }); - - this.watcher.watch({ files, directories, missing, startTime }); - - if (oldWatcher) { - oldWatcher.close(); + } catch (e) { + console.warn(e); + // ignore error } - return { - close: () => { - if (this.watcher) { - this.watcher.close(); - this.watcher = null; - } - }, - pause: () => { - if (this.watcher) { - this.watcher.pause(); - } - }, - getAggregatedRemovals: () => { - const items = this.watcher && this.watcher.aggregatedRemovals; - if (items && this.inputFileSystem && this.inputFileSystem.purge) { - const fs = this.inputFileSystem; - for (const item of items) { - fs.purge(item); - } + return new BasicEvaluatedExpression() + .setRange(expression.range) + .setExpression(expression); + } + + parseString(expression) { + switch (expression.type) { + case "BinaryExpression": + if (expression.operator === "+") { + return ( + this.parseString(expression.left) + + this.parseString(expression.right) + ); } - return items; - }, - getAggregatedChanges: () => { - const items = this.watcher && this.watcher.aggregatedChanges; - if (items && this.inputFileSystem && this.inputFileSystem.purge) { - const fs = this.inputFileSystem; - for (const item of items) { - fs.purge(item); + break; + case "Literal": + return expression.value + ""; + } + throw new Error( + expression.type + " is not supported as parameter for require" + ); + } + + parseCalculatedString(expression) { + switch (expression.type) { + case "BinaryExpression": + if (expression.operator === "+") { + const left = this.parseCalculatedString(expression.left); + const right = this.parseCalculatedString(expression.right); + if (left.code) { + return { + range: left.range, + value: left.value, + code: true, + conditional: false + }; + } else if (right.code) { + return { + range: [ + left.range[0], + right.range ? right.range[1] : left.range[1] + ], + value: left.value + right.value, + code: true, + conditional: false + }; + } else { + return { + range: [left.range[0], right.range[1]], + value: left.value + right.value, + code: false, + conditional: false + }; } } - return items; - }, - getFileTimeInfoEntries: () => { - if (this.watcher) { - return this.watcher.getTimeInfoEntries(); + break; + case "ConditionalExpression": { + const consequent = this.parseCalculatedString(expression.consequent); + const alternate = this.parseCalculatedString(expression.alternate); + const items = []; + if (consequent.conditional) { + items.push(...consequent.conditional); + } else if (!consequent.code) { + items.push(consequent); } else { - return new Map(); + break; } - }, - getContextTimeInfoEntries: () => { - if (this.watcher) { - return this.watcher.getTimeInfoEntries(); + if (alternate.conditional) { + items.push(...alternate.conditional); + } else if (!alternate.code) { + items.push(alternate); } else { - return new Map(); + break; } + return { + range: undefined, + value: "", + code: true, + conditional: items + }; } + case "Literal": + return { + range: expression.range, + value: expression.value + "", + code: false, + conditional: false + }; + } + return { + range: undefined, + value: "", + code: true, + conditional: false }; } -} -module.exports = NodeWatchFileSystem; + /** + * @param {string | Buffer | PreparsedAst} source the source to parse + * @param {ParserState} state the parser state + * @returns {ParserState} the parser state + */ + parse(source, state) { + let ast; + let comments; + const semicolons = new Set(); + if (source === null) { + throw new Error("source must not be null"); + } + if (Buffer.isBuffer(source)) { + source = source.toString("utf-8"); + } + if (typeof source === "object") { + ast = /** @type {ProgramNode} */ (source); + comments = source.comments; + } else { + comments = []; + ast = JavascriptParser._parse(source, { + sourceType: this.sourceType, + onComment: comments, + onInsertedSemicolon: pos => semicolons.add(pos) + }); + } + const oldScope = this.scope; + const oldState = this.state; + const oldComments = this.comments; + const oldSemicolons = this.semicolons; + const oldStatementPath = this.statementPath; + const oldPrevStatement = this.prevStatement; + this.scope = { + topLevelScope: true, + inTry: false, + inShorthand: false, + isStrict: false, + isAsmJs: false, + definitions: new StackedMap() + }; + /** @type {ParserState} */ + this.state = state; + this.comments = comments; + this.semicolons = semicolons; + this.statementPath = []; + this.prevStatement = undefined; + if (this.hooks.program.call(ast, comments) === undefined) { + this.detectMode(ast.body); + this.preWalkStatements(ast.body); + this.prevStatement = undefined; + this.blockPreWalkStatements(ast.body); + this.prevStatement = undefined; + this.walkStatements(ast.body); + } + this.hooks.finish.call(ast, comments); + this.scope = oldScope; + /** @type {ParserState} */ + this.state = oldState; + this.comments = oldComments; + this.semicolons = oldSemicolons; + this.statementPath = oldStatementPath; + this.prevStatement = oldPrevStatement; + return state; + } -/***/ }), + evaluate(source) { + const ast = JavascriptParser._parse("(" + source + ")", { + sourceType: this.sourceType, + locations: false + }); + if (ast.body.length !== 1 || ast.body[0].type !== "ExpressionStatement") { + throw new Error("evaluate: Source is not a expression"); + } + return this.evaluateExpression(ast.body[0].expression); + } -/***/ 71842: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + /** + * @param {ExpressionNode | DeclarationNode | PrivateIdentifierNode | null | undefined} expr an expression + * @param {number} commentsStartPos source position from which annotation comments are checked + * @returns {boolean} true, when the expression is pure + */ + isPure(expr, commentsStartPos) { + if (!expr) return true; + const result = this.hooks.isPure + .for(expr.type) + .call(expr, commentsStartPos); + if (typeof result === "boolean") return result; + switch (expr.type) { + case "ClassDeclaration": + case "ClassExpression": { + if (expr.body.type !== "ClassBody") return false; + if (expr.superClass && !this.isPure(expr.superClass, expr.range[0])) { + return false; + } + const items = + /** @type {(MethodDefinitionNode | PropertyDefinitionNode)[]} */ ( + expr.body.body + ); + return items.every( + item => + (!item.computed || + !item.key || + this.isPure(item.key, item.range[0])) && + (!item.static || + !item.value || + this.isPure( + item.value, + item.key ? item.key.range[1] : item.range[0] + )) + ); + } -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php -*/ + case "FunctionDeclaration": + case "FunctionExpression": + case "ArrowFunctionExpression": + case "Literal": + case "PrivateIdentifier": + return true; + case "VariableDeclaration": + return expr.declarations.every(decl => + this.isPure(decl.init, decl.range[0]) + ); + case "ConditionalExpression": + return ( + this.isPure(expr.test, commentsStartPos) && + this.isPure(expr.consequent, expr.test.range[1]) && + this.isPure(expr.alternate, expr.consequent.range[1]) + ); -const RuntimeGlobals = __webpack_require__(49404); -const RuntimeModule = __webpack_require__(61439); -const Template = __webpack_require__(92066); -const { - chunkHasJs, - getChunkFilenameTemplate -} = __webpack_require__(76767); -const { getInitialChunkIds } = __webpack_require__(30951); -const compileBooleanMatcher = __webpack_require__(356); -const { getUndoPath } = __webpack_require__(96236); + case "SequenceExpression": + return expr.expressions.every(expr => { + const pureFlag = this.isPure(expr, commentsStartPos); + commentsStartPos = expr.range[1]; + return pureFlag; + }); -class ReadFileChunkLoadingRuntimeModule extends RuntimeModule { - constructor(runtimeRequirements) { - super("readFile chunk loading", RuntimeModule.STAGE_ATTACH); - this.runtimeRequirements = runtimeRequirements; + case "CallExpression": { + const pureFlag = + expr.range[0] - commentsStartPos > 12 && + this.getComments([commentsStartPos, expr.range[0]]).some( + comment => + comment.type === "Block" && + /^\s*(#|@)__PURE__\s*$/.test(comment.value) + ); + if (!pureFlag) return false; + commentsStartPos = expr.callee.range[1]; + return expr.arguments.every(arg => { + if (arg.type === "SpreadElement") return false; + const pureFlag = this.isPure(arg, commentsStartPos); + commentsStartPos = arg.range[1]; + return pureFlag; + }); + } + } + const evaluated = this.evaluateExpression(expr); + return !evaluated.couldHaveSideEffects(); + } + + getComments(range) { + const [rangeStart, rangeEnd] = range; + const compare = (comment, needle) => comment.range[0] - needle; + let idx = binarySearchBounds.ge(this.comments, rangeStart, compare); + let commentsInRange = []; + while (this.comments[idx] && this.comments[idx].range[1] <= rangeEnd) { + commentsInRange.push(this.comments[idx]); + idx++; + } + + return commentsInRange; } /** - * @returns {string} runtime code + * @param {number} pos source code position + * @returns {boolean} true when a semicolon has been inserted before this position, false if not */ - generate() { - const { chunkGraph, chunk } = this; - const { runtimeTemplate } = this.compilation; - const fn = RuntimeGlobals.ensureChunkHandlers; - const withBaseURI = this.runtimeRequirements.has(RuntimeGlobals.baseURI); - const withExternalInstallChunk = this.runtimeRequirements.has( - RuntimeGlobals.externalInstallChunk - ); - const withOnChunkLoad = this.runtimeRequirements.has( - RuntimeGlobals.onChunksLoaded - ); - const withLoading = this.runtimeRequirements.has( - RuntimeGlobals.ensureChunkHandlers - ); - const withHmr = this.runtimeRequirements.has( - RuntimeGlobals.hmrDownloadUpdateHandlers + isAsiPosition(pos) { + const currentStatement = this.statementPath[this.statementPath.length - 1]; + if (currentStatement === undefined) throw new Error("Not in statement"); + return ( + // Either asking directly for the end position of the current statement + (currentStatement.range[1] === pos && this.semicolons.has(pos)) || + // Or asking for the start position of the current statement, + // here we have to check multiple things + (currentStatement.range[0] === pos && + // is there a previous statement which might be relevant? + this.prevStatement !== undefined && + // is the end position of the previous statement an ASI position? + this.semicolons.has(this.prevStatement.range[1])) ); - const withHmrManifest = this.runtimeRequirements.has( - RuntimeGlobals.hmrDownloadManifest + } + + /** + * @param {number} pos source code position + * @returns {void} + */ + unsetAsiPosition(pos) { + this.semicolons.delete(pos); + } + + isStatementLevelExpression(expr) { + const currentStatement = this.statementPath[this.statementPath.length - 1]; + return ( + expr === currentStatement || + (currentStatement.type === "ExpressionStatement" && + currentStatement.expression === expr) ); - const conditionMap = chunkGraph.getChunkConditionMap(chunk, chunkHasJs); - const hasJsMatcher = compileBooleanMatcher(conditionMap); - const initialChunkIds = getInitialChunkIds(chunk, chunkGraph); + } - const outputName = this.compilation.getPath( - getChunkFilenameTemplate(chunk, this.compilation.outputOptions), - { - chunk, - contentHashType: "javascript" + getTagData(name, tag) { + const info = this.scope.definitions.get(name); + if (info instanceof VariableInfo) { + let tagInfo = info.tagInfo; + while (tagInfo !== undefined) { + if (tagInfo.tag === tag) return tagInfo.data; + tagInfo = tagInfo.next; } - ); - const rootOutputDir = getUndoPath( - outputName, - this.compilation.outputOptions.path, - false - ); - - const stateExpression = withHmr - ? `${RuntimeGlobals.hmrRuntimeStatePrefix}_readFileVm` - : undefined; + } + } - return Template.asString([ - withBaseURI - ? Template.asString([ - `${RuntimeGlobals.baseURI} = require("url").pathToFileURL(${ - rootOutputDir - ? `__dirname + ${JSON.stringify("/" + rootOutputDir)}` - : "__filename" - });` - ]) - : "// no baseURI", - "", - "// object to store loaded chunks", - '// "0" means "already loaded", Promise means loading', - `var installedChunks = ${ - stateExpression ? `${stateExpression} = ${stateExpression} || ` : "" - }{`, - Template.indent( - Array.from(initialChunkIds, id => `${JSON.stringify(id)}: 0`).join( - ",\n" - ) - ), - "};", - "", - withOnChunkLoad - ? `${ - RuntimeGlobals.onChunksLoaded - }.readFileVm = ${runtimeTemplate.returningFunction( - "installedChunks[chunkId] === 0", - "chunkId" - )};` - : "// no on chunks loaded", - "", - withLoading || withExternalInstallChunk - ? `var installChunk = ${runtimeTemplate.basicFunction("chunk", [ - "var moreModules = chunk.modules, chunkIds = chunk.ids, runtime = chunk.runtime;", - "for(var moduleId in moreModules) {", - Template.indent([ - `if(${RuntimeGlobals.hasOwnProperty}(moreModules, moduleId)) {`, - Template.indent([ - `${RuntimeGlobals.moduleFactories}[moduleId] = moreModules[moduleId];` - ]), - "}" - ]), - "}", - `if(runtime) runtime(__webpack_require__);`, - "for(var i = 0; i < chunkIds.length; i++) {", - Template.indent([ - "if(installedChunks[chunkIds[i]]) {", - Template.indent(["installedChunks[chunkIds[i]][0]();"]), - "}", - "installedChunks[chunkIds[i]] = 0;" - ]), - "}", - withOnChunkLoad ? `${RuntimeGlobals.onChunksLoaded}();` : "" - ])};` - : "// no chunk install function needed", - "", - withLoading - ? Template.asString([ - "// ReadFile + VM.run chunk loading for javascript", - `${fn}.readFileVm = function(chunkId, promises) {`, - hasJsMatcher !== false - ? Template.indent([ - "", - "var installedChunkData = installedChunks[chunkId];", - 'if(installedChunkData !== 0) { // 0 means "already installed".', - Template.indent([ - '// array of [resolve, reject, promise] means "currently loading"', - "if(installedChunkData) {", - Template.indent(["promises.push(installedChunkData[2]);"]), - "} else {", - Template.indent([ - hasJsMatcher === true - ? "if(true) { // all chunks have JS" - : `if(${hasJsMatcher("chunkId")}) {`, - Template.indent([ - "// load the chunk and return promise to it", - "var promise = new Promise(function(resolve, reject) {", - Template.indent([ - "installedChunkData = installedChunks[chunkId] = [resolve, reject];", - `var filename = require('path').join(__dirname, ${JSON.stringify( - rootOutputDir - )} + ${ - RuntimeGlobals.getChunkScriptFilename - }(chunkId));`, - "require('fs').readFile(filename, 'utf-8', function(err, content) {", - Template.indent([ - "if(err) return reject(err);", - "var chunk = {};", - "require('vm').runInThisContext('(function(exports, require, __dirname, __filename) {' + content + '\\n})', filename)" + - "(chunk, require, require('path').dirname(filename), filename);", - "installChunk(chunk);" - ]), - "});" - ]), - "});", - "promises.push(installedChunkData[2] = promise);" - ]), - "} else installedChunks[chunkId] = 0;" - ]), - "}" - ]), - "}" - ]) - : Template.indent(["installedChunks[chunkId] = 0;"]), - "};" - ]) - : "// no chunk loading", - "", - withExternalInstallChunk - ? Template.asString([ - "module.exports = __webpack_require__;", - `${RuntimeGlobals.externalInstallChunk} = installChunk;` - ]) - : "// no external install chunk", - "", - withHmr - ? Template.asString([ - "function loadUpdateChunk(chunkId, updatedModulesList) {", - Template.indent([ - "return new Promise(function(resolve, reject) {", - Template.indent([ - `var filename = require('path').join(__dirname, ${JSON.stringify( - rootOutputDir - )} + ${RuntimeGlobals.getChunkUpdateScriptFilename}(chunkId));`, - "require('fs').readFile(filename, 'utf-8', function(err, content) {", - Template.indent([ - "if(err) return reject(err);", - "var update = {};", - "require('vm').runInThisContext('(function(exports, require, __dirname, __filename) {' + content + '\\n})', filename)" + - "(update, require, require('path').dirname(filename), filename);", - "var updatedModules = update.modules;", - "var runtime = update.runtime;", - "for(var moduleId in updatedModules) {", - Template.indent([ - `if(${RuntimeGlobals.hasOwnProperty}(updatedModules, moduleId)) {`, - Template.indent([ - `currentUpdate[moduleId] = updatedModules[moduleId];`, - "if(updatedModulesList) updatedModulesList.push(moduleId);" - ]), - "}" - ]), - "}", - "if(runtime) currentUpdateRuntime.push(runtime);", - "resolve();" - ]), - "});" - ]), - "});" - ]), - "}", - "", - Template.getFunctionContent( - require('./JavascriptHotModuleReplacement.runtime.js') - ) - .replace(/\$key\$/g, "readFileVm") - .replace(/\$installedChunks\$/g, "installedChunks") - .replace(/\$loadUpdateChunk\$/g, "loadUpdateChunk") - .replace(/\$moduleCache\$/g, RuntimeGlobals.moduleCache) - .replace(/\$moduleFactories\$/g, RuntimeGlobals.moduleFactories) - .replace( - /\$ensureChunkHandlers\$/g, - RuntimeGlobals.ensureChunkHandlers - ) - .replace(/\$hasOwnProperty\$/g, RuntimeGlobals.hasOwnProperty) - .replace(/\$hmrModuleData\$/g, RuntimeGlobals.hmrModuleData) - .replace( - /\$hmrDownloadUpdateHandlers\$/g, - RuntimeGlobals.hmrDownloadUpdateHandlers - ) - .replace( - /\$hmrInvalidateModuleHandlers\$/g, - RuntimeGlobals.hmrInvalidateModuleHandlers - ) - ]) - : "// no HMR", - "", - withHmrManifest - ? Template.asString([ - `${RuntimeGlobals.hmrDownloadManifest} = function() {`, - Template.indent([ - "return new Promise(function(resolve, reject) {", - Template.indent([ - `var filename = require('path').join(__dirname, ${JSON.stringify( - rootOutputDir - )} + ${RuntimeGlobals.getUpdateManifestFilename}());`, - "require('fs').readFile(filename, 'utf-8', function(err, content) {", - Template.indent([ - "if(err) {", - Template.indent([ - 'if(err.code === "ENOENT") return resolve();', - "return reject(err);" - ]), - "}", - "try { resolve(JSON.parse(content)); }", - "catch(e) { reject(e); }" - ]), - "});" - ]), - "});" - ]), - "}" - ]) - : "// no HMR manifest" - ]); + tagVariable(name, tag, data) { + const oldInfo = this.scope.definitions.get(name); + /** @type {VariableInfo} */ + let newInfo; + if (oldInfo === undefined) { + newInfo = new VariableInfo(this.scope, name, { + tag, + data, + next: undefined + }); + } else if (oldInfo instanceof VariableInfo) { + newInfo = new VariableInfo(oldInfo.declaredScope, oldInfo.freeName, { + tag, + data, + next: oldInfo.tagInfo + }); + } else { + newInfo = new VariableInfo(oldInfo, true, { + tag, + data, + next: undefined + }); + } + this.scope.definitions.set(name, newInfo); } -} -module.exports = ReadFileChunkLoadingRuntimeModule; + defineVariable(name) { + const oldInfo = this.scope.definitions.get(name); + // Don't redefine variable in same scope to keep existing tags + if (oldInfo instanceof VariableInfo && oldInfo.declaredScope === this.scope) + return; + this.scope.definitions.set(name, this.scope); + } + undefineVariable(name) { + this.scope.definitions.delete(name); + } -/***/ }), + isVariableDefined(name) { + const info = this.scope.definitions.get(name); + if (info === undefined) return false; + if (info instanceof VariableInfo) { + return info.freeName === true; + } + return true; + } -/***/ 82138: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + /** + * @param {string} name variable name + * @returns {ExportedVariableInfo} info for this variable + */ + getVariableInfo(name) { + const value = this.scope.definitions.get(name); + if (value === undefined) { + return name; + } else { + return value; + } + } -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ + /** + * @param {string} name variable name + * @param {ExportedVariableInfo} variableInfo new info for this variable + * @returns {void} + */ + setVariable(name, variableInfo) { + if (typeof variableInfo === "string") { + if (variableInfo === name) { + this.scope.definitions.delete(name); + } else { + this.scope.definitions.set( + name, + new VariableInfo(this.scope, variableInfo, undefined) + ); + } + } else { + this.scope.definitions.set(name, variableInfo); + } + } + parseCommentOptions(range) { + const comments = this.getComments(range); + if (comments.length === 0) { + return EMPTY_COMMENT_OPTIONS; + } + let options = {}; + let errors = []; + for (const comment of comments) { + const { value } = comment; + if (value && webpackCommentRegExp.test(value)) { + // try compile only if webpack options comment is present + try { + const val = vm.runInNewContext(`(function(){return {${value}};})()`); + Object.assign(options, val); + } catch (e) { + e.comment = comment; + errors.push(e); + } + } + } + return { options, errors }; + } + /** + * @param {MemberExpressionNode} expression a member expression + * @returns {{ members: string[], object: ExpressionNode | SuperNode }} member names (reverse order) and remaining object + */ + extractMemberExpressionChain(expression) { + /** @type {AnyNode} */ + let expr = expression; + const members = []; + while (expr.type === "MemberExpression") { + if (expr.computed) { + if (expr.property.type !== "Literal") break; + members.push(`${expr.property.value}`); + } else { + if (expr.property.type !== "Identifier") break; + members.push(expr.property.name); + } + expr = expr.object; + } + return { + members, + object: expr + }; + } -const RuntimeGlobals = __webpack_require__(49404); -const Template = __webpack_require__(92066); -const AsyncWasmLoadingRuntimeModule = __webpack_require__(84465); + /** + * @param {string} varName variable name + * @returns {{name: string, info: VariableInfo | string}} name of the free variable and variable info for that + */ + getFreeInfoFromVariable(varName) { + const info = this.getVariableInfo(varName); + let name; + if (info instanceof VariableInfo) { + name = info.freeName; + if (typeof name !== "string") return undefined; + } else if (typeof info !== "string") { + return undefined; + } else { + name = info; + } + return { info, name }; + } -/** @typedef {import("../Compiler")} Compiler */ + /** @typedef {{ type: "call", call: CallExpressionNode, calleeName: string, rootInfo: string | VariableInfo, getCalleeMembers: () => string[], name: string, getMembers: () => string[]}} CallExpressionInfo */ + /** @typedef {{ type: "expression", rootInfo: string | VariableInfo, name: string, getMembers: () => string[]}} ExpressionExpressionInfo */ -class ReadFileCompileAsyncWasmPlugin { - constructor({ type = "async-node", import: useImport = false } = {}) { - this._type = type; - this._import = useImport; - } /** - * Apply the plugin - * @param {Compiler} compiler the compiler instance - * @returns {void} + * @param {MemberExpressionNode} expression a member expression + * @param {number} allowedTypes which types should be returned, presented in bit mask + * @returns {CallExpressionInfo | ExpressionExpressionInfo | undefined} expression info */ - apply(compiler) { - compiler.hooks.thisCompilation.tap( - "ReadFileCompileAsyncWasmPlugin", - compilation => { - const globalWasmLoading = compilation.outputOptions.wasmLoading; - const isEnabledForChunk = chunk => { - const options = chunk.getEntryOptions(); - const wasmLoading = - options && options.wasmLoading !== undefined - ? options.wasmLoading - : globalWasmLoading; - return wasmLoading === this._type; + getMemberExpressionInfo(expression, allowedTypes) { + const { object, members } = this.extractMemberExpressionChain(expression); + switch (object.type) { + case "CallExpression": { + if ((allowedTypes & ALLOWED_MEMBER_TYPES_CALL_EXPRESSION) === 0) + return undefined; + let callee = object.callee; + let rootMembers = EMPTY_ARRAY; + if (callee.type === "MemberExpression") { + ({ object: callee, members: rootMembers } = + this.extractMemberExpressionChain(callee)); + } + const rootName = getRootName(callee); + if (!rootName) return undefined; + const result = this.getFreeInfoFromVariable(rootName); + if (!result) return undefined; + const { info: rootInfo, name: resolvedRoot } = result; + const calleeName = objectAndMembersToName(resolvedRoot, rootMembers); + return { + type: "call", + call: object, + calleeName, + rootInfo, + getCalleeMembers: memoize(() => rootMembers.reverse()), + name: objectAndMembersToName(`${calleeName}()`, members), + getMembers: memoize(() => members.reverse()) }; - const generateLoadBinaryCode = this._import - ? path => - Template.asString([ - "Promise.all([import('fs'), import('url')]).then(([{ readFile }, { URL }]) => new Promise((resolve, reject) => {", - Template.indent([ - `readFile(new URL(${path}, import.meta.url), (err, buffer) => {`, - Template.indent([ - "if (err) return reject(err);", - "", - "// Fake fetch response", - "resolve({", - Template.indent(["arrayBuffer() { return buffer; }"]), - "});" - ]), - "});" - ]), - "}))" - ]) - : path => - Template.asString([ - "new Promise(function (resolve, reject) {", - Template.indent([ - "try {", - Template.indent([ - "var { readFile } = require('fs');", - "var { join } = require('path');", - "", - `readFile(join(__dirname, ${path}), function(err, buffer){`, - Template.indent([ - "if (err) return reject(err);", - "", - "// Fake fetch response", - "resolve({", - Template.indent(["arrayBuffer() { return buffer; }"]), - "});" - ]), - "});" - ]), - "} catch (err) { reject(err); }" - ]), - "})" - ]); + } + case "Identifier": + case "MetaProperty": + case "ThisExpression": { + if ((allowedTypes & ALLOWED_MEMBER_TYPES_EXPRESSION) === 0) + return undefined; + const rootName = getRootName(object); + if (!rootName) return undefined; - compilation.hooks.runtimeRequirementInTree - .for(RuntimeGlobals.instantiateWasm) - .tap("ReadFileCompileAsyncWasmPlugin", (chunk, set) => { - if (!isEnabledForChunk(chunk)) return; - const chunkGraph = compilation.chunkGraph; - if ( - !chunkGraph.hasModuleInGraph( - chunk, - m => m.type === "webassembly/async" - ) - ) { - return; - } - set.add(RuntimeGlobals.publicPath); - compilation.addRuntimeModule( - chunk, - new AsyncWasmLoadingRuntimeModule({ - generateLoadBinaryCode, - supportsStreaming: false - }) - ); - }); + const result = this.getFreeInfoFromVariable(rootName); + if (!result) return undefined; + const { info: rootInfo, name: resolvedRoot } = result; + return { + type: "expression", + name: objectAndMembersToName(resolvedRoot, members), + rootInfo, + getMembers: memoize(() => members.reverse()) + }; } + } + } + + /** + * @param {MemberExpressionNode} expression an expression + * @returns {{ name: string, rootInfo: ExportedVariableInfo, getMembers: () => string[]}} name info + */ + getNameForExpression(expression) { + return this.getMemberExpressionInfo( + expression, + ALLOWED_MEMBER_TYPES_EXPRESSION ); } + + /** + * @param {string} code source code + * @param {ParseOptions} options parsing options + * @returns {ProgramNode} parsed ast + */ + static _parse(code, options) { + const type = options ? options.sourceType : "module"; + /** @type {AcornOptions} */ + const parserOptions = { + ...defaultParserOptions, + allowReturnOutsideFunction: type === "script", + ...options, + sourceType: type === "auto" ? "module" : type + }; + + /** @type {AnyNode} */ + let ast; + let error; + let threw = false; + try { + ast = /** @type {AnyNode} */ (parser.parse(code, parserOptions)); + } catch (e) { + error = e; + threw = true; + } + + if (threw && type === "auto") { + parserOptions.sourceType = "script"; + if (!("allowReturnOutsideFunction" in options)) { + parserOptions.allowReturnOutsideFunction = true; + } + if (Array.isArray(parserOptions.onComment)) { + parserOptions.onComment.length = 0; + } + try { + ast = /** @type {AnyNode} */ (parser.parse(code, parserOptions)); + threw = false; + } catch (e) { + // we use the error from first parse try + // so nothing to do here + } + } + + if (threw) { + throw error; + } + + return /** @type {ProgramNode} */ (ast); + } } -module.exports = ReadFileCompileAsyncWasmPlugin; +module.exports = JavascriptParser; +module.exports.ALLOWED_MEMBER_TYPES_ALL = ALLOWED_MEMBER_TYPES_ALL; +module.exports.ALLOWED_MEMBER_TYPES_EXPRESSION = + ALLOWED_MEMBER_TYPES_EXPRESSION; +module.exports.ALLOWED_MEMBER_TYPES_CALL_EXPRESSION = + ALLOWED_MEMBER_TYPES_CALL_EXPRESSION; /***/ }), -/***/ 98724: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { +/***/ 28723: +/***/ (function(__unused_webpack_module, exports, __webpack_require__) { "use strict"; /* @@ -100400,328 +98237,274 @@ module.exports = ReadFileCompileAsyncWasmPlugin; -const RuntimeGlobals = __webpack_require__(49404); -const Template = __webpack_require__(92066); -const WasmChunkLoadingRuntimeModule = __webpack_require__(92153); +const UnsupportedFeatureWarning = __webpack_require__(9532); +const ConstDependency = __webpack_require__(60864); +const BasicEvaluatedExpression = __webpack_require__(2412); -/** @typedef {import("../Compiler")} Compiler */ +/** @typedef {import("estree").Expression} ExpressionNode */ +/** @typedef {import("estree").Node} Node */ +/** @typedef {import("./JavascriptParser")} JavascriptParser */ -// TODO webpack 6 remove +/** + * @param {JavascriptParser} parser the parser + * @param {string} value the const value + * @param {string[]=} runtimeRequirements runtime requirements + * @returns {function(ExpressionNode): true} plugin function + */ +exports.toConstantDependency = (parser, value, runtimeRequirements) => { + return function constDependency(expr) { + const dep = new ConstDependency(value, expr.range, runtimeRequirements); + dep.loc = expr.loc; + parser.state.module.addPresentationalDependency(dep); + return true; + }; +}; -class ReadFileCompileWasmPlugin { - constructor(options) { - this.options = options || {}; - } +/** + * @param {string} value the string value + * @returns {function(ExpressionNode): BasicEvaluatedExpression} plugin function + */ +exports.evaluateToString = value => { + return function stringExpression(expr) { + return new BasicEvaluatedExpression().setString(value).setRange(expr.range); + }; +}; - /** - * Apply the plugin - * @param {Compiler} compiler the compiler instance - * @returns {void} - */ - apply(compiler) { - compiler.hooks.thisCompilation.tap( - "ReadFileCompileWasmPlugin", - compilation => { - const globalWasmLoading = compilation.outputOptions.wasmLoading; - const isEnabledForChunk = chunk => { - const options = chunk.getEntryOptions(); - const wasmLoading = - options && options.wasmLoading !== undefined - ? options.wasmLoading - : globalWasmLoading; - return wasmLoading === "async-node"; - }; - const generateLoadBinaryCode = path => - Template.asString([ - "new Promise(function (resolve, reject) {", - Template.indent([ - "var { readFile } = require('fs');", - "var { join } = require('path');", - "", - "try {", - Template.indent([ - `readFile(join(__dirname, ${path}), function(err, buffer){`, - Template.indent([ - "if (err) return reject(err);", - "", - "// Fake fetch response", - "resolve({", - Template.indent(["arrayBuffer() { return buffer; }"]), - "});" - ]), - "});" - ]), - "} catch (err) { reject(err); }" - ]), - "})" - ]); +/** + * @param {number} value the number value + * @returns {function(ExpressionNode): BasicEvaluatedExpression} plugin function + */ +exports.evaluateToNumber = value => { + return function stringExpression(expr) { + return new BasicEvaluatedExpression().setNumber(value).setRange(expr.range); + }; +}; - compilation.hooks.runtimeRequirementInTree - .for(RuntimeGlobals.ensureChunkHandlers) - .tap("ReadFileCompileWasmPlugin", (chunk, set) => { - if (!isEnabledForChunk(chunk)) return; - const chunkGraph = compilation.chunkGraph; - if ( - !chunkGraph.hasModuleInGraph( - chunk, - m => m.type === "webassembly/sync" - ) - ) { - return; - } - set.add(RuntimeGlobals.moduleCache); - compilation.addRuntimeModule( - chunk, - new WasmChunkLoadingRuntimeModule({ - generateLoadBinaryCode, - supportsStreaming: false, - mangleImports: this.options.mangleImports, - runtimeRequirements: set - }) - ); - }); - } +/** + * @param {boolean} value the boolean value + * @returns {function(ExpressionNode): BasicEvaluatedExpression} plugin function + */ +exports.evaluateToBoolean = value => { + return function booleanExpression(expr) { + return new BasicEvaluatedExpression() + .setBoolean(value) + .setRange(expr.range); + }; +}; + +/** + * @param {string} identifier identifier + * @param {string} rootInfo rootInfo + * @param {function(): string[]} getMembers getMembers + * @param {boolean|null=} truthy is truthy, null if nullish + * @returns {function(ExpressionNode): BasicEvaluatedExpression} callback + */ +exports.evaluateToIdentifier = (identifier, rootInfo, getMembers, truthy) => { + return function identifierExpression(expr) { + let evaluatedExpression = new BasicEvaluatedExpression() + .setIdentifier(identifier, rootInfo, getMembers) + .setSideEffects(false) + .setRange(expr.range); + switch (truthy) { + case true: + evaluatedExpression.setTruthy(); + break; + case null: + evaluatedExpression.setNullish(true); + break; + case false: + evaluatedExpression.setFalsy(); + break; + } + + return evaluatedExpression; + }; +}; + +exports.expressionIsUnsupported = (parser, message) => { + return function unsupportedExpression(expr) { + const dep = new ConstDependency("(void 0)", expr.range, null); + dep.loc = expr.loc; + parser.state.module.addPresentationalDependency(dep); + if (!parser.state.module) return; + parser.state.module.addWarning( + new UnsupportedFeatureWarning(message, expr.loc) ); - } -} + return true; + }; +}; -module.exports = ReadFileCompileWasmPlugin; +exports.skipTraversal = () => true; + +exports.approve = () => true; /***/ }), -/***/ 37181: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { +/***/ 30951: +/***/ (function(__unused_webpack_module, exports, __webpack_require__) { "use strict"; /* MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra */ +const Entrypoint = __webpack_require__(86695); const RuntimeGlobals = __webpack_require__(49404); -const RuntimeModule = __webpack_require__(61439); const Template = __webpack_require__(92066); -const { - chunkHasJs, - getChunkFilenameTemplate -} = __webpack_require__(76767); -const { getInitialChunkIds } = __webpack_require__(30951); -const compileBooleanMatcher = __webpack_require__(356); -const { getUndoPath } = __webpack_require__(96236); +const { isSubset } = __webpack_require__(34715); +const { chunkHasJs } = __webpack_require__(76767); -class RequireChunkLoadingRuntimeModule extends RuntimeModule { - constructor(runtimeRequirements) { - super("require chunk loading", RuntimeModule.STAGE_ATTACH); - this.runtimeRequirements = runtimeRequirements; - } +/** @typedef {import("../util/Hash")} Hash */ +/** @typedef {import("../Chunk")} Chunk */ +/** @typedef {import("../Compilation")} Compilation */ +/** @typedef {import("../ChunkGraph")} ChunkGraph */ +/** @typedef {import("../ChunkGroup")} ChunkGroup */ +/** @typedef {import("../RuntimeTemplate")} RuntimeTemplate */ +/** @typedef {(string|number)[]} EntryItem */ - /** - * @returns {string} runtime code - */ - generate() { - const { chunkGraph, chunk } = this; - const { runtimeTemplate } = this.compilation; - const fn = RuntimeGlobals.ensureChunkHandlers; - const withBaseURI = this.runtimeRequirements.has(RuntimeGlobals.baseURI); - const withExternalInstallChunk = this.runtimeRequirements.has( - RuntimeGlobals.externalInstallChunk - ); - const withOnChunkLoad = this.runtimeRequirements.has( - RuntimeGlobals.onChunksLoaded - ); - const withLoading = this.runtimeRequirements.has( - RuntimeGlobals.ensureChunkHandlers - ); - const withHmr = this.runtimeRequirements.has( - RuntimeGlobals.hmrDownloadUpdateHandlers - ); - const withHmrManifest = this.runtimeRequirements.has( - RuntimeGlobals.hmrDownloadManifest - ); - const conditionMap = chunkGraph.getChunkConditionMap(chunk, chunkHasJs); - const hasJsMatcher = compileBooleanMatcher(conditionMap); - const initialChunkIds = getInitialChunkIds(chunk, chunkGraph); +// TODO move to this file to ../javascript/ChunkHelpers.js - const outputName = this.compilation.getPath( - getChunkFilenameTemplate(chunk, this.compilation.outputOptions), - { - chunk, - contentHashType: "javascript" - } - ); - const rootOutputDir = getUndoPath( - outputName, - this.compilation.outputOptions.path, - true - ); +/** + * @param {Entrypoint} entrypoint a chunk group + * @param {Chunk} excludedChunk1 current chunk which is excluded + * @param {Chunk} excludedChunk2 runtime chunk which is excluded + * @returns {Set} chunks + */ +const getAllChunks = (entrypoint, excludedChunk1, excludedChunk2) => { + const queue = new Set([entrypoint]); + const chunks = new Set(); + for (const entrypoint of queue) { + for (const chunk of entrypoint.chunks) { + if (chunk === excludedChunk1) continue; + if (chunk === excludedChunk2) continue; + chunks.add(chunk); + } + for (const parent of entrypoint.parentsIterable) { + if (parent instanceof Entrypoint) queue.add(parent); + } + } + return chunks; +}; - const stateExpression = withHmr - ? `${RuntimeGlobals.hmrRuntimeStatePrefix}_require` - : undefined; +const EXPORT_PREFIX = "var __webpack_exports__ = "; - return Template.asString([ - withBaseURI - ? Template.asString([ - `${RuntimeGlobals.baseURI} = require("url").pathToFileURL(${ - rootOutputDir !== "./" - ? `__dirname + ${JSON.stringify("/" + rootOutputDir)}` - : "__filename" - });` - ]) - : "// no baseURI", - "", - "// object to store loaded chunks", - '// "1" means "loaded", otherwise not loaded yet', - `var installedChunks = ${ - stateExpression ? `${stateExpression} = ${stateExpression} || ` : "" - }{`, - Template.indent( - Array.from(initialChunkIds, id => `${JSON.stringify(id)}: 1`).join( - ",\n" - ) - ), - "};", - "", - withOnChunkLoad - ? `${ - RuntimeGlobals.onChunksLoaded - }.require = ${runtimeTemplate.returningFunction( - "installedChunks[chunkId]", - "chunkId" - )};` - : "// no on chunks loaded", - "", - withLoading || withExternalInstallChunk - ? `var installChunk = ${runtimeTemplate.basicFunction("chunk", [ - "var moreModules = chunk.modules, chunkIds = chunk.ids, runtime = chunk.runtime;", - "for(var moduleId in moreModules) {", - Template.indent([ - `if(${RuntimeGlobals.hasOwnProperty}(moreModules, moduleId)) {`, - Template.indent([ - `${RuntimeGlobals.moduleFactories}[moduleId] = moreModules[moduleId];` - ]), - "}" - ]), - "}", - `if(runtime) runtime(__webpack_require__);`, - "for(var i = 0; i < chunkIds.length; i++)", - Template.indent("installedChunks[chunkIds[i]] = 1;"), - withOnChunkLoad ? `${RuntimeGlobals.onChunksLoaded}();` : "" - ])};` - : "// no chunk install function needed", - "", - withLoading - ? Template.asString([ - "// require() chunk loading for javascript", - `${fn}.require = ${runtimeTemplate.basicFunction( - "chunkId, promises", - hasJsMatcher !== false - ? [ - '// "1" is the signal for "already loaded"', - "if(!installedChunks[chunkId]) {", - Template.indent([ - hasJsMatcher === true - ? "if(true) { // all chunks have JS" - : `if(${hasJsMatcher("chunkId")}) {`, - Template.indent([ - `installChunk(require(${JSON.stringify( - rootOutputDir - )} + ${ - RuntimeGlobals.getChunkScriptFilename - }(chunkId)));` - ]), - "} else installedChunks[chunkId] = 1;", - "" - ]), - "}" - ] - : "installedChunks[chunkId] = 1;" - )};` - ]) - : "// no chunk loading", - "", - withExternalInstallChunk - ? Template.asString([ - "module.exports = __webpack_require__;", - `${RuntimeGlobals.externalInstallChunk} = installChunk;` - ]) - : "// no external install chunk", - "", - withHmr - ? Template.asString([ - "function loadUpdateChunk(chunkId, updatedModulesList) {", - Template.indent([ - `var update = require(${JSON.stringify(rootOutputDir)} + ${ - RuntimeGlobals.getChunkUpdateScriptFilename - }(chunkId));`, - "var updatedModules = update.modules;", - "var runtime = update.runtime;", - "for(var moduleId in updatedModules) {", - Template.indent([ - `if(${RuntimeGlobals.hasOwnProperty}(updatedModules, moduleId)) {`, - Template.indent([ - `currentUpdate[moduleId] = updatedModules[moduleId];`, - "if(updatedModulesList) updatedModulesList.push(moduleId);" - ]), - "}" - ]), - "}", - "if(runtime) currentUpdateRuntime.push(runtime);" - ]), - "}", - "", - Template.getFunctionContent( - require('./JavascriptHotModuleReplacement.runtime.js') - ) - .replace(/\$key\$/g, "require") - .replace(/\$installedChunks\$/g, "installedChunks") - .replace(/\$loadUpdateChunk\$/g, "loadUpdateChunk") - .replace(/\$moduleCache\$/g, RuntimeGlobals.moduleCache) - .replace(/\$moduleFactories\$/g, RuntimeGlobals.moduleFactories) - .replace( - /\$ensureChunkHandlers\$/g, - RuntimeGlobals.ensureChunkHandlers - ) - .replace(/\$hasOwnProperty\$/g, RuntimeGlobals.hasOwnProperty) - .replace(/\$hmrModuleData\$/g, RuntimeGlobals.hmrModuleData) - .replace( - /\$hmrDownloadUpdateHandlers\$/g, - RuntimeGlobals.hmrDownloadUpdateHandlers - ) - .replace( - /\$hmrInvalidateModuleHandlers\$/g, - RuntimeGlobals.hmrInvalidateModuleHandlers - ) - ]) - : "// no HMR", - "", - withHmrManifest - ? Template.asString([ - `${RuntimeGlobals.hmrDownloadManifest} = function() {`, - Template.indent([ - "return Promise.resolve().then(function() {", - Template.indent([ - `return require(${JSON.stringify(rootOutputDir)} + ${ - RuntimeGlobals.getUpdateManifestFilename - }());` - ]), - "})['catch'](function(err) { if(err.code !== 'MODULE_NOT_FOUND') throw err; });" - ]), - "}" - ]) - : "// no HMR manifest" - ]); +/** + * @param {ChunkGraph} chunkGraph chunkGraph + * @param {RuntimeTemplate} runtimeTemplate runtimeTemplate + * @param {import("../ChunkGraph").EntryModuleWithChunkGroup[]} entries entries + * @param {Chunk} chunk chunk + * @param {boolean} passive true: passive startup with on chunks loaded + * @returns {string} runtime code + */ +exports.generateEntryStartup = ( + chunkGraph, + runtimeTemplate, + entries, + chunk, + passive +) => { + /** @type {string[]} */ + const runtime = [ + `var __webpack_exec__ = ${runtimeTemplate.returningFunction( + `__webpack_require__(${RuntimeGlobals.entryModuleId} = moduleId)`, + "moduleId" + )}` + ]; + + const runModule = id => { + return `__webpack_exec__(${JSON.stringify(id)})`; + }; + const outputCombination = (chunks, moduleIds, final) => { + if (chunks.size === 0) { + runtime.push( + `${final ? EXPORT_PREFIX : ""}(${moduleIds.map(runModule).join(", ")});` + ); + } else { + const fn = runtimeTemplate.returningFunction( + moduleIds.map(runModule).join(", ") + ); + runtime.push( + `${final && !passive ? EXPORT_PREFIX : ""}${ + passive + ? RuntimeGlobals.onChunksLoaded + : RuntimeGlobals.startupEntrypoint + }(0, ${JSON.stringify(Array.from(chunks, c => c.id))}, ${fn});` + ); + if (final && passive) { + runtime.push(`${EXPORT_PREFIX}${RuntimeGlobals.onChunksLoaded}();`); + } + } + }; + + let currentChunks = undefined; + let currentModuleIds = undefined; + + for (const [module, entrypoint] of entries) { + const runtimeChunk = entrypoint.getRuntimeChunk(); + const moduleId = chunkGraph.getModuleId(module); + const chunks = getAllChunks(entrypoint, chunk, runtimeChunk); + if ( + currentChunks && + currentChunks.size === chunks.size && + isSubset(currentChunks, chunks) + ) { + currentModuleIds.push(moduleId); + } else { + if (currentChunks) { + outputCombination(currentChunks, currentModuleIds); + } + currentChunks = chunks; + currentModuleIds = [moduleId]; + } } -} -module.exports = RequireChunkLoadingRuntimeModule; + // output current modules with export prefix + if (currentChunks) { + outputCombination(currentChunks, currentModuleIds, true); + } + runtime.push(""); + return Template.asString(runtime); +}; + +/** + * @param {Hash} hash the hash to update + * @param {ChunkGraph} chunkGraph chunkGraph + * @param {import("../ChunkGraph").EntryModuleWithChunkGroup[]} entries entries + * @param {Chunk} chunk chunk + * @returns {void} + */ +exports.updateHashForEntryStartup = (hash, chunkGraph, entries, chunk) => { + for (const [module, entrypoint] of entries) { + const runtimeChunk = entrypoint.getRuntimeChunk(); + const moduleId = chunkGraph.getModuleId(module); + hash.update(`${moduleId}`); + for (const c of getAllChunks(entrypoint, chunk, runtimeChunk)) + hash.update(`${c.id}`); + } +}; + +/** + * @param {Chunk} chunk the chunk + * @param {ChunkGraph} chunkGraph the chunk graph + * @returns {Set} initially fulfilled chunk ids + */ +exports.getInitialChunkIds = (chunk, chunkGraph) => { + const initialChunkIds = new Set(chunk.ids); + for (const c of chunk.getAllInitialChunks()) { + if (c === chunk || chunkHasJs(c, chunkGraph)) continue; + for (const id of c.ids) initialChunkIds.add(id); + } + return initialChunkIds; +}; /***/ }), -/***/ 10152: +/***/ 97637: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; @@ -100732,147 +98515,244 @@ module.exports = RequireChunkLoadingRuntimeModule; -const util = __webpack_require__(31669); -const truncateArgs = __webpack_require__(10072); - -module.exports = ({ colors, appendOnly, stream }) => { - let currentStatusMessage = undefined; - let hasStatusMessage = false; - let currentIndent = ""; - let currentCollapsed = 0; +const { register } = __webpack_require__(99551); - const indent = (str, prefix, colorPrefix, colorSuffix) => { - if (str === "") return str; - prefix = currentIndent + prefix; - if (colors) { - return ( - prefix + - colorPrefix + - str.replace(/\n/g, colorSuffix + "\n" + prefix + colorPrefix) + - colorSuffix - ); +class JsonData { + constructor(data) { + this._buffer = undefined; + this._data = undefined; + if (Buffer.isBuffer(data)) { + this._buffer = data; } else { - return prefix + str.replace(/\n/g, "\n" + prefix); + this._data = data; } - }; + } - const clearStatusMessage = () => { - if (hasStatusMessage) { - stream.write("\x1b[2K\r"); - hasStatusMessage = false; + get() { + if (this._data === undefined && this._buffer !== undefined) { + this._data = JSON.parse(this._buffer.toString()); } - }; + return this._data; + } +} - const writeStatusMessage = () => { - if (!currentStatusMessage) return; - const l = stream.columns; - const args = l - ? truncateArgs(currentStatusMessage, l - 1) - : currentStatusMessage; - const str = args.join(" "); - const coloredStr = `\u001b[1m${str}\u001b[39m\u001b[22m`; - stream.write(`\x1b[2K\r${coloredStr}`); - hasStatusMessage = true; - }; +register(JsonData, "webpack/lib/json/JsonData", null, { + serialize(obj, { write }) { + if (obj._buffer === undefined && obj._data !== undefined) { + obj._buffer = Buffer.from(JSON.stringify(obj._data)); + } + write(obj._buffer); + }, + deserialize({ read }) { + return new JsonData(read()); + } +}); - const writeColored = (prefix, colorPrefix, colorSuffix) => { - return (...args) => { - if (currentCollapsed > 0) return; - clearStatusMessage(); - const str = indent( - util.format(...args), - prefix, - colorPrefix, - colorSuffix - ); - stream.write(str + "\n"); - writeStatusMessage(); - }; - }; +module.exports = JsonData; - const writeGroupMessage = writeColored( - "<-> ", - "\u001b[1m\u001b[36m", - "\u001b[39m\u001b[22m" - ); - const writeGroupCollapsedMessage = writeColored( - "<+> ", - "\u001b[1m\u001b[36m", - "\u001b[39m\u001b[22m" - ); +/***/ }), - return { - log: writeColored(" ", "\u001b[1m", "\u001b[22m"), - debug: writeColored(" ", "", ""), - trace: writeColored(" ", "", ""), - info: writeColored(" ", "\u001b[1m\u001b[32m", "\u001b[39m\u001b[22m"), - warn: writeColored(" ", "\u001b[1m\u001b[33m", "\u001b[39m\u001b[22m"), - error: writeColored(" ", "\u001b[1m\u001b[31m", "\u001b[39m\u001b[22m"), - logTime: writeColored( - " ", - "\u001b[1m\u001b[35m", - "\u001b[39m\u001b[22m" - ), - group: (...args) => { - writeGroupMessage(...args); - if (currentCollapsed > 0) { - currentCollapsed++; +/***/ 38140: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ + + + +const { RawSource } = __webpack_require__(96192); +const ConcatenationScope = __webpack_require__(14067); +const { UsageState } = __webpack_require__(4295); +const Generator = __webpack_require__(1826); +const RuntimeGlobals = __webpack_require__(49404); + +/** @typedef {import("webpack-sources").Source} Source */ +/** @typedef {import("../ExportsInfo")} ExportsInfo */ +/** @typedef {import("../Generator").GenerateContext} GenerateContext */ +/** @typedef {import("../Module").ConcatenationBailoutReasonContext} ConcatenationBailoutReasonContext */ +/** @typedef {import("../NormalModule")} NormalModule */ +/** @typedef {import("../util/runtime").RuntimeSpec} RuntimeSpec */ + +const stringifySafe = data => { + const stringified = JSON.stringify(data); + if (!stringified) { + return undefined; // Invalid JSON + } + + return stringified.replace(/\u2028|\u2029/g, str => + str === "\u2029" ? "\\u2029" : "\\u2028" + ); // invalid in JavaScript but valid JSON +}; + +/** + * @param {Object} data data (always an object or array) + * @param {ExportsInfo} exportsInfo exports info + * @param {RuntimeSpec} runtime the runtime + * @returns {Object} reduced data + */ +const createObjectForExportsInfo = (data, exportsInfo, runtime) => { + if (exportsInfo.otherExportsInfo.getUsed(runtime) !== UsageState.Unused) + return data; + const isArray = Array.isArray(data); + const reducedData = isArray ? [] : {}; + for (const key of Object.keys(data)) { + const exportInfo = exportsInfo.getReadOnlyExportInfo(key); + const used = exportInfo.getUsed(runtime); + if (used === UsageState.Unused) continue; + + let value; + if (used === UsageState.OnlyPropertiesUsed && exportInfo.exportsInfo) { + value = createObjectForExportsInfo( + data[key], + exportInfo.exportsInfo, + runtime + ); + } else { + value = data[key]; + } + const name = exportInfo.getUsedName(key, runtime); + reducedData[name] = value; + } + if (isArray) { + let arrayLengthWhenUsed = + exportsInfo.getReadOnlyExportInfo("length").getUsed(runtime) !== + UsageState.Unused + ? data.length + : undefined; + + let sizeObjectMinusArray = 0; + for (let i = 0; i < reducedData.length; i++) { + if (reducedData[i] === undefined) { + sizeObjectMinusArray -= 2; } else { - currentIndent += " "; + sizeObjectMinusArray += `${i}`.length + 3; } - }, - groupCollapsed: (...args) => { - writeGroupCollapsedMessage(...args); - currentCollapsed++; - }, - groupEnd: () => { - if (currentCollapsed > 0) currentCollapsed--; - else if (currentIndent.length >= 2) - currentIndent = currentIndent.slice(0, currentIndent.length - 2); - }, - // eslint-disable-next-line node/no-unsupported-features/node-builtins - profile: console.profile && (name => console.profile(name)), - // eslint-disable-next-line node/no-unsupported-features/node-builtins - profileEnd: console.profileEnd && (name => console.profileEnd(name)), - clear: - !appendOnly && - // eslint-disable-next-line node/no-unsupported-features/node-builtins - console.clear && - (() => { - clearStatusMessage(); - // eslint-disable-next-line node/no-unsupported-features/node-builtins - console.clear(); - writeStatusMessage(); - }), - status: appendOnly - ? writeColored(" ", "", "") - : (name, ...args) => { - args = args.filter(Boolean); - if (name === undefined && args.length === 0) { - clearStatusMessage(); - currentStatusMessage = undefined; - } else if ( - typeof name === "string" && - name.startsWith("[webpack.Progress] ") - ) { - currentStatusMessage = [name.slice(19), ...args]; - writeStatusMessage(); - } else if (name === "[webpack.Progress]") { - currentStatusMessage = [...args]; - writeStatusMessage(); - } else { - currentStatusMessage = [name, ...args]; - writeStatusMessage(); - } - } - }; + } + if (arrayLengthWhenUsed !== undefined) { + sizeObjectMinusArray += + `${arrayLengthWhenUsed}`.length + + 8 - + (arrayLengthWhenUsed - reducedData.length) * 2; + } + if (sizeObjectMinusArray < 0) + return Object.assign( + arrayLengthWhenUsed === undefined + ? {} + : { length: arrayLengthWhenUsed }, + reducedData + ); + const generatedLength = + arrayLengthWhenUsed !== undefined + ? Math.max(arrayLengthWhenUsed, reducedData.length) + : reducedData.length; + for (let i = 0; i < generatedLength; i++) { + if (reducedData[i] === undefined) { + reducedData[i] = 0; + } + } + } + return reducedData; }; +const TYPES = new Set(["javascript"]); + +class JsonGenerator extends Generator { + /** + * @param {NormalModule} module fresh module + * @returns {Set} available types (do not mutate) + */ + getTypes(module) { + return TYPES; + } + + /** + * @param {NormalModule} module the module + * @param {string=} type source type + * @returns {number} estimate size of the module + */ + getSize(module, type) { + let data = + module.buildInfo && + module.buildInfo.jsonData && + module.buildInfo.jsonData.get(); + if (!data) return 0; + return stringifySafe(data).length + 10; + } + + /** + * @param {NormalModule} module module for which the bailout reason should be determined + * @param {ConcatenationBailoutReasonContext} context context + * @returns {string | undefined} reason why this module can't be concatenated, undefined when it can be concatenated + */ + getConcatenationBailoutReason(module, context) { + return undefined; + } + + /** + * @param {NormalModule} module module for which the code should be generated + * @param {GenerateContext} generateContext context for generate + * @returns {Source} generated code + */ + generate( + module, + { + moduleGraph, + runtimeTemplate, + runtimeRequirements, + runtime, + concatenationScope + } + ) { + const data = + module.buildInfo && + module.buildInfo.jsonData && + module.buildInfo.jsonData.get(); + if (data === undefined) { + return new RawSource( + runtimeTemplate.missingModuleStatement({ + request: module.rawRequest + }) + ); + } + const exportsInfo = moduleGraph.getExportsInfo(module); + let finalJson = + typeof data === "object" && + data && + exportsInfo.otherExportsInfo.getUsed(runtime) === UsageState.Unused + ? createObjectForExportsInfo(data, exportsInfo, runtime) + : data; + // Use JSON because JSON.parse() is much faster than JavaScript evaluation + const jsonStr = stringifySafe(finalJson); + const jsonExpr = + jsonStr.length > 20 && typeof finalJson === "object" + ? `JSON.parse('${jsonStr.replace(/[\\']/g, "\\$&")}')` + : jsonStr; + let content; + if (concatenationScope) { + content = `${runtimeTemplate.supportsConst() ? "const" : "var"} ${ + ConcatenationScope.NAMESPACE_OBJECT_EXPORT + } = ${jsonExpr};`; + concatenationScope.registerNamespaceExport( + ConcatenationScope.NAMESPACE_OBJECT_EXPORT + ); + } else { + runtimeRequirements.add(RuntimeGlobals.module); + content = `${module.moduleArgument}.exports = ${jsonExpr};`; + } + return new RawSource(content); + } +} + +module.exports = JsonGenerator; + /***/ }), -/***/ 8239: +/***/ 8841: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; @@ -100883,96 +98763,119 @@ module.exports = ({ colors, appendOnly, stream }) => { -const { STAGE_ADVANCED } = __webpack_require__(68145); +const createSchemaValidation = __webpack_require__(77695); +const JsonGenerator = __webpack_require__(38140); +const JsonParser = __webpack_require__(27679); -/** @typedef {import("../Chunk")} Chunk */ /** @typedef {import("../Compiler")} Compiler */ -class AggressiveMergingPlugin { - constructor(options) { - if ( - (options !== undefined && typeof options !== "object") || - Array.isArray(options) - ) { - throw new Error( - "Argument should be an options object. To use defaults, pass in nothing.\nFor more info on options, see https://webpack.js.org/plugins/" - ); - } - this.options = options || {}; +const validate = createSchemaValidation( + __webpack_require__(95306), + () => __webpack_require__(15685), + { + name: "Json Modules Plugin", + baseDataPath: "parser" } +); +class JsonModulesPlugin { /** * Apply the plugin * @param {Compiler} compiler the compiler instance * @returns {void} */ apply(compiler) { - const options = this.options; - const minSizeReduce = options.minSizeReduce || 1.5; + compiler.hooks.compilation.tap( + "JsonModulesPlugin", + (compilation, { normalModuleFactory }) => { + normalModuleFactory.hooks.createParser + .for("json") + .tap("JsonModulesPlugin", parserOptions => { + validate(parserOptions); - compiler.hooks.thisCompilation.tap( - "AggressiveMergingPlugin", - compilation => { - compilation.hooks.optimizeChunks.tap( - { - name: "AggressiveMergingPlugin", - stage: STAGE_ADVANCED - }, - chunks => { - const chunkGraph = compilation.chunkGraph; - /** @type {{a: Chunk, b: Chunk, improvement: number}[]} */ - let combinations = []; - for (const a of chunks) { - if (a.canBeInitial()) continue; - for (const b of chunks) { - if (b.canBeInitial()) continue; - if (b === a) break; - if (!chunkGraph.canChunksBeIntegrated(a, b)) { - continue; - } - const aSize = chunkGraph.getChunkSize(b, { - chunkOverhead: 0 - }); - const bSize = chunkGraph.getChunkSize(a, { - chunkOverhead: 0 - }); - const abSize = chunkGraph.getIntegratedChunksSize(b, a, { - chunkOverhead: 0 - }); - const improvement = (aSize + bSize) / abSize; - combinations.push({ - a, - b, - improvement - }); - } - } + return new JsonParser(parserOptions); + }); + normalModuleFactory.hooks.createGenerator + .for("json") + .tap("JsonModulesPlugin", () => { + return new JsonGenerator(); + }); + } + ); + } +} - combinations.sort((a, b) => { - return b.improvement - a.improvement; - }); +module.exports = JsonModulesPlugin; - const pair = combinations[0]; - if (!pair) return; - if (pair.improvement < minSizeReduce) return; +/***/ }), - chunkGraph.integrateChunks(pair.b, pair.a); - compilation.chunks.delete(pair.a); - return true; - } - ); - } +/***/ 27679: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ + + + +const parseJson = __webpack_require__(48335); +const Parser = __webpack_require__(68214); +const JsonExportsDependency = __webpack_require__(36986); +const JsonData = __webpack_require__(97637); + +/** @typedef {import("../../declarations/plugins/JsonModulesPluginParser").JsonModulesPluginParserOptions} JsonModulesPluginParserOptions */ +/** @typedef {import("../Parser").ParserState} ParserState */ +/** @typedef {import("../Parser").PreparsedAst} PreparsedAst */ + +class JsonParser extends Parser { + /** + * @param {JsonModulesPluginParserOptions} options parser options + */ + constructor(options) { + super(); + this.options = options || {}; + } + + /** + * @param {string | Buffer | PreparsedAst} source the source to parse + * @param {ParserState} state the parser state + * @returns {ParserState} the parser state + */ + parse(source, state) { + if (Buffer.isBuffer(source)) { + source = source.toString("utf-8"); + } + + /** @type {JsonModulesPluginParserOptions["parse"]} */ + const parseFn = + typeof this.options.parse === "function" ? this.options.parse : parseJson; + + const data = + typeof source === "object" + ? source + : parseFn(source[0] === "\ufeff" ? source.slice(1) : source); + + state.module.buildInfo.jsonData = new JsonData(data); + state.module.buildInfo.strict = true; + state.module.buildMeta.exportsType = "default"; + state.module.buildMeta.defaultObject = + typeof data === "object" ? "redirect-warn" : false; + state.module.addDependency( + new JsonExportsDependency(JsonExportsDependency.getExportsFromData(data)) ); + return state; } } -module.exports = AggressiveMergingPlugin; +module.exports = JsonParser; /***/ }), -/***/ 10055: +/***/ 94051: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; @@ -100983,80 +98886,46 @@ module.exports = AggressiveMergingPlugin; -const { STAGE_ADVANCED } = __webpack_require__(68145); -const { intersect } = __webpack_require__(34715); -const { - compareModulesByIdentifier, - compareChunks -} = __webpack_require__(26296); -const createSchemaValidation = __webpack_require__(77695); -const identifierUtils = __webpack_require__(96236); +const RuntimeGlobals = __webpack_require__(49404); +const JavascriptModulesPlugin = __webpack_require__(76767); -/** @typedef {import("../../declarations/plugins/optimize/AggressiveSplittingPlugin").AggressiveSplittingPluginOptions} AggressiveSplittingPluginOptions */ +/** @typedef {import("webpack-sources").Source} Source */ +/** @typedef {import("../../declarations/WebpackOptions").LibraryOptions} LibraryOptions */ +/** @typedef {import("../../declarations/WebpackOptions").LibraryType} LibraryType */ /** @typedef {import("../Chunk")} Chunk */ /** @typedef {import("../ChunkGraph")} ChunkGraph */ +/** @typedef {import("../Compilation")} Compilation */ +/** @typedef {import("../Compilation").ChunkHashContext} ChunkHashContext */ /** @typedef {import("../Compiler")} Compiler */ /** @typedef {import("../Module")} Module */ +/** @typedef {import("../javascript/JavascriptModulesPlugin").RenderContext} RenderContext */ +/** @typedef {import("../javascript/JavascriptModulesPlugin").StartupRenderContext} StartupRenderContext */ +/** @typedef {import("../util/Hash")} Hash */ -const validate = createSchemaValidation( - __webpack_require__(70603), - () => - __webpack_require__(3572), - { - name: "Aggressive Splitting Plugin", - baseDataPath: "options" - } -); - -const moveModuleBetween = (chunkGraph, oldChunk, newChunk) => { - return module => { - chunkGraph.disconnectChunkAndModule(oldChunk, module); - chunkGraph.connectChunkAndModule(newChunk, module); - }; -}; +const COMMON_LIBRARY_NAME_MESSAGE = + "Common configuration options that specific library names are 'output.library[.name]', 'entry.xyz.library[.name]', 'ModuleFederationPlugin.name' and 'ModuleFederationPlugin.library[.name]'."; /** - * @param {ChunkGraph} chunkGraph the chunk graph - * @param {Chunk} chunk the chunk - * @returns {function(Module): boolean} filter for entry module + * @template T + * @typedef {Object} LibraryContext + * @property {Compilation} compilation + * @property {ChunkGraph} chunkGraph + * @property {T} options */ -const isNotAEntryModule = (chunkGraph, chunk) => { - return module => { - return !chunkGraph.isEntryModuleInChunk(module, chunk); - }; -}; - -/** @type {WeakSet} */ -const recordedChunks = new WeakSet(); - -class AggressiveSplittingPlugin { - /** - * @param {AggressiveSplittingPluginOptions=} options options object - */ - constructor(options = {}) { - validate(options); - - this.options = options; - if (typeof this.options.minSize !== "number") { - this.options.minSize = 30 * 1024; - } - if (typeof this.options.maxSize !== "number") { - this.options.maxSize = 50 * 1024; - } - if (typeof this.options.chunkOverhead !== "number") { - this.options.chunkOverhead = 0; - } - if (typeof this.options.entryChunkMultiplicator !== "number") { - this.options.entryChunkMultiplicator = 1; - } - } +/** + * @template T + */ +class AbstractLibraryPlugin { /** - * @param {Chunk} chunk the chunk to test - * @returns {boolean} true if the chunk was recorded + * @param {Object} options options + * @param {string} options.pluginName name of the plugin + * @param {LibraryType} options.type used library type */ - static wasChunkRecorded(chunk) { - return recordedChunks.has(chunk); + constructor({ pluginName, type }) { + this._pluginName = pluginName; + this._type = type; + this._parseCache = new WeakMap(); } /** @@ -101065,251 +98934,253 @@ class AggressiveSplittingPlugin { * @returns {void} */ apply(compiler) { - compiler.hooks.thisCompilation.tap( - "AggressiveSplittingPlugin", - compilation => { - let needAdditionalSeal = false; - let newSplits; - let fromAggressiveSplittingSet; - let chunkSplitDataMap; - compilation.hooks.optimize.tap("AggressiveSplittingPlugin", () => { - newSplits = []; - fromAggressiveSplittingSet = new Set(); - chunkSplitDataMap = new Map(); - }); - compilation.hooks.optimizeChunks.tap( - { - name: "AggressiveSplittingPlugin", - stage: STAGE_ADVANCED - }, - chunks => { - const chunkGraph = compilation.chunkGraph; - // Precompute stuff - const nameToModuleMap = new Map(); - const moduleToNameMap = new Map(); - const makePathsRelative = - identifierUtils.makePathsRelative.bindContextCache( - compiler.context, - compiler.root - ); - for (const m of compilation.modules) { - const name = makePathsRelative(m.identifier()); - nameToModuleMap.set(name, m); - moduleToNameMap.set(m, name); + const { _pluginName } = this; + compiler.hooks.thisCompilation.tap(_pluginName, compilation => { + compilation.hooks.finishModules.tap( + { name: _pluginName, stage: 10 }, + () => { + for (const [ + name, + { + dependencies: deps, + options: { library } } - - // Check used chunk ids - const usedIds = new Set(); - for (const chunk of chunks) { - usedIds.add(chunk.id); + ] of compilation.entries) { + const options = this._parseOptionsCached( + library !== undefined + ? library + : compilation.outputOptions.library + ); + if (options !== false) { + const dep = deps[deps.length - 1]; + if (dep) { + const module = compilation.moduleGraph.getModule(dep); + if (module) { + this.finishEntryModule(module, name, { + options, + compilation, + chunkGraph: compilation.chunkGraph + }); + } + } } + } + } + ); - const recordedSplits = - (compilation.records && compilation.records.aggressiveSplits) || - []; - const usedSplits = newSplits - ? recordedSplits.concat(newSplits) - : recordedSplits; - - const minSize = this.options.minSize; - const maxSize = this.options.maxSize; - - const applySplit = splitData => { - // Cannot split if id is already taken - if (splitData.id !== undefined && usedIds.has(splitData.id)) { - return false; - } + const getOptionsForChunk = chunk => { + if (compilation.chunkGraph.getNumberOfEntryModules(chunk) === 0) + return false; + const options = chunk.getEntryOptions(); + const library = options && options.library; + return this._parseOptionsCached( + library !== undefined ? library : compilation.outputOptions.library + ); + }; - // Get module objects from names - const selectedModules = splitData.modules.map(name => - nameToModuleMap.get(name) - ); + if ( + this.render !== AbstractLibraryPlugin.prototype.render || + this.runtimeRequirements !== + AbstractLibraryPlugin.prototype.runtimeRequirements + ) { + compilation.hooks.additionalChunkRuntimeRequirements.tap( + _pluginName, + (chunk, set, { chunkGraph }) => { + const options = getOptionsForChunk(chunk); + if (options !== false) { + this.runtimeRequirements(chunk, set, { + options, + compilation, + chunkGraph + }); + } + } + ); + } - // Does the modules exist at all? - if (!selectedModules.every(Boolean)) return false; + const hooks = JavascriptModulesPlugin.getCompilationHooks(compilation); - // Check if size matches (faster than waiting for hash) - let size = 0; - for (const m of selectedModules) size += m.size(); - if (size !== splitData.size) return false; + if (this.render !== AbstractLibraryPlugin.prototype.render) { + hooks.render.tap(_pluginName, (source, renderContext) => { + const options = getOptionsForChunk(renderContext.chunk); + if (options === false) return source; + return this.render(source, renderContext, { + options, + compilation, + chunkGraph: compilation.chunkGraph + }); + }); + } - // get chunks with all modules - const selectedChunks = intersect( - selectedModules.map( - m => new Set(chunkGraph.getModuleChunksIterable(m)) - ) - ); + if ( + this.embedInRuntimeBailout !== + AbstractLibraryPlugin.prototype.embedInRuntimeBailout + ) { + hooks.embedInRuntimeBailout.tap( + _pluginName, + (module, renderContext) => { + const options = getOptionsForChunk(renderContext.chunk); + if (options === false) return; + return this.embedInRuntimeBailout(module, renderContext, { + options, + compilation, + chunkGraph: compilation.chunkGraph + }); + } + ); + } - // No relevant chunks found - if (selectedChunks.size === 0) return false; + if ( + this.strictRuntimeBailout !== + AbstractLibraryPlugin.prototype.strictRuntimeBailout + ) { + hooks.strictRuntimeBailout.tap(_pluginName, renderContext => { + const options = getOptionsForChunk(renderContext.chunk); + if (options === false) return; + return this.strictRuntimeBailout(renderContext, { + options, + compilation, + chunkGraph: compilation.chunkGraph + }); + }); + } - // The found chunk is already the split or similar - if ( - selectedChunks.size === 1 && - chunkGraph.getNumberOfChunkModules( - Array.from(selectedChunks)[0] - ) === selectedModules.length - ) { - const chunk = Array.from(selectedChunks)[0]; - if (fromAggressiveSplittingSet.has(chunk)) return false; - fromAggressiveSplittingSet.add(chunk); - chunkSplitDataMap.set(chunk, splitData); - return true; - } + if ( + this.renderStartup !== AbstractLibraryPlugin.prototype.renderStartup + ) { + hooks.renderStartup.tap( + _pluginName, + (source, module, renderContext) => { + const options = getOptionsForChunk(renderContext.chunk); + if (options === false) return source; + return this.renderStartup(source, module, renderContext, { + options, + compilation, + chunkGraph: compilation.chunkGraph + }); + } + ); + } - // split the chunk into two parts - const newChunk = compilation.addChunk(); - newChunk.chunkReason = "aggressive splitted"; - for (const chunk of selectedChunks) { - selectedModules.forEach( - moveModuleBetween(chunkGraph, chunk, newChunk) - ); - chunk.split(newChunk); - chunk.name = null; - } - fromAggressiveSplittingSet.add(newChunk); - chunkSplitDataMap.set(newChunk, splitData); + hooks.chunkHash.tap(_pluginName, (chunk, hash, context) => { + const options = getOptionsForChunk(chunk); + if (options === false) return; + this.chunkHash(chunk, hash, context, { + options, + compilation, + chunkGraph: compilation.chunkGraph + }); + }); + }); + } - if (splitData.id !== null && splitData.id !== undefined) { - newChunk.id = splitData.id; - newChunk.ids = [splitData.id]; - } - return true; - }; + /** + * @param {LibraryOptions=} library normalized library option + * @returns {T | false} preprocess as needed by overriding + */ + _parseOptionsCached(library) { + if (!library) return false; + if (library.type !== this._type) return false; + const cacheEntry = this._parseCache.get(library); + if (cacheEntry !== undefined) return cacheEntry; + const result = this.parseOptions(library); + this._parseCache.set(library, result); + return result; + } - // try to restore to recorded splitting - let changed = false; - for (let j = 0; j < usedSplits.length; j++) { - const splitData = usedSplits[j]; - if (applySplit(splitData)) changed = true; - } + /* istanbul ignore next */ + /** + * @abstract + * @param {LibraryOptions} library normalized library option + * @returns {T | false} preprocess as needed by overriding + */ + parseOptions(library) { + const AbstractMethodError = __webpack_require__(570); + throw new AbstractMethodError(); + } - // for any chunk which isn't splitted yet, split it and create a new entry - // start with the biggest chunk - const cmpFn = compareChunks(chunkGraph); - const sortedChunks = Array.from(chunks).sort((a, b) => { - const diff1 = - chunkGraph.getChunkModulesSize(b) - - chunkGraph.getChunkModulesSize(a); - if (diff1) return diff1; - const diff2 = - chunkGraph.getNumberOfChunkModules(a) - - chunkGraph.getNumberOfChunkModules(b); - if (diff2) return diff2; - return cmpFn(a, b); - }); - for (const chunk of sortedChunks) { - if (fromAggressiveSplittingSet.has(chunk)) continue; - const size = chunkGraph.getChunkModulesSize(chunk); - if ( - size > maxSize && - chunkGraph.getNumberOfChunkModules(chunk) > 1 - ) { - const modules = chunkGraph - .getOrderedChunkModules(chunk, compareModulesByIdentifier) - .filter(isNotAEntryModule(chunkGraph, chunk)); - const selectedModules = []; - let selectedModulesSize = 0; - for (let k = 0; k < modules.length; k++) { - const module = modules[k]; - const newSize = selectedModulesSize + module.size(); - if (newSize > maxSize && selectedModulesSize >= minSize) { - break; - } - selectedModulesSize = newSize; - selectedModules.push(module); - } - if (selectedModules.length === 0) continue; - const splitData = { - modules: selectedModules - .map(m => moduleToNameMap.get(m)) - .sort(), - size: selectedModulesSize - }; + /** + * @param {Module} module the exporting entry module + * @param {string} entryName the name of the entrypoint + * @param {LibraryContext} libraryContext context + * @returns {void} + */ + finishEntryModule(module, entryName, libraryContext) {} - if (applySplit(splitData)) { - newSplits = (newSplits || []).concat(splitData); - changed = true; - } - } - } - if (changed) return true; - } - ); - compilation.hooks.recordHash.tap( - "AggressiveSplittingPlugin", - records => { - // 4. save made splittings to records - const allSplits = new Set(); - const invalidSplits = new Set(); + /** + * @param {Module} module the exporting entry module + * @param {RenderContext} renderContext render context + * @param {LibraryContext} libraryContext context + * @returns {string | undefined} bailout reason + */ + embedInRuntimeBailout(module, renderContext, libraryContext) { + return undefined; + } - // Check if some splittings are invalid - // We remove invalid splittings and try again - for (const chunk of compilation.chunks) { - const splitData = chunkSplitDataMap.get(chunk); - if (splitData !== undefined) { - if (splitData.hash && chunk.hash !== splitData.hash) { - // Split was successful, but hash doesn't equal - // We can throw away the split since it's useless now - invalidSplits.add(splitData); - } - } - } + /** + * @param {RenderContext} renderContext render context + * @param {LibraryContext} libraryContext context + * @returns {string | undefined} bailout reason + */ + strictRuntimeBailout(renderContext, libraryContext) { + return undefined; + } - if (invalidSplits.size > 0) { - records.aggressiveSplits = records.aggressiveSplits.filter( - splitData => !invalidSplits.has(splitData) - ); - needAdditionalSeal = true; - } else { - // set hash and id values on all (new) splittings - for (const chunk of compilation.chunks) { - const splitData = chunkSplitDataMap.get(chunk); - if (splitData !== undefined) { - splitData.hash = chunk.hash; - splitData.id = chunk.id; - allSplits.add(splitData); - // set flag for stats - recordedChunks.add(chunk); - } - } + /** + * @param {Chunk} chunk the chunk + * @param {Set} set runtime requirements + * @param {LibraryContext} libraryContext context + * @returns {void} + */ + runtimeRequirements(chunk, set, libraryContext) { + if (this.render !== AbstractLibraryPlugin.prototype.render) + set.add(RuntimeGlobals.returnExportsFromRuntime); + } - // Also add all unused historical splits (after the used ones) - // They can still be used in some future compilation - const recordedSplits = - compilation.records && compilation.records.aggressiveSplits; - if (recordedSplits) { - for (const splitData of recordedSplits) { - if (!invalidSplits.has(splitData)) allSplits.add(splitData); - } - } + /** + * @param {Source} source source + * @param {RenderContext} renderContext render context + * @param {LibraryContext} libraryContext context + * @returns {Source} source with library export + */ + render(source, renderContext, libraryContext) { + return source; + } - // record all splits - records.aggressiveSplits = Array.from(allSplits); + /** + * @param {Source} source source + * @param {Module} module module + * @param {StartupRenderContext} renderContext render context + * @param {LibraryContext} libraryContext context + * @returns {Source} source with library export + */ + renderStartup(source, module, renderContext, libraryContext) { + return source; + } - needAdditionalSeal = false; - } - } - ); - compilation.hooks.needAdditionalSeal.tap( - "AggressiveSplittingPlugin", - () => { - if (needAdditionalSeal) { - needAdditionalSeal = false; - return true; - } - } - ); - } + /** + * @param {Chunk} chunk the chunk + * @param {Hash} hash hash + * @param {ChunkHashContext} chunkHashContext chunk hash context + * @param {LibraryContext} libraryContext context + * @returns {void} + */ + chunkHash(chunk, hash, chunkHashContext, libraryContext) { + const options = this._parseOptionsCached( + libraryContext.compilation.outputOptions.library ); + hash.update(this._pluginName); + hash.update(JSON.stringify(options)); } } -module.exports = AggressiveSplittingPlugin; + +AbstractLibraryPlugin.COMMON_LIBRARY_NAME_MESSAGE = COMMON_LIBRARY_NAME_MESSAGE; +module.exports = AbstractLibraryPlugin; /***/ }), -/***/ 1881: +/***/ 4494: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; @@ -101320,1872 +99191,1673 @@ module.exports = AggressiveSplittingPlugin; -const eslintScope = __webpack_require__(26839); -const Referencer = __webpack_require__(96988); -const { - CachedSource, - ConcatSource, - ReplaceSource -} = __webpack_require__(96192); -const ConcatenationScope = __webpack_require__(14067); -const { UsageState } = __webpack_require__(4295); -const Module = __webpack_require__(85887); -const RuntimeGlobals = __webpack_require__(49404); +const { ConcatSource } = __webpack_require__(96192); +const ExternalModule = __webpack_require__(89805); const Template = __webpack_require__(92066); -const HarmonyImportDependency = __webpack_require__(19577); -const JavascriptParser = __webpack_require__(42060); -const { equals } = __webpack_require__(21537); -const LazySet = __webpack_require__(59534); -const { concatComparators, keepOriginalOrder } = __webpack_require__(26296); -const createHash = __webpack_require__(24123); -const { makePathsRelative } = __webpack_require__(96236); -const makeSerializable = __webpack_require__(26522); -const propertyAccess = __webpack_require__(86709); -const { - filterRuntime, - intersectRuntime, - mergeRuntimeCondition, - mergeRuntimeConditionNonFalse, - runtimeConditionToString, - subtractRuntimeCondition -} = __webpack_require__(19655); +const AbstractLibraryPlugin = __webpack_require__(94051); -/** @typedef {import("eslint-scope").Scope} Scope */ /** @typedef {import("webpack-sources").Source} Source */ -/** @typedef {import("../../declarations/WebpackOptions").WebpackOptionsNormalized} WebpackOptions */ -/** @typedef {import("../ChunkGraph")} ChunkGraph */ -/** @typedef {import("../Compilation")} Compilation */ -/** @typedef {import("../Dependency")} Dependency */ -/** @typedef {import("../Dependency").UpdateHashContext} UpdateHashContext */ -/** @typedef {import("../DependencyTemplate").DependencyTemplateContext} DependencyTemplateContext */ -/** @typedef {import("../DependencyTemplates")} DependencyTemplates */ -/** @typedef {import("../ExportsInfo").ExportInfo} ExportInfo */ -/** @template T @typedef {import("../InitFragment")} InitFragment */ -/** @typedef {import("../Module").CodeGenerationContext} CodeGenerationContext */ -/** @typedef {import("../Module").CodeGenerationResult} CodeGenerationResult */ -/** @typedef {import("../Module").LibIdentOptions} LibIdentOptions */ -/** @typedef {import("../ModuleGraph")} ModuleGraph */ -/** @typedef {import("../ModuleGraphConnection")} ModuleGraphConnection */ -/** @typedef {import("../ModuleGraphConnection").ConnectionState} ConnectionState */ -/** @typedef {import("../RequestShortener")} RequestShortener */ -/** @typedef {import("../ResolverFactory").ResolverWithOptions} ResolverWithOptions */ -/** @typedef {import("../RuntimeTemplate")} RuntimeTemplate */ -/** @typedef {import("../WebpackError")} WebpackError */ -/** @typedef {import("../javascript/JavascriptModulesPlugin").ChunkRenderContext} ChunkRenderContext */ +/** @typedef {import("../../declarations/WebpackOptions").LibraryOptions} LibraryOptions */ +/** @typedef {import("../../declarations/WebpackOptions").LibraryType} LibraryType */ +/** @typedef {import("../Chunk")} Chunk */ +/** @typedef {import("../Compilation").ChunkHashContext} ChunkHashContext */ +/** @typedef {import("../Compiler")} Compiler */ +/** @typedef {import("../javascript/JavascriptModulesPlugin").RenderContext} RenderContext */ /** @typedef {import("../util/Hash")} Hash */ -/** @typedef {typeof import("../util/Hash")} HashConstructor */ -/** @typedef {import("../util/fs").InputFileSystem} InputFileSystem */ -/** @typedef {import("../util/runtime").RuntimeSpec} RuntimeSpec */ - -// fix eslint-scope to support class properties correctly -// cspell:word Referencer -const ReferencerClass = Referencer; -if (!ReferencerClass.prototype.PropertyDefinition) { - ReferencerClass.prototype.PropertyDefinition = - ReferencerClass.prototype.Property; -} +/** @template T @typedef {import("./AbstractLibraryPlugin").LibraryContext} LibraryContext */ /** - * @typedef {Object} ReexportInfo - * @property {Module} module - * @property {string[]} export + * @typedef {Object} AmdLibraryPluginOptions + * @property {LibraryType} type + * @property {boolean=} requireAsWrapper */ -/** @typedef {RawBinding | SymbolBinding} Binding */ - /** - * @typedef {Object} RawBinding - * @property {ModuleInfo} info - * @property {string} rawName - * @property {string=} comment - * @property {string[]} ids - * @property {string[]} exportName + * @typedef {Object} AmdLibraryPluginParsed + * @property {string} name */ /** - * @typedef {Object} SymbolBinding - * @property {ConcatenatedModuleInfo} info - * @property {string} name - * @property {string=} comment - * @property {string[]} ids - * @property {string[]} exportName + * @typedef {AmdLibraryPluginParsed} T + * @extends {AbstractLibraryPlugin} */ +class AmdLibraryPlugin extends AbstractLibraryPlugin { + /** + * @param {AmdLibraryPluginOptions} options the plugin options + */ + constructor(options) { + super({ + pluginName: "AmdLibraryPlugin", + type: options.type + }); + this.requireAsWrapper = options.requireAsWrapper; + } -/** @typedef {ConcatenatedModuleInfo | ExternalModuleInfo } ModuleInfo */ -/** @typedef {ConcatenatedModuleInfo | ExternalModuleInfo | ReferenceToModuleInfo } ModuleInfoOrReference */ + /** + * @param {LibraryOptions} library normalized library option + * @returns {T | false} preprocess as needed by overriding + */ + parseOptions(library) { + const { name } = library; + if (this.requireAsWrapper) { + if (name) { + throw new Error( + `AMD library name must be unset. ${AbstractLibraryPlugin.COMMON_LIBRARY_NAME_MESSAGE}` + ); + } + } else { + if (name && typeof name !== "string") { + throw new Error( + `AMD library name must be a simple string or unset. ${AbstractLibraryPlugin.COMMON_LIBRARY_NAME_MESSAGE}` + ); + } + } + return { + name: /** @type {string=} */ (name) + }; + } -/** - * @typedef {Object} ConcatenatedModuleInfo - * @property {"concatenated"} type - * @property {Module} module - * @property {number} index - * @property {Object} ast - * @property {Source} internalSource - * @property {ReplaceSource} source - * @property {InitFragment[]=} chunkInitFragments - * @property {Iterable} runtimeRequirements - * @property {Scope} globalScope - * @property {Scope} moduleScope - * @property {Map} internalNames - * @property {Map} exportMap - * @property {Map} rawExportMap - * @property {string=} namespaceExportSymbol - * @property {string} namespaceObjectName - * @property {boolean} interopNamespaceObjectUsed - * @property {string} interopNamespaceObjectName - * @property {boolean} interopNamespaceObject2Used - * @property {string} interopNamespaceObject2Name - * @property {boolean} interopDefaultAccessUsed - * @property {string} interopDefaultAccessName - */ + /** + * @param {Source} source source + * @param {RenderContext} renderContext render context + * @param {LibraryContext} libraryContext context + * @returns {Source} source with library export + */ + render( + source, + { chunkGraph, chunk, runtimeTemplate }, + { options, compilation } + ) { + const modern = runtimeTemplate.supportsArrowFunction(); + const modules = chunkGraph + .getChunkModules(chunk) + .filter(m => m instanceof ExternalModule); + const externals = /** @type {ExternalModule[]} */ (modules); + const externalsDepsArray = JSON.stringify( + externals.map(m => + typeof m.request === "object" && !Array.isArray(m.request) + ? m.request.amd + : m.request + ) + ); + const externalsArguments = externals + .map( + m => + `__WEBPACK_EXTERNAL_MODULE_${Template.toIdentifier( + `${chunkGraph.getModuleId(m)}` + )}__` + ) + .join(", "); -/** - * @typedef {Object} ExternalModuleInfo - * @property {"external"} type - * @property {Module} module - * @property {RuntimeSpec | boolean} runtimeCondition - * @property {number} index - * @property {string} name - * @property {boolean} interopNamespaceObjectUsed - * @property {string} interopNamespaceObjectName - * @property {boolean} interopNamespaceObject2Used - * @property {string} interopNamespaceObject2Name - * @property {boolean} interopDefaultAccessUsed - * @property {string} interopDefaultAccessName - */ + const iife = runtimeTemplate.isIIFE(); + const fnStart = + (modern + ? `(${externalsArguments}) => {` + : `function(${externalsArguments}) {`) + + (iife || !chunk.hasRuntime() ? " return " : "\n"); + const fnEnd = iife ? ";\n}" : "\n}"; -/** - * @typedef {Object} ReferenceToModuleInfo - * @property {"reference"} type - * @property {RuntimeSpec | boolean} runtimeCondition - * @property {ConcatenatedModuleInfo | ExternalModuleInfo} target - */ + if (this.requireAsWrapper) { + return new ConcatSource( + `require(${externalsDepsArray}, ${fnStart}`, + source, + `${fnEnd});` + ); + } else if (options.name) { + const name = compilation.getPath(options.name, { + chunk + }); -const RESERVED_NAMES = new Set( - [ - // internal names (should always be renamed) - ConcatenationScope.DEFAULT_EXPORT, - ConcatenationScope.NAMESPACE_OBJECT_EXPORT, + return new ConcatSource( + `define(${JSON.stringify(name)}, ${externalsDepsArray}, ${fnStart}`, + source, + `${fnEnd});` + ); + } else if (externalsArguments) { + return new ConcatSource( + `define(${externalsDepsArray}, ${fnStart}`, + source, + `${fnEnd});` + ); + } else { + return new ConcatSource(`define(${fnStart}`, source, `${fnEnd});`); + } + } - // keywords - "abstract,arguments,async,await,boolean,break,byte,case,catch,char,class,const,continue", - "debugger,default,delete,do,double,else,enum,eval,export,extends,false,final,finally,float", - "for,function,goto,if,implements,import,in,instanceof,int,interface,let,long,native,new,null", - "package,private,protected,public,return,short,static,super,switch,synchronized,this,throw", - "throws,transient,true,try,typeof,var,void,volatile,while,with,yield", + /** + * @param {Chunk} chunk the chunk + * @param {Hash} hash hash + * @param {ChunkHashContext} chunkHashContext chunk hash context + * @param {LibraryContext} libraryContext context + * @returns {void} + */ + chunkHash(chunk, hash, chunkHashContext, { options, compilation }) { + hash.update("AmdLibraryPlugin"); + if (this.requireAsWrapper) { + hash.update("requireAsWrapper"); + } else if (options.name) { + hash.update("named"); + const name = compilation.getPath(options.name, { + chunk + }); + hash.update(name); + } + } +} - // commonjs/amd - "module,__dirname,__filename,exports,require,define", +module.exports = AmdLibraryPlugin; - // js globals - "Array,Date,eval,function,hasOwnProperty,Infinity,isFinite,isNaN,isPrototypeOf,length,Math", - "NaN,name,Number,Object,prototype,String,toString,undefined,valueOf", - // browser globals - "alert,all,anchor,anchors,area,assign,blur,button,checkbox,clearInterval,clearTimeout", - "clientInformation,close,closed,confirm,constructor,crypto,decodeURI,decodeURIComponent", - "defaultStatus,document,element,elements,embed,embeds,encodeURI,encodeURIComponent,escape", - "event,fileUpload,focus,form,forms,frame,innerHeight,innerWidth,layer,layers,link,location", - "mimeTypes,navigate,navigator,frames,frameRate,hidden,history,image,images,offscreenBuffering", - "open,opener,option,outerHeight,outerWidth,packages,pageXOffset,pageYOffset,parent,parseFloat", - "parseInt,password,pkcs11,plugin,prompt,propertyIsEnum,radio,reset,screenX,screenY,scroll", - "secure,select,self,setInterval,setTimeout,status,submit,taint,text,textarea,top,unescape", - "untaint,window", +/***/ }), - // window events - "onblur,onclick,onerror,onfocus,onkeydown,onkeypress,onkeyup,onmouseover,onload,onmouseup,onmousedown,onsubmit" - ] - .join(",") - .split(",") -); +/***/ 20909: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { -const bySourceOrder = (a, b) => { - const aOrder = a.sourceOrder; - const bOrder = b.sourceOrder; - if (isNaN(aOrder)) { - if (!isNaN(bOrder)) { - return 1; - } +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ + + + +const { ConcatSource } = __webpack_require__(96192); +const { UsageState } = __webpack_require__(4295); +const Template = __webpack_require__(92066); +const propertyAccess = __webpack_require__(86709); +const { getEntryRuntime } = __webpack_require__(19655); +const AbstractLibraryPlugin = __webpack_require__(94051); + +/** @typedef {import("webpack-sources").Source} Source */ +/** @typedef {import("../../declarations/WebpackOptions").LibraryOptions} LibraryOptions */ +/** @typedef {import("../../declarations/WebpackOptions").LibraryType} LibraryType */ +/** @typedef {import("../Chunk")} Chunk */ +/** @typedef {import("../Compilation").ChunkHashContext} ChunkHashContext */ +/** @typedef {import("../Compiler")} Compiler */ +/** @typedef {import("../Module")} Module */ +/** @typedef {import("../javascript/JavascriptModulesPlugin").RenderContext} RenderContext */ +/** @typedef {import("../javascript/JavascriptModulesPlugin").StartupRenderContext} StartupRenderContext */ +/** @typedef {import("../util/Hash")} Hash */ +/** @template T @typedef {import("./AbstractLibraryPlugin").LibraryContext} LibraryContext */ + +const KEYWORD_REGEX = + /^(await|break|case|catch|class|const|continue|debugger|default|delete|do|else|enum|export|extends|false|finally|for|function|if|implements|import|in|instanceof|interface|let|new|null|package|private|protected|public|return|super|switch|static|this|throw|try|true|typeof|var|void|while|with|yield)$/; +const IDENTIFIER_REGEX = + /^[\p{L}\p{Nl}$_][\p{L}\p{Nl}$\p{Mn}\p{Mc}\p{Nd}\p{Pc}]*$/iu; + +/** + * Validates the library name by checking for keywords and valid characters + * @param {string} name name to be validated + * @returns {boolean} true, when valid + */ +const isNameValid = name => { + return !KEYWORD_REGEX.test(name) && IDENTIFIER_REGEX.test(name); +}; + +/** + * @param {string[]} accessor variable plus properties + * @param {number} existingLength items of accessor that are existing already + * @param {boolean=} initLast if the last property should also be initialized to an object + * @returns {string} code to access the accessor while initializing + */ +const accessWithInit = (accessor, existingLength, initLast = false) => { + // This generates for [a, b, c, d]: + // (((a = typeof a === "undefined" ? {} : a).b = a.b || {}).c = a.b.c || {}).d + const base = accessor[0]; + if (accessor.length === 1 && !initLast) return base; + let current = + existingLength > 0 + ? base + : `(${base} = typeof ${base} === "undefined" ? {} : ${base})`; + + // i is the current position in accessor that has been printed + let i = 1; + + // all properties printed so far (excluding base) + let propsSoFar; + + // if there is existingLength, print all properties until this position as property access + if (existingLength > i) { + propsSoFar = accessor.slice(1, existingLength); + i = existingLength; + current += propertyAccess(propsSoFar); } else { - if (isNaN(bOrder)) { - return -1; - } - if (aOrder !== bOrder) { - return aOrder < bOrder ? -1 : 1; - } + propsSoFar = []; } - return 0; -}; -const joinIterableWithComma = iterable => { - // This is more performant than Array.from().join(", ") - // as it doesn't create an array - let str = ""; - let first = true; - for (const item of iterable) { - if (first) { - first = false; - } else { - str += ", "; - } - str += item; + // all remaining properties (except the last one when initLast is not set) + // should be printed as initializer + const initUntil = initLast ? accessor.length : accessor.length - 1; + for (; i < initUntil; i++) { + const prop = accessor[i]; + propsSoFar.push(prop); + current = `(${current}${propertyAccess([prop])} = ${base}${propertyAccess( + propsSoFar + )} || {})`; } - return str; + + // print the last property as property access if not yet printed + if (i < accessor.length) + current = `${current}${propertyAccess([accessor[accessor.length - 1]])}`; + + return current; }; /** - * @typedef {Object} ConcatenationEntry - * @property {"concatenated" | "external"} type - * @property {Module} module - * @property {RuntimeSpec | boolean} runtimeCondition + * @typedef {Object} AssignLibraryPluginOptions + * @property {LibraryType} type + * @property {string[] | "global"} prefix name prefix + * @property {string | false} declare declare name as variable + * @property {"error"|"copy"|"assign"} unnamed behavior for unnamed library name + * @property {"copy"|"assign"=} named behavior for named library name + */ + +/** + * @typedef {Object} AssignLibraryPluginParsed + * @property {string | string[]} name + * @property {string | string[] | undefined} export */ /** - * @param {ModuleGraph} moduleGraph the module graph - * @param {ModuleInfo} info module info - * @param {string[]} exportName exportName - * @param {Map} moduleToInfoMap moduleToInfoMap - * @param {RuntimeSpec} runtime for which runtime - * @param {RequestShortener} requestShortener the request shortener - * @param {RuntimeTemplate} runtimeTemplate the runtime template - * @param {Set} neededNamespaceObjects modules for which a namespace object should be generated - * @param {boolean} asCall asCall - * @param {boolean} strictHarmonyModule strictHarmonyModule - * @param {boolean | undefined} asiSafe asiSafe - * @param {Set} alreadyVisited alreadyVisited - * @returns {Binding} the final variable + * @typedef {AssignLibraryPluginParsed} T + * @extends {AbstractLibraryPlugin} */ -const getFinalBinding = ( - moduleGraph, - info, - exportName, - moduleToInfoMap, - runtime, - requestShortener, - runtimeTemplate, - neededNamespaceObjects, - asCall, - strictHarmonyModule, - asiSafe, - alreadyVisited = new Set() -) => { - const exportsType = info.module.getExportsType( - moduleGraph, - strictHarmonyModule - ); - if (exportName.length === 0) { - switch (exportsType) { - case "default-only": - info.interopNamespaceObject2Used = true; - return { - info, - rawName: info.interopNamespaceObject2Name, - ids: exportName, - exportName - }; - case "default-with-named": - info.interopNamespaceObjectUsed = true; - return { - info, - rawName: info.interopNamespaceObjectName, - ids: exportName, - exportName - }; - case "namespace": - case "dynamic": - break; - default: - throw new Error(`Unexpected exportsType ${exportsType}`); - } - } else { - switch (exportsType) { - case "namespace": - break; - case "default-with-named": - switch (exportName[0]) { - case "default": - exportName = exportName.slice(1); - break; - case "__esModule": - return { - info, - rawName: "/* __esModule */true", - ids: exportName.slice(1), - exportName - }; - } - break; - case "default-only": { - const exportId = exportName[0]; - if (exportId === "__esModule") { - return { - info, - rawName: "/* __esModule */true", - ids: exportName.slice(1), - exportName - }; - } - exportName = exportName.slice(1); - if (exportId !== "default") { - return { - info, - rawName: - "/* non-default import from default-exporting module */undefined", - ids: exportName, - exportName - }; - } - break; - } - case "dynamic": - switch (exportName[0]) { - case "default": { - exportName = exportName.slice(1); - info.interopDefaultAccessUsed = true; - const defaultExport = asCall - ? `${info.interopDefaultAccessName}()` - : asiSafe - ? `(${info.interopDefaultAccessName}())` - : asiSafe === false - ? `;(${info.interopDefaultAccessName}())` - : `${info.interopDefaultAccessName}.a`; - return { - info, - rawName: defaultExport, - ids: exportName, - exportName - }; - } - case "__esModule": - return { - info, - rawName: "/* __esModule */true", - ids: exportName.slice(1), - exportName - }; - } - break; - default: - throw new Error(`Unexpected exportsType ${exportsType}`); - } - } - if (exportName.length === 0) { - switch (info.type) { - case "concatenated": - neededNamespaceObjects.add(info); - return { - info, - rawName: info.namespaceObjectName, - ids: exportName, - exportName - }; - case "external": - return { info, rawName: info.name, ids: exportName, exportName }; - } - } - const exportsInfo = moduleGraph.getExportsInfo(info.module); - const exportInfo = exportsInfo.getExportInfo(exportName[0]); - if (alreadyVisited.has(exportInfo)) { - return { - info, - rawName: "/* circular reexport */ Object(function x() { x() }())", - ids: [], - exportName - }; +class AssignLibraryPlugin extends AbstractLibraryPlugin { + /** + * @param {AssignLibraryPluginOptions} options the plugin options + */ + constructor(options) { + super({ + pluginName: "AssignLibraryPlugin", + type: options.type + }); + this.prefix = options.prefix; + this.declare = options.declare; + this.unnamed = options.unnamed; + this.named = options.named || "assign"; } - alreadyVisited.add(exportInfo); - switch (info.type) { - case "concatenated": { - const exportId = exportName[0]; - if (exportInfo.provided === false) { - // It's not provided, but it could be on the prototype - neededNamespaceObjects.add(info); - return { - info, - rawName: info.namespaceObjectName, - ids: exportName, - exportName - }; - } - const directExport = info.exportMap && info.exportMap.get(exportId); - if (directExport) { - const usedName = /** @type {string[]} */ ( - exportsInfo.getUsedName(exportName, runtime) - ); - if (!usedName) { - return { - info, - rawName: "/* unused export */ undefined", - ids: exportName.slice(1), - exportName - }; - } - return { - info, - name: directExport, - ids: usedName.slice(1), - exportName - }; - } - const rawExport = info.rawExportMap && info.rawExportMap.get(exportId); - if (rawExport) { - return { - info, - rawName: rawExport, - ids: exportName.slice(1), - exportName - }; - } - const reexport = exportInfo.findTarget(moduleGraph, module => - moduleToInfoMap.has(module) - ); - if (reexport === false) { + + /** + * @param {LibraryOptions} library normalized library option + * @returns {T | false} preprocess as needed by overriding + */ + parseOptions(library) { + const { name } = library; + if (this.unnamed === "error") { + if (typeof name !== "string" && !Array.isArray(name)) { throw new Error( - `Target module of reexport from '${info.module.readableIdentifier( - requestShortener - )}' is not part of the concatenation (export '${exportId}')\nModules in the concatenation:\n${Array.from( - moduleToInfoMap, - ([m, info]) => - ` * ${info.type} ${m.readableIdentifier(requestShortener)}` - ).join("\n")}` - ); - } - if (reexport) { - const refInfo = moduleToInfoMap.get(reexport.module); - return getFinalBinding( - moduleGraph, - refInfo, - reexport.export - ? [...reexport.export, ...exportName.slice(1)] - : exportName.slice(1), - moduleToInfoMap, - runtime, - requestShortener, - runtimeTemplate, - neededNamespaceObjects, - asCall, - info.module.buildMeta.strictHarmonyModule, - asiSafe, - alreadyVisited + `Library name must be a string or string array. ${AbstractLibraryPlugin.COMMON_LIBRARY_NAME_MESSAGE}` ); } - if (info.namespaceExportSymbol) { - const usedName = /** @type {string[]} */ ( - exportsInfo.getUsedName(exportName, runtime) + } else { + if (name && typeof name !== "string" && !Array.isArray(name)) { + throw new Error( + `Library name must be a string, string array or unset. ${AbstractLibraryPlugin.COMMON_LIBRARY_NAME_MESSAGE}` ); - return { - info, - rawName: info.namespaceObjectName, - ids: usedName, - exportName - }; } - throw new Error( - `Cannot get final name for export '${exportName.join( - "." - )}' of ${info.module.readableIdentifier(requestShortener)}` - ); } + return { + name: /** @type {string|string[]=} */ (name), + export: library.export + }; + } - case "external": { - const used = /** @type {string[]} */ ( - exportsInfo.getUsedName(exportName, runtime) + /** + * @param {Module} module the exporting entry module + * @param {string} entryName the name of the entrypoint + * @param {LibraryContext} libraryContext context + * @returns {void} + */ + finishEntryModule( + module, + entryName, + { options, compilation, compilation: { moduleGraph } } + ) { + const runtime = getEntryRuntime(compilation, entryName); + if (options.export) { + const exportsInfo = moduleGraph.getExportInfo( + module, + Array.isArray(options.export) ? options.export[0] : options.export ); - if (!used) { - return { - info, - rawName: "/* unused export */ undefined", - ids: exportName.slice(1), - exportName - }; - } - const comment = equals(used, exportName) - ? "" - : Template.toNormalComment(`${exportName.join(".")}`); - return { info, rawName: info.name + comment, ids: used, exportName }; + exportsInfo.setUsed(UsageState.Used, runtime); + exportsInfo.canMangleUse = false; + } else { + const exportsInfo = moduleGraph.getExportsInfo(module); + exportsInfo.setUsedInUnknownWay(runtime); } + moduleGraph.addExtraReason(module, "used as library export"); } -}; -/** - * @param {ModuleGraph} moduleGraph the module graph - * @param {ModuleInfo} info module info - * @param {string[]} exportName exportName - * @param {Map} moduleToInfoMap moduleToInfoMap - * @param {RuntimeSpec} runtime for which runtime - * @param {RequestShortener} requestShortener the request shortener - * @param {RuntimeTemplate} runtimeTemplate the runtime template - * @param {Set} neededNamespaceObjects modules for which a namespace object should be generated - * @param {boolean} asCall asCall - * @param {boolean} callContext callContext - * @param {boolean} strictHarmonyModule strictHarmonyModule - * @param {boolean | undefined} asiSafe asiSafe - * @returns {string} the final name - */ -const getFinalName = ( - moduleGraph, - info, - exportName, - moduleToInfoMap, - runtime, - requestShortener, - runtimeTemplate, - neededNamespaceObjects, - asCall, - callContext, - strictHarmonyModule, - asiSafe -) => { - const binding = getFinalBinding( - moduleGraph, - info, - exportName, - moduleToInfoMap, - runtime, - requestShortener, - runtimeTemplate, - neededNamespaceObjects, - asCall, - strictHarmonyModule, - asiSafe - ); - { - const { ids, comment } = binding; - let reference; - let isPropertyAccess; - if ("rawName" in binding) { - reference = `${binding.rawName}${comment || ""}${propertyAccess(ids)}`; - isPropertyAccess = ids.length > 0; - } else { - const { info, name: exportId } = binding; - const name = info.internalNames.get(exportId); - if (!name) { + _getPrefix(compilation) { + return this.prefix === "global" + ? [compilation.outputOptions.globalObject] + : this.prefix; + } + + _getResolvedFullName(options, chunk, compilation) { + const prefix = this._getPrefix(compilation); + const fullName = options.name ? prefix.concat(options.name) : prefix; + return fullName.map(n => + compilation.getPath(n, { + chunk + }) + ); + } + + /** + * @param {Source} source source + * @param {RenderContext} renderContext render context + * @param {LibraryContext} libraryContext context + * @returns {Source} source with library export + */ + render(source, { chunk }, { options, compilation }) { + const fullNameResolved = this._getResolvedFullName( + options, + chunk, + compilation + ); + if (this.declare) { + const base = fullNameResolved[0]; + if (!isNameValid(base)) { throw new Error( - `The export "${exportId}" in "${info.module.readableIdentifier( - requestShortener - )}" has no internal name (existing names: ${ - Array.from( - info.internalNames, - ([name, symbol]) => `${name}: ${symbol}` - ).join(", ") || "none" - })` + `Library name base (${base}) must be a valid identifier when using a var declaring library type. Either use a valid identifier (e. g. ${Template.toIdentifier( + base + )}) or use a different library type (e. g. 'type: "global"', which assign a property on the global scope instead of declaring a variable). ${ + AbstractLibraryPlugin.COMMON_LIBRARY_NAME_MESSAGE + }` ); } - reference = `${name}${comment || ""}${propertyAccess(ids)}`; - isPropertyAccess = ids.length > 1; + source = new ConcatSource(`${this.declare} ${base};\n`, source); } - if (isPropertyAccess && asCall && callContext === false) { - return asiSafe - ? `(0,${reference})` - : asiSafe === false - ? `;(0,${reference})` - : `/*#__PURE__*/Object(${reference})`; + return source; + } + + /** + * @param {Module} module the exporting entry module + * @param {RenderContext} renderContext render context + * @param {LibraryContext} libraryContext context + * @returns {string | undefined} bailout reason + */ + embedInRuntimeBailout(module, { chunk }, { options, compilation }) { + const topLevelDeclarations = + module.buildInfo && module.buildInfo.topLevelDeclarations; + if (!topLevelDeclarations) + return "it doesn't tell about top level declarations."; + const fullNameResolved = this._getResolvedFullName( + options, + chunk, + compilation + ); + const base = fullNameResolved[0]; + if (topLevelDeclarations.has(base)) + return `it declares '${base}' on top-level, which conflicts with the current library output.`; + } + + /** + * @param {RenderContext} renderContext render context + * @param {LibraryContext} libraryContext context + * @returns {string | undefined} bailout reason + */ + strictRuntimeBailout({ chunk }, { options, compilation }) { + if ( + this.declare || + this.prefix === "global" || + this.prefix.length > 0 || + !options.name + ) { + return; } - return reference; + return "a global variable is assign and maybe created"; + } + + /** + * @param {Source} source source + * @param {Module} module module + * @param {StartupRenderContext} renderContext render context + * @param {LibraryContext} libraryContext context + * @returns {Source} source with library export + */ + renderStartup(source, module, { chunk }, { options, compilation }) { + const fullNameResolved = this._getResolvedFullName( + options, + chunk, + compilation + ); + const exportAccess = options.export + ? propertyAccess( + Array.isArray(options.export) ? options.export : [options.export] + ) + : ""; + const result = new ConcatSource(source); + if (options.name ? this.named === "copy" : this.unnamed === "copy") { + result.add( + `var __webpack_export_target__ = ${accessWithInit( + fullNameResolved, + this._getPrefix(compilation).length, + true + )};\n` + ); + let exports = "__webpack_exports__"; + if (exportAccess) { + result.add( + `var __webpack_exports_export__ = __webpack_exports__${exportAccess};\n` + ); + exports = "__webpack_exports_export__"; + } + result.add( + `for(var i in ${exports}) __webpack_export_target__[i] = ${exports}[i];\n` + ); + result.add( + `if(${exports}.__esModule) Object.defineProperty(__webpack_export_target__, "__esModule", { value: true });\n` + ); + } else { + result.add( + `${accessWithInit( + fullNameResolved, + this._getPrefix(compilation).length, + false + )} = __webpack_exports__${exportAccess};\n` + ); + } + return result; + } + + /** + * @param {Chunk} chunk the chunk + * @param {Set} set runtime requirements + * @param {LibraryContext} libraryContext context + * @returns {void} + */ + runtimeRequirements(chunk, set, libraryContext) { + // we don't need to return exports from runtime } -}; -const addScopeSymbols = (s, nameSet, scopeSet1, scopeSet2) => { - let scope = s; - while (scope) { - if (scopeSet1.has(scope)) break; - if (scopeSet2.has(scope)) break; - scopeSet1.add(scope); - for (const variable of scope.variables) { - nameSet.add(variable.name); + /** + * @param {Chunk} chunk the chunk + * @param {Hash} hash hash + * @param {ChunkHashContext} chunkHashContext chunk hash context + * @param {LibraryContext} libraryContext context + * @returns {void} + */ + chunkHash(chunk, hash, chunkHashContext, { options, compilation }) { + hash.update("AssignLibraryPlugin"); + const prefix = + this.prefix === "global" + ? [compilation.outputOptions.globalObject] + : this.prefix; + const fullName = options.name ? prefix.concat(options.name) : prefix; + const fullNameResolved = fullName.map(n => + compilation.getPath(n, { + chunk + }) + ); + if (options.name ? this.named === "copy" : this.unnamed === "copy") { + hash.update("copy"); + } + if (this.declare) { + hash.update(this.declare); + } + hash.update(fullNameResolved.join(".")); + if (options.export) { + hash.update(`${options.export}`); } - scope = scope.upper; } -}; +} -const getAllReferences = variable => { - let set = variable.references; - // Look for inner scope variables too (like in class Foo { t() { Foo } }) - const identifiers = new Set(variable.identifiers); - for (const scope of variable.scope.childScopes) { - for (const innerVar of scope.variables) { - if (innerVar.identifiers.some(id => identifiers.has(id))) { - set = set.concat(innerVar.references); - break; - } - } +module.exports = AssignLibraryPlugin; + + +/***/ }), + +/***/ 35613: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ + + + +/** @typedef {import("../../declarations/WebpackOptions").LibraryOptions} LibraryOptions */ +/** @typedef {import("../../declarations/WebpackOptions").LibraryType} LibraryType */ +/** @typedef {import("../Compiler")} Compiler */ + +/** @type {WeakMap>} */ +const enabledTypes = new WeakMap(); + +const getEnabledTypes = compiler => { + let set = enabledTypes.get(compiler); + if (set === undefined) { + set = new Set(); + enabledTypes.set(compiler, set); } return set; }; -const getPathInAst = (ast, node) => { - if (ast === node) { - return []; +class EnableLibraryPlugin { + /** + * @param {LibraryType} type library type that should be available + */ + constructor(type) { + this.type = type; } - const nr = node.range; + /** + * @param {Compiler} compiler the compiler instance + * @param {LibraryType} type type of library + * @returns {void} + */ + static setEnabled(compiler, type) { + getEnabledTypes(compiler).add(type); + } - const enterNode = n => { - if (!n) return undefined; - const r = n.range; - if (r) { - if (r[0] <= nr[0] && r[1] >= nr[1]) { - const path = getPathInAst(n, node); - if (path) { - path.push(n); - return path; - } - } + /** + * @param {Compiler} compiler the compiler instance + * @param {LibraryType} type type of library + * @returns {void} + */ + static checkEnabled(compiler, type) { + if (!getEnabledTypes(compiler).has(type)) { + throw new Error( + `Library type "${type}" is not enabled. ` + + "EnableLibraryPlugin need to be used to enable this type of library. " + + 'This usually happens through the "output.enabledLibraryTypes" option. ' + + 'If you are using a function as entry which sets "library", you need to add all potential library types to "output.enabledLibraryTypes". ' + + "These types are enabled: " + + Array.from(getEnabledTypes(compiler)).join(", ") + ); } - return undefined; - }; + } - if (Array.isArray(ast)) { - for (let i = 0; i < ast.length; i++) { - const enterResult = enterNode(ast[i]); - if (enterResult !== undefined) return enterResult; - } - } else if (ast && typeof ast === "object") { - const keys = Object.keys(ast); - for (let i = 0; i < keys.length; i++) { - const value = ast[keys[i]]; - if (Array.isArray(value)) { - const pathResult = getPathInAst(value, node); - if (pathResult !== undefined) return pathResult; - } else if (value && typeof value === "object") { - const enterResult = enterNode(value); - if (enterResult !== undefined) return enterResult; + /** + * Apply the plugin + * @param {Compiler} compiler the compiler instance + * @returns {void} + */ + apply(compiler) { + const { type } = this; + + // Only enable once + const enabled = getEnabledTypes(compiler); + if (enabled.has(type)) return; + enabled.add(type); + + if (typeof type === "string") { + const enableExportProperty = () => { + const ExportPropertyTemplatePlugin = __webpack_require__(84806); + new ExportPropertyTemplatePlugin({ + type, + nsObjectUsed: type !== "module" + }).apply(compiler); + }; + switch (type) { + case "var": { + //@ts-expect-error https://github.com/microsoft/TypeScript/issues/41697 + const AssignLibraryPlugin = __webpack_require__(20909); + new AssignLibraryPlugin({ + type, + prefix: [], + declare: "var", + unnamed: "error" + }).apply(compiler); + break; + } + case "assign-properties": { + //@ts-expect-error https://github.com/microsoft/TypeScript/issues/41697 + const AssignLibraryPlugin = __webpack_require__(20909); + new AssignLibraryPlugin({ + type, + prefix: [], + declare: false, + unnamed: "error", + named: "copy" + }).apply(compiler); + break; + } + case "assign": { + //@ts-expect-error https://github.com/microsoft/TypeScript/issues/41697 + const AssignLibraryPlugin = __webpack_require__(20909); + new AssignLibraryPlugin({ + type, + prefix: [], + declare: false, + unnamed: "error" + }).apply(compiler); + break; + } + case "this": { + //@ts-expect-error https://github.com/microsoft/TypeScript/issues/41697 + const AssignLibraryPlugin = __webpack_require__(20909); + new AssignLibraryPlugin({ + type, + prefix: ["this"], + declare: false, + unnamed: "copy" + }).apply(compiler); + break; + } + case "window": { + //@ts-expect-error https://github.com/microsoft/TypeScript/issues/41697 + const AssignLibraryPlugin = __webpack_require__(20909); + new AssignLibraryPlugin({ + type, + prefix: ["window"], + declare: false, + unnamed: "copy" + }).apply(compiler); + break; + } + case "self": { + //@ts-expect-error https://github.com/microsoft/TypeScript/issues/41697 + const AssignLibraryPlugin = __webpack_require__(20909); + new AssignLibraryPlugin({ + type, + prefix: ["self"], + declare: false, + unnamed: "copy" + }).apply(compiler); + break; + } + case "global": { + //@ts-expect-error https://github.com/microsoft/TypeScript/issues/41697 + const AssignLibraryPlugin = __webpack_require__(20909); + new AssignLibraryPlugin({ + type, + prefix: "global", + declare: false, + unnamed: "copy" + }).apply(compiler); + break; + } + case "commonjs": { + //@ts-expect-error https://github.com/microsoft/TypeScript/issues/41697 + const AssignLibraryPlugin = __webpack_require__(20909); + new AssignLibraryPlugin({ + type, + prefix: ["exports"], + declare: false, + unnamed: "copy" + }).apply(compiler); + break; + } + case "commonjs2": + case "commonjs-module": { + //@ts-expect-error https://github.com/microsoft/TypeScript/issues/41697 + const AssignLibraryPlugin = __webpack_require__(20909); + new AssignLibraryPlugin({ + type, + prefix: ["module", "exports"], + declare: false, + unnamed: "assign" + }).apply(compiler); + break; + } + case "amd": + case "amd-require": { + enableExportProperty(); + const AmdLibraryPlugin = __webpack_require__(4494); + new AmdLibraryPlugin({ + type, + requireAsWrapper: type === "amd-require" + }).apply(compiler); + break; + } + case "umd": + case "umd2": { + enableExportProperty(); + const UmdLibraryPlugin = __webpack_require__(59401); + new UmdLibraryPlugin({ + type, + optionalAmdExternalAsGlobal: type === "umd2" + }).apply(compiler); + break; + } + case "system": { + enableExportProperty(); + const SystemLibraryPlugin = __webpack_require__(36253); + new SystemLibraryPlugin({ + type + }).apply(compiler); + break; + } + case "jsonp": { + enableExportProperty(); + const JsonpLibraryPlugin = __webpack_require__(75773); + new JsonpLibraryPlugin({ + type + }).apply(compiler); + break; + } + case "module": { + enableExportProperty(); + const ModuleLibraryPlugin = __webpack_require__(88548); + new ModuleLibraryPlugin({ + type + }).apply(compiler); + break; + } + default: + throw new Error(`Unsupported library type ${type}. +Plugins which provide custom library types must call EnableLibraryPlugin.setEnabled(compiler, type) to disable this error.`); } + } else { + // TODO support plugin instances here + // apply them to the compiler } } -}; +} -const TYPES = new Set(["javascript"]); +module.exports = EnableLibraryPlugin; -class ConcatenatedModule extends Module { + +/***/ }), + +/***/ 84806: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ + + + +const { ConcatSource } = __webpack_require__(96192); +const { UsageState } = __webpack_require__(4295); +const propertyAccess = __webpack_require__(86709); +const { getEntryRuntime } = __webpack_require__(19655); +const AbstractLibraryPlugin = __webpack_require__(94051); + +/** @typedef {import("webpack-sources").Source} Source */ +/** @typedef {import("../../declarations/WebpackOptions").LibraryOptions} LibraryOptions */ +/** @typedef {import("../../declarations/WebpackOptions").LibraryType} LibraryType */ +/** @typedef {import("../Chunk")} Chunk */ +/** @typedef {import("../Compiler")} Compiler */ +/** @typedef {import("../Module")} Module */ +/** @typedef {import("../javascript/JavascriptModulesPlugin").StartupRenderContext} StartupRenderContext */ +/** @template T @typedef {import("./AbstractLibraryPlugin").LibraryContext} LibraryContext */ + +/** + * @typedef {Object} ExportPropertyLibraryPluginParsed + * @property {string | string[]} export + */ + +/** + * @typedef {Object} ExportPropertyLibraryPluginOptions + * @property {LibraryType} type + * @property {boolean} nsObjectUsed the namespace object is used + */ +/** + * @typedef {ExportPropertyLibraryPluginParsed} T + * @extends {AbstractLibraryPlugin} + */ +class ExportPropertyLibraryPlugin extends AbstractLibraryPlugin { /** - * @param {Module} rootModule the root module of the concatenation - * @param {Set} modules all modules in the concatenation (including the root module) - * @param {RuntimeSpec} runtime the runtime - * @param {Object=} associatedObjectForCache object for caching - * @param {string | HashConstructor=} hashFunction hash function to use - * @returns {ConcatenatedModule} the module + * @param {ExportPropertyLibraryPluginOptions} options options */ - static create( - rootModule, - modules, - runtime, - associatedObjectForCache, - hashFunction = "md4" - ) { - const identifier = ConcatenatedModule._createIdentifier( - rootModule, - modules, - associatedObjectForCache, - hashFunction - ); - return new ConcatenatedModule({ - identifier, - rootModule, - modules, - runtime + constructor({ type, nsObjectUsed }) { + super({ + pluginName: "ExportPropertyLibraryPlugin", + type }); + this.nsObjectUsed = nsObjectUsed; } /** - * @param {Object} options options - * @param {string} options.identifier the identifier of the module - * @param {Module=} options.rootModule the root module of the concatenation - * @param {RuntimeSpec} options.runtime the selected runtime - * @param {Set=} options.modules all concatenated modules + * @param {LibraryOptions} library normalized library option + * @returns {T | false} preprocess as needed by overriding */ - constructor({ identifier, rootModule, modules, runtime }) { - super("javascript/esm", null, rootModule && rootModule.layer); - - // Info from Factory - /** @type {string} */ - this._identifier = identifier; - /** @type {Module} */ - this.rootModule = rootModule; - /** @type {Set} */ - this._modules = modules; - this._runtime = runtime; - this.factoryMeta = rootModule && rootModule.factoryMeta; + parseOptions(library) { + return { + export: library.export + }; } /** - * Assuming this module is in the cache. Update the (cached) module with - * the fresh module from the factory. Usually updates internal references - * and properties. - * @param {Module} module fresh module + * @param {Module} module the exporting entry module + * @param {string} entryName the name of the entrypoint + * @param {LibraryContext} libraryContext context * @returns {void} */ - updateCacheModule(module) { - throw new Error("Must not be called"); + finishEntryModule( + module, + entryName, + { options, compilation, compilation: { moduleGraph } } + ) { + const runtime = getEntryRuntime(compilation, entryName); + if (options.export) { + const exportsInfo = moduleGraph.getExportInfo( + module, + Array.isArray(options.export) ? options.export[0] : options.export + ); + exportsInfo.setUsed(UsageState.Used, runtime); + exportsInfo.canMangleUse = false; + } else { + const exportsInfo = moduleGraph.getExportsInfo(module); + if (this.nsObjectUsed) { + exportsInfo.setUsedInUnknownWay(runtime); + } else { + exportsInfo.setAllKnownExportsUsed(runtime); + } + } + moduleGraph.addExtraReason(module, "used as library export"); } /** - * @returns {Set} types available (do not mutate) + * @param {Chunk} chunk the chunk + * @param {Set} set runtime requirements + * @param {LibraryContext} libraryContext context + * @returns {void} */ - getSourceTypes() { - return TYPES; - } - - get modules() { - return Array.from(this._modules); - } + runtimeRequirements(chunk, set, libraryContext) {} /** - * @returns {string} a unique identifier of the module + * @param {Source} source source + * @param {Module} module module + * @param {StartupRenderContext} renderContext render context + * @param {LibraryContext} libraryContext context + * @returns {Source} source with library export */ - identifier() { - return this._identifier; + renderStartup(source, module, renderContext, { options }) { + if (!options.export) return source; + const postfix = `__webpack_exports__ = __webpack_exports__${propertyAccess( + Array.isArray(options.export) ? options.export : [options.export] + )};\n`; + return new ConcatSource(source, postfix); } +} + +module.exports = ExportPropertyLibraryPlugin; + + +/***/ }), + +/***/ 75773: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ + + + +const { ConcatSource } = __webpack_require__(96192); +const AbstractLibraryPlugin = __webpack_require__(94051); + +/** @typedef {import("webpack-sources").Source} Source */ +/** @typedef {import("../../declarations/WebpackOptions").LibraryOptions} LibraryOptions */ +/** @typedef {import("../../declarations/WebpackOptions").LibraryType} LibraryType */ +/** @typedef {import("../Chunk")} Chunk */ +/** @typedef {import("../Compilation").ChunkHashContext} ChunkHashContext */ +/** @typedef {import("../Compiler")} Compiler */ +/** @typedef {import("../javascript/JavascriptModulesPlugin").RenderContext} RenderContext */ +/** @typedef {import("../util/Hash")} Hash */ +/** @template T @typedef {import("./AbstractLibraryPlugin").LibraryContext} LibraryContext */ + +/** + * @typedef {Object} JsonpLibraryPluginOptions + * @property {LibraryType} type + */ - /** - * @param {RequestShortener} requestShortener the request shortener - * @returns {string} a user readable identifier of the module - */ - readableIdentifier(requestShortener) { - return ( - this.rootModule.readableIdentifier(requestShortener) + - ` + ${this._modules.size - 1} modules` - ); - } +/** + * @typedef {Object} JsonpLibraryPluginParsed + * @property {string} name + */ +/** + * @typedef {JsonpLibraryPluginParsed} T + * @extends {AbstractLibraryPlugin} + */ +class JsonpLibraryPlugin extends AbstractLibraryPlugin { /** - * @param {LibIdentOptions} options options - * @returns {string | null} an identifier for library inclusion + * @param {JsonpLibraryPluginOptions} options the plugin options */ - libIdent(options) { - return this.rootModule.libIdent(options); + constructor(options) { + super({ + pluginName: "JsonpLibraryPlugin", + type: options.type + }); } /** - * @returns {string | null} absolute path which should be used for condition matching (usually the resource path) + * @param {LibraryOptions} library normalized library option + * @returns {T | false} preprocess as needed by overriding */ - nameForCondition() { - return this.rootModule.nameForCondition(); + parseOptions(library) { + const { name } = library; + if (typeof name !== "string") { + throw new Error( + `Jsonp library name must be a simple string. ${AbstractLibraryPlugin.COMMON_LIBRARY_NAME_MESSAGE}` + ); + } + return { + name: /** @type {string} */ (name) + }; } /** - * @param {ModuleGraph} moduleGraph the module graph - * @returns {ConnectionState} how this module should be connected to referencing modules when consumed for side-effects only + * @param {Source} source source + * @param {RenderContext} renderContext render context + * @param {LibraryContext} libraryContext context + * @returns {Source} source with library export */ - getSideEffectsConnectionState(moduleGraph) { - return this.rootModule.getSideEffectsConnectionState(moduleGraph); + render(source, { chunk }, { options, compilation }) { + const name = compilation.getPath(options.name, { + chunk + }); + return new ConcatSource(`${name}(`, source, ")"); } /** - * @param {WebpackOptions} options webpack options - * @param {Compilation} compilation the compilation - * @param {ResolverWithOptions} resolver the resolver - * @param {InputFileSystem} fs the file system - * @param {function(WebpackError=): void} callback callback function + * @param {Chunk} chunk the chunk + * @param {Hash} hash hash + * @param {ChunkHashContext} chunkHashContext chunk hash context + * @param {LibraryContext} libraryContext context * @returns {void} */ - build(options, compilation, resolver, fs, callback) { - const { rootModule } = this; - this.buildInfo = { - strict: true, - cacheable: true, - moduleArgument: rootModule.buildInfo.moduleArgument, - exportsArgument: rootModule.buildInfo.exportsArgument, - fileDependencies: new LazySet(), - contextDependencies: new LazySet(), - missingDependencies: new LazySet(), - topLevelDeclarations: new Set(), - assets: undefined - }; - this.buildMeta = rootModule.buildMeta; - this.clearDependenciesAndBlocks(); - this.clearWarningsAndErrors(); + chunkHash(chunk, hash, chunkHashContext, { options, compilation }) { + hash.update("JsonpLibraryPlugin"); + hash.update(compilation.getPath(options.name, { chunk })); + } +} - for (const m of this._modules) { - // populate cacheable - if (!m.buildInfo.cacheable) { - this.buildInfo.cacheable = false; - } +module.exports = JsonpLibraryPlugin; - // populate dependencies - for (const d of m.dependencies.filter( - dep => - !(dep instanceof HarmonyImportDependency) || - !this._modules.has(compilation.moduleGraph.getModule(dep)) - )) { - this.dependencies.push(d); - } - // populate blocks - for (const d of m.blocks) { - this.blocks.push(d); - } - // populate warnings - const warnings = m.getWarnings(); - if (warnings !== undefined) { - for (const warning of warnings) { - this.addWarning(warning); - } - } +/***/ }), - // populate errors - const errors = m.getErrors(); - if (errors !== undefined) { - for (const error of errors) { - this.addError(error); - } - } +/***/ 88548: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - // populate topLevelDeclarations - if (m.buildInfo.topLevelDeclarations) { - const topLevelDeclarations = this.buildInfo.topLevelDeclarations; - if (topLevelDeclarations !== undefined) { - for (const decl of m.buildInfo.topLevelDeclarations) { - // reserved names will always be renamed - if (RESERVED_NAMES.has(decl)) continue; - // TODO actually this is incorrect since with renaming there could be more - // We should do the renaming during build - topLevelDeclarations.add(decl); - } - } - } else { - this.buildInfo.topLevelDeclarations = undefined; - } +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ - // populate assets - if (m.buildInfo.assets) { - if (this.buildInfo.assets === undefined) { - this.buildInfo.assets = Object.create(null); - } - Object.assign(this.buildInfo.assets, m.buildInfo.assets); - } - if (m.buildInfo.assetsInfo) { - if (this.buildInfo.assetsInfo === undefined) { - this.buildInfo.assetsInfo = new Map(); - } - for (const [key, value] of m.buildInfo.assetsInfo) { - this.buildInfo.assetsInfo.set(key, value); - } - } - } - callback(); - } - /** - * @param {string=} type the source type for which the size should be estimated - * @returns {number} the estimated size of the module (must be non-zero) - */ - size(type) { - // Guess size from embedded modules - let size = 0; - for (const module of this._modules) { - size += module.size(type); - } - return size; - } - /** - * @private - * @param {Module} rootModule the root of the concatenation - * @param {Set} modulesSet a set of modules which should be concatenated - * @param {RuntimeSpec} runtime for this runtime - * @param {ModuleGraph} moduleGraph the module graph - * @returns {ConcatenationEntry[]} concatenation list - */ - _createConcatenationList(rootModule, modulesSet, runtime, moduleGraph) { - /** @type {ConcatenationEntry[]} */ - const list = []; - /** @type {Map} */ - const existingEntries = new Map(); +const { ConcatSource } = __webpack_require__(96192); +const Template = __webpack_require__(92066); +const propertyAccess = __webpack_require__(86709); +const AbstractLibraryPlugin = __webpack_require__(94051); - /** - * @param {Module} module a module - * @returns {Iterable<{ connection: ModuleGraphConnection, runtimeCondition: RuntimeSpec | true }>} imported modules in order - */ - const getConcatenatedImports = module => { - let connections = Array.from(moduleGraph.getOutgoingConnections(module)); - if (module === rootModule) { - for (const c of moduleGraph.getOutgoingConnections(this)) - connections.push(c); - } - const references = connections - .filter(connection => { - if (!(connection.dependency instanceof HarmonyImportDependency)) - return false; - return ( - connection && - connection.resolvedOriginModule === module && - connection.module && - connection.isTargetActive(runtime) - ); - }) - .map(connection => ({ - connection, - sourceOrder: /** @type {HarmonyImportDependency} */ ( - connection.dependency - ).sourceOrder - })); - references.sort( - concatComparators(bySourceOrder, keepOriginalOrder(references)) - ); - /** @type {Map} */ - const referencesMap = new Map(); - for (const { connection } of references) { - const runtimeCondition = filterRuntime(runtime, r => - connection.isTargetActive(r) - ); - if (runtimeCondition === false) continue; - const module = connection.module; - const entry = referencesMap.get(module); - if (entry === undefined) { - referencesMap.set(module, { connection, runtimeCondition }); - continue; - } - entry.runtimeCondition = mergeRuntimeConditionNonFalse( - entry.runtimeCondition, - runtimeCondition, - runtime - ); - } - return referencesMap.values(); - }; +/** @typedef {import("webpack-sources").Source} Source */ +/** @typedef {import("../../declarations/WebpackOptions").LibraryOptions} LibraryOptions */ +/** @typedef {import("../../declarations/WebpackOptions").LibraryType} LibraryType */ +/** @typedef {import("../Chunk")} Chunk */ +/** @typedef {import("../Compilation").ChunkHashContext} ChunkHashContext */ +/** @typedef {import("../Compiler")} Compiler */ +/** @typedef {import("../Module")} Module */ +/** @typedef {import("../javascript/JavascriptModulesPlugin").StartupRenderContext} StartupRenderContext */ +/** @typedef {import("../util/Hash")} Hash */ +/** @template T @typedef {import("./AbstractLibraryPlugin").LibraryContext} LibraryContext */ - /** - * @param {ModuleGraphConnection} connection graph connection - * @param {RuntimeSpec | true} runtimeCondition runtime condition - * @returns {void} - */ - const enterModule = (connection, runtimeCondition) => { - const module = connection.module; - if (!module) return; - const existingEntry = existingEntries.get(module); - if (existingEntry === true) { - return; - } - if (modulesSet.has(module)) { - existingEntries.set(module, true); - if (runtimeCondition !== true) { - throw new Error( - `Cannot runtime-conditional concatenate a module (${module.identifier()} in ${this.rootModule.identifier()}, ${runtimeConditionToString( - runtimeCondition - )}). This should not happen.` - ); - } - const imports = getConcatenatedImports(module); - for (const { connection, runtimeCondition } of imports) - enterModule(connection, runtimeCondition); - list.push({ - type: "concatenated", - module: connection.module, - runtimeCondition - }); - } else { - if (existingEntry !== undefined) { - const reducedRuntimeCondition = subtractRuntimeCondition( - runtimeCondition, - existingEntry, - runtime - ); - if (reducedRuntimeCondition === false) return; - runtimeCondition = reducedRuntimeCondition; - existingEntries.set( - connection.module, - mergeRuntimeConditionNonFalse( - existingEntry, - runtimeCondition, - runtime - ) - ); - } else { - existingEntries.set(connection.module, runtimeCondition); - } - if (list.length > 0) { - const lastItem = list[list.length - 1]; - if ( - lastItem.type === "external" && - lastItem.module === connection.module - ) { - lastItem.runtimeCondition = mergeRuntimeCondition( - lastItem.runtimeCondition, - runtimeCondition, - runtime - ); - return; - } - } - list.push({ - type: "external", - get module() { - // We need to use a getter here, because the module in the dependency - // could be replaced by some other process (i. e. also replaced with a - // concatenated module) - return connection.module; - }, - runtimeCondition - }); - } - }; +/** + * @typedef {Object} ModuleLibraryPluginOptions + * @property {LibraryType} type + */ - existingEntries.set(rootModule, true); - const imports = getConcatenatedImports(rootModule); - for (const { connection, runtimeCondition } of imports) - enterModule(connection, runtimeCondition); - list.push({ - type: "concatenated", - module: rootModule, - runtimeCondition: true - }); +/** + * @typedef {Object} ModuleLibraryPluginParsed + * @property {string} name + */ - return list; +/** + * @typedef {ModuleLibraryPluginParsed} T + * @extends {AbstractLibraryPlugin} + */ +class ModuleLibraryPlugin extends AbstractLibraryPlugin { + /** + * @param {ModuleLibraryPluginOptions} options the plugin options + */ + constructor(options) { + super({ + pluginName: "ModuleLibraryPlugin", + type: options.type + }); } /** - * @param {Module} rootModule the root module of the concatenation - * @param {Set} modules all modules in the concatenation (including the root module) - * @param {Object=} associatedObjectForCache object for caching - * @param {string | HashConstructor=} hashFunction hash function to use - * @returns {string} the identifier + * @param {LibraryOptions} library normalized library option + * @returns {T | false} preprocess as needed by overriding */ - static _createIdentifier( - rootModule, - modules, - associatedObjectForCache, - hashFunction = "md4" - ) { - const cachedMakePathsRelative = makePathsRelative.bindContextCache( - rootModule.context, - associatedObjectForCache - ); - let identifiers = []; - for (const module of modules) { - identifiers.push(cachedMakePathsRelative(module.identifier())); + parseOptions(library) { + const { name } = library; + if (name) { + throw new Error( + `Library name must be unset. ${AbstractLibraryPlugin.COMMON_LIBRARY_NAME_MESSAGE}` + ); } - identifiers.sort(); - const hash = createHash(hashFunction); - hash.update(identifiers.join(" ")); - return rootModule.identifier() + "|" + hash.digest("hex"); + return { + name: /** @type {string} */ (name) + }; } /** - * @param {LazySet} fileDependencies set where file dependencies are added to - * @param {LazySet} contextDependencies set where context dependencies are added to - * @param {LazySet} missingDependencies set where missing dependencies are added to - * @param {LazySet} buildDependencies set where build dependencies are added to + * @param {Source} source source + * @param {Module} module module + * @param {StartupRenderContext} renderContext render context + * @param {LibraryContext} libraryContext context + * @returns {Source} source with library export */ - addCacheDependencies( - fileDependencies, - contextDependencies, - missingDependencies, - buildDependencies + renderStartup( + source, + module, + { moduleGraph, chunk }, + { options, compilation } ) { - for (const module of this._modules) { - module.addCacheDependencies( - fileDependencies, - contextDependencies, - missingDependencies, - buildDependencies + const result = new ConcatSource(source); + const exportsInfo = moduleGraph.getExportsInfo(module); + const exports = []; + const isAsync = moduleGraph.isAsync(module); + if (isAsync) { + result.add(`__webpack_exports__ = await __webpack_exports__;\n`); + } + for (const exportInfo of exportsInfo.orderedExports) { + if (!exportInfo.provided) continue; + const varName = `__webpack_exports__${Template.toIdentifier( + exportInfo.name + )}`; + result.add( + `var ${varName} = __webpack_exports__${propertyAccess([ + exportInfo.getUsedName(exportInfo.name, chunk.runtime) + ])};\n` ); + exports.push(`${varName} as ${exportInfo.name}`); + } + if (exports.length > 0) { + result.add(`export { ${exports.join(", ")} };\n`); } + return result; } +} - /** - * @param {CodeGenerationContext} context context for code generation - * @returns {CodeGenerationResult} result - */ - codeGeneration({ - dependencyTemplates, - runtimeTemplate, - moduleGraph, - chunkGraph, - runtime: generationRuntime - }) { - /** @type {Set} */ - const runtimeRequirements = new Set(); - const runtime = intersectRuntime(generationRuntime, this._runtime); +module.exports = ModuleLibraryPlugin; - const requestShortener = runtimeTemplate.requestShortener; - // Meta info for each module - const [modulesWithInfo, moduleToInfoMap] = this._getModulesWithInfo( - moduleGraph, - runtime - ); - // Set with modules that need a generated namespace object - /** @type {Set} */ - const neededNamespaceObjects = new Set(); +/***/ }), - // Generate source code and analyse scopes - // Prepare a ReplaceSource for the final source - for (const info of moduleToInfoMap.values()) { - this._analyseModule( - moduleToInfoMap, - info, - dependencyTemplates, - runtimeTemplate, - moduleGraph, - chunkGraph, - runtime - ); - } +/***/ 36253: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - // List of all used names to avoid conflicts - const allUsedNames = new Set(RESERVED_NAMES); +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Joel Denning @joeldenning +*/ - // List of additional names in scope for module references - /** @type {Map, alreadyCheckedScopes: Set }>} */ - const usedNamesInScopeInfo = new Map(); - /** - * @param {string} module module identifier - * @param {string} id export id - * @returns {{ usedNames: Set, alreadyCheckedScopes: Set }} info - */ - const getUsedNamesInScopeInfo = (module, id) => { - const key = `${module}-${id}`; - let info = usedNamesInScopeInfo.get(key); - if (info === undefined) { - info = { - usedNames: new Set(), - alreadyCheckedScopes: new Set() - }; - usedNamesInScopeInfo.set(key, info); - } - return info; - }; - // Set of already checked scopes - const ignoredScopes = new Set(); - // get all global names - for (const info of modulesWithInfo) { - if (info.type === "concatenated") { - // ignore symbols from moduleScope - if (info.moduleScope) { - ignoredScopes.add(info.moduleScope); - } +const { ConcatSource } = __webpack_require__(96192); +const { UsageState } = __webpack_require__(4295); +const ExternalModule = __webpack_require__(89805); +const Template = __webpack_require__(92066); +const propertyAccess = __webpack_require__(86709); +const AbstractLibraryPlugin = __webpack_require__(94051); + +/** @typedef {import("webpack-sources").Source} Source */ +/** @typedef {import("../../declarations/WebpackOptions").LibraryOptions} LibraryOptions */ +/** @typedef {import("../../declarations/WebpackOptions").LibraryType} LibraryType */ +/** @typedef {import("../Chunk")} Chunk */ +/** @typedef {import("../Compilation").ChunkHashContext} ChunkHashContext */ +/** @typedef {import("../Compiler")} Compiler */ +/** @typedef {import("../javascript/JavascriptModulesPlugin").RenderContext} RenderContext */ +/** @typedef {import("../util/Hash")} Hash */ +/** @template T @typedef {import("./AbstractLibraryPlugin").LibraryContext} LibraryContext */ + +/** + * @typedef {Object} SystemLibraryPluginOptions + * @property {LibraryType} type + */ - // The super class expression in class scopes behaves weird - // We get ranges of all super class expressions to make - // renaming to work correctly - const superClassCache = new WeakMap(); - const getSuperClassExpressions = scope => { - const cacheEntry = superClassCache.get(scope); - if (cacheEntry !== undefined) return cacheEntry; - const superClassExpressions = []; - for (const childScope of scope.childScopes) { - if (childScope.type !== "class") continue; - const block = childScope.block; - if ( - (block.type === "ClassDeclaration" || - block.type === "ClassExpression") && - block.superClass - ) { - superClassExpressions.push({ - range: block.superClass.range, - variables: childScope.variables - }); - } - } - superClassCache.set(scope, superClassExpressions); - return superClassExpressions; - }; +/** + * @typedef {Object} SystemLibraryPluginParsed + * @property {string} name + */ - // add global symbols - if (info.globalScope) { - for (const reference of info.globalScope.through) { - const name = reference.identifier.name; - if (ConcatenationScope.isModuleReference(name)) { - const match = ConcatenationScope.matchModuleReference(name); - if (!match) continue; - const referencedInfo = modulesWithInfo[match.index]; - if (referencedInfo.type === "reference") - throw new Error("Module reference can't point to a reference"); - const binding = getFinalBinding( - moduleGraph, - referencedInfo, - match.ids, - moduleToInfoMap, - runtime, - requestShortener, - runtimeTemplate, - neededNamespaceObjects, - false, - info.module.buildMeta.strictHarmonyModule, - true - ); - if (!binding.ids) continue; - const { usedNames, alreadyCheckedScopes } = - getUsedNamesInScopeInfo( - binding.info.module.identifier(), - "name" in binding ? binding.name : "" - ); - for (const expr of getSuperClassExpressions(reference.from)) { - if ( - expr.range[0] <= reference.identifier.range[0] && - expr.range[1] >= reference.identifier.range[1] - ) { - for (const variable of expr.variables) { - usedNames.add(variable.name); - } - } - } - addScopeSymbols( - reference.from, - usedNames, - alreadyCheckedScopes, - ignoredScopes - ); - } else { - allUsedNames.add(name); - } - } - } - } - } +/** + * @typedef {SystemLibraryPluginParsed} T + * @extends {AbstractLibraryPlugin} + */ +class SystemLibraryPlugin extends AbstractLibraryPlugin { + /** + * @param {SystemLibraryPluginOptions} options the plugin options + */ + constructor(options) { + super({ + pluginName: "SystemLibraryPlugin", + type: options.type + }); + } - // generate names for symbols - for (const info of moduleToInfoMap.values()) { - const { usedNames: namespaceObjectUsedNames } = getUsedNamesInScopeInfo( - info.module.identifier(), - "" + /** + * @param {LibraryOptions} library normalized library option + * @returns {T | false} preprocess as needed by overriding + */ + parseOptions(library) { + const { name } = library; + if (name && typeof name !== "string") { + throw new Error( + `System.js library name must be a simple string or unset. ${AbstractLibraryPlugin.COMMON_LIBRARY_NAME_MESSAGE}` ); - switch (info.type) { - case "concatenated": { - for (const variable of info.moduleScope.variables) { - const name = variable.name; - const { usedNames, alreadyCheckedScopes } = getUsedNamesInScopeInfo( - info.module.identifier(), - name - ); - if (allUsedNames.has(name) || usedNames.has(name)) { - const references = getAllReferences(variable); - for (const ref of references) { - addScopeSymbols( - ref.from, - usedNames, - alreadyCheckedScopes, - ignoredScopes - ); - } - const newName = this.findNewName( - name, - allUsedNames, - usedNames, - info.module.readableIdentifier(requestShortener) - ); - allUsedNames.add(newName); - info.internalNames.set(name, newName); - const source = info.source; - const allIdentifiers = new Set( - references.map(r => r.identifier).concat(variable.identifiers) - ); - for (const identifier of allIdentifiers) { - const r = identifier.range; - const path = getPathInAst(info.ast, identifier); - if (path && path.length > 1) { - const maybeProperty = - path[1].type === "AssignmentPattern" && - path[1].left === path[0] - ? path[2] - : path[1]; - if ( - maybeProperty.type === "Property" && - maybeProperty.shorthand - ) { - source.insert(r[1], `: ${newName}`); - continue; - } - } - source.replace(r[0], r[1] - 1, newName); - } - } else { - allUsedNames.add(name); - info.internalNames.set(name, name); - } - } - let namespaceObjectName; - if (info.namespaceExportSymbol) { - namespaceObjectName = info.internalNames.get( - info.namespaceExportSymbol - ); - } else { - namespaceObjectName = this.findNewName( - "namespaceObject", - allUsedNames, - namespaceObjectUsedNames, - info.module.readableIdentifier(requestShortener) - ); - allUsedNames.add(namespaceObjectName); - } - info.namespaceObjectName = namespaceObjectName; - break; - } - case "external": { - const externalName = this.findNewName( - "", - allUsedNames, - namespaceObjectUsedNames, - info.module.readableIdentifier(requestShortener) - ); - allUsedNames.add(externalName); - info.name = externalName; - break; - } - } - if (info.module.buildMeta.exportsType !== "namespace") { - const externalNameInterop = this.findNewName( - "namespaceObject", - allUsedNames, - namespaceObjectUsedNames, - info.module.readableIdentifier(requestShortener) - ); - allUsedNames.add(externalNameInterop); - info.interopNamespaceObjectName = externalNameInterop; - } - if ( - info.module.buildMeta.exportsType === "default" && - info.module.buildMeta.defaultObject !== "redirect" - ) { - const externalNameInterop = this.findNewName( - "namespaceObject2", - allUsedNames, - namespaceObjectUsedNames, - info.module.readableIdentifier(requestShortener) - ); - allUsedNames.add(externalNameInterop); - info.interopNamespaceObject2Name = externalNameInterop; - } - if ( - info.module.buildMeta.exportsType === "dynamic" || - !info.module.buildMeta.exportsType - ) { - const externalNameInterop = this.findNewName( - "default", - allUsedNames, - namespaceObjectUsedNames, - info.module.readableIdentifier(requestShortener) - ); - allUsedNames.add(externalNameInterop); - info.interopDefaultAccessName = externalNameInterop; - } } + return { + name: /** @type {string=} */ (name) + }; + } - // Find and replace references to modules - for (const info of moduleToInfoMap.values()) { - if (info.type === "concatenated") { - for (const reference of info.globalScope.through) { - const name = reference.identifier.name; - const match = ConcatenationScope.matchModuleReference(name); - if (match) { - const referencedInfo = modulesWithInfo[match.index]; - if (referencedInfo.type === "reference") - throw new Error("Module reference can't point to a reference"); - const finalName = getFinalName( - moduleGraph, - referencedInfo, - match.ids, - moduleToInfoMap, - runtime, - requestShortener, - runtimeTemplate, - neededNamespaceObjects, - match.call, - !match.directImport, - info.module.buildMeta.strictHarmonyModule, - match.asiSafe - ); - const r = reference.identifier.range; - const source = info.source; - // range is extended by 2 chars to cover the appended "._" - source.replace(r[0], r[1] + 1, finalName); - } - } - } - } + /** + * @param {Source} source source + * @param {RenderContext} renderContext render context + * @param {LibraryContext} libraryContext context + * @returns {Source} source with library export + */ + render(source, { chunkGraph, moduleGraph, chunk }, { options, compilation }) { + const modules = chunkGraph + .getChunkModules(chunk) + .filter(m => m instanceof ExternalModule && m.externalType === "system"); + const externals = /** @type {ExternalModule[]} */ (modules); - // Map with all root exposed used exports - /** @type {Map} */ - const exportsMap = new Map(); + // The name this bundle should be registered as with System + const name = options.name + ? `${JSON.stringify(compilation.getPath(options.name, { chunk }))}, ` + : ""; - // Set with all root exposed unused exports - /** @type {Set} */ - const unusedExports = new Set(); + // The array of dependencies that are external to webpack and will be provided by System + const systemDependencies = JSON.stringify( + externals.map(m => + typeof m.request === "object" && !Array.isArray(m.request) + ? m.request.amd + : m.request + ) + ); - const rootInfo = /** @type {ConcatenatedModuleInfo} */ ( - moduleToInfoMap.get(this.rootModule) + // The name of the variable provided by System for exporting + const dynamicExport = "__WEBPACK_DYNAMIC_EXPORT__"; + + // An array of the internal variable names for the webpack externals + const externalWebpackNames = externals.map( + m => + `__WEBPACK_EXTERNAL_MODULE_${Template.toIdentifier( + `${chunkGraph.getModuleId(m)}` + )}__` ); - const strictHarmonyModule = rootInfo.module.buildMeta.strictHarmonyModule; - const exportsInfo = moduleGraph.getExportsInfo(rootInfo.module); - for (const exportInfo of exportsInfo.orderedExports) { - const name = exportInfo.name; - if (exportInfo.provided === false) continue; - const used = exportInfo.getUsedName(undefined, runtime); - if (!used) { - unusedExports.add(name); - continue; - } - exportsMap.set(used, requestShortener => { - try { - const finalName = getFinalName( - moduleGraph, - rootInfo, - [name], - moduleToInfoMap, - runtime, - requestShortener, - runtimeTemplate, - neededNamespaceObjects, - false, - false, - strictHarmonyModule, - true - ); - return `/* ${ - exportInfo.isReexport() ? "reexport" : "binding" - } */ ${finalName}`; - } catch (e) { - e.message += `\nwhile generating the root export '${name}' (used name: '${used}')`; - throw e; - } - }); - } - const result = new ConcatSource(); + // Declaring variables for the internal variable names for the webpack externals + const externalVarDeclarations = externalWebpackNames + .map(name => `var ${name} = {};`) + .join("\n"); - // add harmony compatibility flag (must be first because of possible circular dependencies) - if ( - moduleGraph.getExportsInfo(this).otherExportsInfo.getUsed(runtime) !== - UsageState.Unused - ) { - result.add(`// ESM COMPAT FLAG\n`); - result.add( - runtimeTemplate.defineEsModuleFlagStatement({ - exportsArgument: this.exportsArgument, - runtimeRequirements - }) - ); - } + // Define __esModule flag on all internal variables and helpers + const externalVarInitialization = []; - // define exports - if (exportsMap.size > 0) { - runtimeRequirements.add(RuntimeGlobals.exports); - runtimeRequirements.add(RuntimeGlobals.definePropertyGetters); - const definitions = []; - for (const [key, value] of exportsMap) { - definitions.push( - `\n ${JSON.stringify(key)}: ${runtimeTemplate.returningFunction( - value(requestShortener) - )}` - ); - } - result.add(`\n// EXPORTS\n`); - result.add( - `${RuntimeGlobals.definePropertyGetters}(${ - this.exportsArgument - }, {${definitions.join(",")}\n});\n` - ); + // The system.register format requires an array of setter functions for externals. + const setters = + externalWebpackNames.length === 0 + ? "" + : Template.asString([ + "setters: [", + Template.indent( + externals + .map((module, i) => { + const external = externalWebpackNames[i]; + const exportsInfo = moduleGraph.getExportsInfo(module); + const otherUnused = + exportsInfo.otherExportsInfo.getUsed(chunk.runtime) === + UsageState.Unused; + const instructions = []; + const handledNames = []; + for (const exportInfo of exportsInfo.orderedExports) { + const used = exportInfo.getUsedName( + undefined, + chunk.runtime + ); + if (used) { + if (otherUnused || used !== exportInfo.name) { + instructions.push( + `${external}${propertyAccess([ + used + ])} = module${propertyAccess([exportInfo.name])};` + ); + handledNames.push(exportInfo.name); + } + } else { + handledNames.push(exportInfo.name); + } + } + if (!otherUnused) { + if ( + !Array.isArray(module.request) || + module.request.length === 1 + ) { + externalVarInitialization.push( + `Object.defineProperty(${external}, "__esModule", { value: true });` + ); + } + if (handledNames.length > 0) { + const name = `${external}handledNames`; + externalVarInitialization.push( + `var ${name} = ${JSON.stringify(handledNames)};` + ); + instructions.push( + Template.asString([ + "Object.keys(module).forEach(function(key) {", + Template.indent([ + `if(${name}.indexOf(key) >= 0)`, + Template.indent(`${external}[key] = module[key];`) + ]), + "});" + ]) + ); + } else { + instructions.push( + Template.asString([ + "Object.keys(module).forEach(function(key) {", + Template.indent([`${external}[key] = module[key];`]), + "});" + ]) + ); + } + } + if (instructions.length === 0) return "function() {}"; + return Template.asString([ + "function(module) {", + Template.indent(instructions), + "}" + ]); + }) + .join(",\n") + ), + "]," + ]); + + return new ConcatSource( + Template.asString([ + `System.register(${name}${systemDependencies}, function(${dynamicExport}, __system_context__) {`, + Template.indent([ + externalVarDeclarations, + Template.asString(externalVarInitialization), + "return {", + Template.indent([ + setters, + "execute: function() {", + Template.indent(`${dynamicExport}(`) + ]) + ]), + "" + ]), + source, + Template.asString([ + "", + Template.indent([ + Template.indent([Template.indent([");"]), "}"]), + "};" + ]), + "})" + ]) + ); + } + + /** + * @param {Chunk} chunk the chunk + * @param {Hash} hash hash + * @param {ChunkHashContext} chunkHashContext chunk hash context + * @param {LibraryContext} libraryContext context + * @returns {void} + */ + chunkHash(chunk, hash, chunkHashContext, { options, compilation }) { + hash.update("SystemLibraryPlugin"); + if (options.name) { + hash.update(compilation.getPath(options.name, { chunk })); } + } +} - // list unused exports - if (unusedExports.size > 0) { - result.add( - `\n// UNUSED EXPORTS: ${joinIterableWithComma(unusedExports)}\n` - ); - } +module.exports = SystemLibraryPlugin; - // generate namespace objects - const namespaceObjectSources = new Map(); - for (const info of neededNamespaceObjects) { - if (info.namespaceExportSymbol) continue; - const nsObj = []; - const exportsInfo = moduleGraph.getExportsInfo(info.module); - for (const exportInfo of exportsInfo.orderedExports) { - if (exportInfo.provided === false) continue; - const usedName = exportInfo.getUsedName(undefined, runtime); - if (usedName) { - const finalName = getFinalName( - moduleGraph, - info, - [exportInfo.name], - moduleToInfoMap, - runtime, - requestShortener, - runtimeTemplate, - neededNamespaceObjects, - false, - undefined, - info.module.buildMeta.strictHarmonyModule, - true - ); - nsObj.push( - `\n ${JSON.stringify( - usedName - )}: ${runtimeTemplate.returningFunction(finalName)}` - ); - } - } - const name = info.namespaceObjectName; - const defineGetters = - nsObj.length > 0 - ? `${RuntimeGlobals.definePropertyGetters}(${name}, {${nsObj.join( - "," - )}\n});\n` - : ""; - if (nsObj.length > 0) - runtimeRequirements.add(RuntimeGlobals.definePropertyGetters); - namespaceObjectSources.set( - info, - ` -// NAMESPACE OBJECT: ${info.module.readableIdentifier(requestShortener)} -var ${name} = {}; -${RuntimeGlobals.makeNamespaceObject}(${name}); -${defineGetters}` - ); - runtimeRequirements.add(RuntimeGlobals.makeNamespaceObject); - } - // define required namespace objects (must be before evaluation modules) - for (const info of modulesWithInfo) { - if (info.type === "concatenated") { - const source = namespaceObjectSources.get(info); - if (!source) continue; - result.add(source); - } - } +/***/ }), - const chunkInitFragments = []; +/***/ 59401: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - // evaluate modules in order - for (const rawInfo of modulesWithInfo) { - let name; - let isConditional = false; - const info = rawInfo.type === "reference" ? rawInfo.target : rawInfo; - switch (info.type) { - case "concatenated": { - result.add( - `\n;// CONCATENATED MODULE: ${info.module.readableIdentifier( - requestShortener - )}\n` - ); - result.add(info.source); - if (info.chunkInitFragments) { - for (const f of info.chunkInitFragments) chunkInitFragments.push(f); - } - if (info.runtimeRequirements) { - for (const r of info.runtimeRequirements) { - runtimeRequirements.add(r); - } - } - name = info.namespaceObjectName; - break; - } - case "external": { - result.add( - `\n// EXTERNAL MODULE: ${info.module.readableIdentifier( - requestShortener - )}\n` - ); - runtimeRequirements.add(RuntimeGlobals.require); - const { runtimeCondition } = - /** @type {ExternalModuleInfo | ReferenceToModuleInfo} */ (rawInfo); - const condition = runtimeTemplate.runtimeConditionExpression({ - chunkGraph, - runtimeCondition, - runtime, - runtimeRequirements - }); - if (condition !== "true") { - isConditional = true; - result.add(`if (${condition}) {\n`); - } - result.add( - `var ${info.name} = __webpack_require__(${JSON.stringify( - chunkGraph.getModuleId(info.module) - )});` - ); - name = info.name; - break; - } - default: - // @ts-expect-error never is expected here - throw new Error(`Unsupported concatenation entry type ${info.type}`); - } - if (info.interopNamespaceObjectUsed) { - runtimeRequirements.add(RuntimeGlobals.createFakeNamespaceObject); - result.add( - `\nvar ${info.interopNamespaceObjectName} = /*#__PURE__*/${RuntimeGlobals.createFakeNamespaceObject}(${name}, 2);` - ); - } - if (info.interopNamespaceObject2Used) { - runtimeRequirements.add(RuntimeGlobals.createFakeNamespaceObject); - result.add( - `\nvar ${info.interopNamespaceObject2Name} = /*#__PURE__*/${RuntimeGlobals.createFakeNamespaceObject}(${name});` - ); - } - if (info.interopDefaultAccessUsed) { - runtimeRequirements.add(RuntimeGlobals.compatGetDefaultExport); - result.add( - `\nvar ${info.interopDefaultAccessName} = /*#__PURE__*/${RuntimeGlobals.compatGetDefaultExport}(${name});` - ); - } - if (isConditional) { - result.add("\n}"); - } - } +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ - const data = new Map(); - if (chunkInitFragments.length > 0) - data.set("chunkInitFragments", chunkInitFragments); - /** @type {CodeGenerationResult} */ - const resultEntry = { - sources: new Map([["javascript", new CachedSource(result)]]), - data, - runtimeRequirements - }; - return resultEntry; - } +const { ConcatSource, OriginalSource } = __webpack_require__(96192); +const ExternalModule = __webpack_require__(89805); +const Template = __webpack_require__(92066); +const AbstractLibraryPlugin = __webpack_require__(94051); + +/** @typedef {import("webpack-sources").Source} Source */ +/** @typedef {import("../../declarations/WebpackOptions").LibraryCustomUmdCommentObject} LibraryCustomUmdCommentObject */ +/** @typedef {import("../../declarations/WebpackOptions").LibraryCustomUmdObject} LibraryCustomUmdObject */ +/** @typedef {import("../../declarations/WebpackOptions").LibraryName} LibraryName */ +/** @typedef {import("../../declarations/WebpackOptions").LibraryOptions} LibraryOptions */ +/** @typedef {import("../../declarations/WebpackOptions").LibraryType} LibraryType */ +/** @typedef {import("../Compiler")} Compiler */ +/** @typedef {import("../javascript/JavascriptModulesPlugin").RenderContext} RenderContext */ +/** @typedef {import("../util/Hash")} Hash */ +/** @template T @typedef {import("./AbstractLibraryPlugin").LibraryContext} LibraryContext */ + +/** + * @param {string[]} accessor the accessor to convert to path + * @returns {string} the path + */ +const accessorToObjectAccess = accessor => { + return accessor.map(a => `[${JSON.stringify(a)}]`).join(""); +}; + +/** + * @param {string|undefined} base the path prefix + * @param {string|string[]} accessor the accessor + * @param {string=} joinWith the element separator + * @returns {string} the path + */ +const accessorAccess = (base, accessor, joinWith = ", ") => { + const accessors = Array.isArray(accessor) ? accessor : [accessor]; + return accessors + .map((_, idx) => { + const a = base + ? base + accessorToObjectAccess(accessors.slice(0, idx + 1)) + : accessors[0] + accessorToObjectAccess(accessors.slice(1, idx + 1)); + if (idx === accessors.length - 1) return a; + if (idx === 0 && base === undefined) + return `${a} = typeof ${a} === "object" ? ${a} : {}`; + return `${a} = ${a} || {}`; + }) + .join(joinWith); +}; + +/** @typedef {string | string[] | LibraryCustomUmdObject} UmdLibraryPluginName */ + +/** + * @typedef {Object} UmdLibraryPluginOptions + * @property {LibraryType} type + * @property {boolean=} optionalAmdExternalAsGlobal + */ +/** + * @typedef {Object} UmdLibraryPluginParsed + * @property {string | string[]} name + * @property {LibraryCustomUmdObject} names + * @property {string | LibraryCustomUmdCommentObject} auxiliaryComment + * @property {boolean} namedDefine + */ + +/** + * @typedef {UmdLibraryPluginParsed} T + * @extends {AbstractLibraryPlugin} + */ +class UmdLibraryPlugin extends AbstractLibraryPlugin { /** - * @param {Map} modulesMap modulesMap - * @param {ModuleInfo} info info - * @param {DependencyTemplates} dependencyTemplates dependencyTemplates - * @param {RuntimeTemplate} runtimeTemplate runtimeTemplate - * @param {ModuleGraph} moduleGraph moduleGraph - * @param {ChunkGraph} chunkGraph chunkGraph - * @param {RuntimeSpec} runtime runtime + * @param {UmdLibraryPluginOptions} options the plugin option */ - _analyseModule( - modulesMap, - info, - dependencyTemplates, - runtimeTemplate, - moduleGraph, - chunkGraph, - runtime - ) { - if (info.type === "concatenated") { - const m = info.module; - try { - // Create a concatenation scope to track and capture information - const concatenationScope = new ConcatenationScope(modulesMap, info); + constructor(options) { + super({ + pluginName: "UmdLibraryPlugin", + type: options.type + }); - // TODO cache codeGeneration results - const codeGenResult = m.codeGeneration({ - dependencyTemplates, - runtimeTemplate, - moduleGraph, - chunkGraph, - runtime, - concatenationScope - }); - const source = codeGenResult.sources.get("javascript"); - const data = codeGenResult.data; - const chunkInitFragments = data && data.get("chunkInitFragments"); - const code = source.source().toString(); - let ast; - try { - ast = JavascriptParser._parse(code, { - sourceType: "module" - }); - } catch (err) { - if ( - err.loc && - typeof err.loc === "object" && - typeof err.loc.line === "number" - ) { - const lineNumber = err.loc.line; - const lines = code.split("\n"); - err.message += - "\n| " + - lines - .slice(Math.max(0, lineNumber - 3), lineNumber + 2) - .join("\n| "); - } - throw err; - } - const scopeManager = eslintScope.analyze(ast, { - ecmaVersion: 6, - sourceType: "module", - optimistic: true, - ignoreEval: true, - impliedStrict: true - }); - const globalScope = scopeManager.acquire(ast); - const moduleScope = globalScope.childScopes[0]; - const resultSource = new ReplaceSource(source); - info.runtimeRequirements = codeGenResult.runtimeRequirements; - info.ast = ast; - info.internalSource = source; - info.source = resultSource; - info.chunkInitFragments = chunkInitFragments; - info.globalScope = globalScope; - info.moduleScope = moduleScope; - } catch (err) { - err.message += `\nwhile analysing module ${m.identifier()} for concatenation`; - throw err; - } + this.optionalAmdExternalAsGlobal = options.optionalAmdExternalAsGlobal; + } + + /** + * @param {LibraryOptions} library normalized library option + * @returns {T | false} preprocess as needed by overriding + */ + parseOptions(library) { + /** @type {LibraryName} */ + let name; + /** @type {LibraryCustomUmdObject} */ + let names; + if (typeof library.name === "object" && !Array.isArray(library.name)) { + name = library.name.root || library.name.amd || library.name.commonjs; + names = library.name; + } else { + name = library.name; + const singleName = Array.isArray(name) ? name[0] : name; + names = { + commonjs: singleName, + root: library.name, + amd: singleName + }; } + return { + name, + names, + auxiliaryComment: library.auxiliaryComment, + namedDefine: library.umdNamedDefine + }; } /** - * @param {ModuleGraph} moduleGraph the module graph - * @param {RuntimeSpec} runtime the runtime - * @returns {[ModuleInfoOrReference[], Map]} module info items + * @param {Source} source source + * @param {RenderContext} renderContext render context + * @param {LibraryContext} libraryContext context + * @returns {Source} source with library export */ - _getModulesWithInfo(moduleGraph, runtime) { - const orderedConcatenationList = this._createConcatenationList( - this.rootModule, - this._modules, - runtime, - moduleGraph - ); - /** @type {Map} */ - const map = new Map(); - const list = orderedConcatenationList.map((info, index) => { - let item = map.get(info.module); - if (item === undefined) { - switch (info.type) { - case "concatenated": - item = { - type: "concatenated", - module: info.module, - index, - ast: undefined, - internalSource: undefined, - runtimeRequirements: undefined, - source: undefined, - globalScope: undefined, - moduleScope: undefined, - internalNames: new Map(), - exportMap: undefined, - rawExportMap: undefined, - namespaceExportSymbol: undefined, - namespaceObjectName: undefined, - interopNamespaceObjectUsed: false, - interopNamespaceObjectName: undefined, - interopNamespaceObject2Used: false, - interopNamespaceObject2Name: undefined, - interopDefaultAccessUsed: false, - interopDefaultAccessName: undefined - }; - break; - case "external": - item = { - type: "external", - module: info.module, - runtimeCondition: info.runtimeCondition, - index, - name: undefined, - interopNamespaceObjectUsed: false, - interopNamespaceObjectName: undefined, - interopNamespaceObject2Used: false, - interopNamespaceObject2Name: undefined, - interopDefaultAccessUsed: false, - interopDefaultAccessName: undefined - }; - break; - default: - throw new Error( - `Unsupported concatenation entry type ${info.type}` - ); + render( + source, + { chunkGraph, runtimeTemplate, chunk, moduleGraph }, + { options, compilation } + ) { + const modules = chunkGraph + .getChunkModules(chunk) + .filter( + m => + m instanceof ExternalModule && + (m.externalType === "umd" || m.externalType === "umd2") + ); + let externals = /** @type {ExternalModule[]} */ (modules); + /** @type {ExternalModule[]} */ + const optionalExternals = []; + /** @type {ExternalModule[]} */ + let requiredExternals = []; + if (this.optionalAmdExternalAsGlobal) { + for (const m of externals) { + if (m.isOptional(moduleGraph)) { + optionalExternals.push(m); + } else { + requiredExternals.push(m); } - map.set(item.module, item); - return item; - } else { - /** @type {ReferenceToModuleInfo} */ - const ref = { - type: "reference", - runtimeCondition: info.runtimeCondition, - target: item - }; - return ref; } - }); - return [list, map]; - } + externals = requiredExternals.concat(optionalExternals); + } else { + requiredExternals = externals; + } - findNewName(oldName, usedNamed1, usedNamed2, extraInfo) { - let name = oldName; + const replaceKeys = str => { + return compilation.getPath(str, { + chunk + }); + }; + + const externalsDepsArray = modules => { + return `[${replaceKeys( + modules + .map(m => + JSON.stringify( + typeof m.request === "object" ? m.request.amd : m.request + ) + ) + .join(", ") + )}]`; + }; + + const externalsRootArray = modules => { + return replaceKeys( + modules + .map(m => { + let request = m.request; + if (typeof request === "object") request = request.root; + return `root${accessorToObjectAccess([].concat(request))}`; + }) + .join(", ") + ); + }; + + const externalsRequireArray = type => { + return replaceKeys( + externals + .map(m => { + let expr; + let request = m.request; + if (typeof request === "object") { + request = request[type]; + } + if (request === undefined) { + throw new Error( + "Missing external configuration for type:" + type + ); + } + if (Array.isArray(request)) { + expr = `require(${JSON.stringify( + request[0] + )})${accessorToObjectAccess(request.slice(1))}`; + } else { + expr = `require(${JSON.stringify(request)})`; + } + if (m.isOptional(moduleGraph)) { + expr = `(function webpackLoadOptionalExternalModule() { try { return ${expr}; } catch(e) {} }())`; + } + return expr; + }) + .join(", ") + ); + }; - if (name === ConcatenationScope.DEFAULT_EXPORT) { - name = ""; - } - if (name === ConcatenationScope.NAMESPACE_OBJECT_EXPORT) { - name = "namespaceObject"; - } + const externalsArguments = modules => { + return modules + .map( + m => + `__WEBPACK_EXTERNAL_MODULE_${Template.toIdentifier( + `${chunkGraph.getModuleId(m)}` + )}__` + ) + .join(", "); + }; - // Remove uncool stuff - extraInfo = extraInfo.replace( - /\.+\/|(\/index)?\.([a-zA-Z0-9]{1,4})($|\s|\?)|\s*\+\s*\d+\s*modules/g, - "" - ); + const libraryName = library => { + return JSON.stringify(replaceKeys([].concat(library).pop())); + }; - const splittedInfo = extraInfo.split("/"); - while (splittedInfo.length) { - name = splittedInfo.pop() + (name ? "_" + name : ""); - const nameIdent = Template.toIdentifier(name); - if ( - !usedNamed1.has(nameIdent) && - (!usedNamed2 || !usedNamed2.has(nameIdent)) - ) - return nameIdent; + let amdFactory; + if (optionalExternals.length > 0) { + const wrapperArguments = externalsArguments(requiredExternals); + const factoryArguments = + requiredExternals.length > 0 + ? externalsArguments(requiredExternals) + + ", " + + externalsRootArray(optionalExternals) + : externalsRootArray(optionalExternals); + amdFactory = + `function webpackLoadOptionalExternalModuleAmd(${wrapperArguments}) {\n` + + ` return factory(${factoryArguments});\n` + + " }"; + } else { + amdFactory = "factory"; } - let i = 0; - let nameWithNumber = Template.toIdentifier(`${name}_${i}`); - while ( - usedNamed1.has(nameWithNumber) || - (usedNamed2 && usedNamed2.has(nameWithNumber)) - ) { - i++; - nameWithNumber = Template.toIdentifier(`${name}_${i}`); - } - return nameWithNumber; - } + const { auxiliaryComment, namedDefine, names } = options; - /** - * @param {Hash} hash the hash used to track dependencies - * @param {UpdateHashContext} context context - * @returns {void} - */ - updateHash(hash, context) { - const { chunkGraph, runtime } = context; - for (const info of this._createConcatenationList( - this.rootModule, - this._modules, - intersectRuntime(runtime, this._runtime), - chunkGraph.moduleGraph - )) { - switch (info.type) { - case "concatenated": - info.module.updateHash(hash, context); - break; - case "external": - hash.update(`${chunkGraph.getModuleId(info.module)}`); - // TODO runtimeCondition - break; + const getAuxiliaryComment = type => { + if (auxiliaryComment) { + if (typeof auxiliaryComment === "string") + return "\t//" + auxiliaryComment + "\n"; + if (auxiliaryComment[type]) + return "\t//" + auxiliaryComment[type] + "\n"; } - } - super.updateHash(hash, context); - } + return ""; + }; - static deserialize(context) { - const obj = new ConcatenatedModule({ - identifier: undefined, - rootModule: undefined, - modules: undefined, - runtime: undefined - }); - obj.deserialize(context); - return obj; + return new ConcatSource( + new OriginalSource( + "(function webpackUniversalModuleDefinition(root, factory) {\n" + + getAuxiliaryComment("commonjs2") + + " if(typeof exports === 'object' && typeof module === 'object')\n" + + " module.exports = factory(" + + externalsRequireArray("commonjs2") + + ");\n" + + getAuxiliaryComment("amd") + + " else if(typeof define === 'function' && define.amd)\n" + + (requiredExternals.length > 0 + ? names.amd && namedDefine === true + ? " define(" + + libraryName(names.amd) + + ", " + + externalsDepsArray(requiredExternals) + + ", " + + amdFactory + + ");\n" + : " define(" + + externalsDepsArray(requiredExternals) + + ", " + + amdFactory + + ");\n" + : names.amd && namedDefine === true + ? " define(" + + libraryName(names.amd) + + ", [], " + + amdFactory + + ");\n" + : " define([], " + amdFactory + ");\n") + + (names.root || names.commonjs + ? getAuxiliaryComment("commonjs") + + " else if(typeof exports === 'object')\n" + + " exports[" + + libraryName(names.commonjs || names.root) + + "] = factory(" + + externalsRequireArray("commonjs") + + ");\n" + + getAuxiliaryComment("root") + + " else\n" + + " " + + replaceKeys( + accessorAccess("root", names.root || names.commonjs) + ) + + " = factory(" + + externalsRootArray(externals) + + ");\n" + : " else {\n" + + (externals.length > 0 + ? " var a = typeof exports === 'object' ? factory(" + + externalsRequireArray("commonjs") + + ") : factory(" + + externalsRootArray(externals) + + ");\n" + : " var a = factory();\n") + + " for(var i in a) (typeof exports === 'object' ? exports : root)[i] = a[i];\n" + + " }\n") + + `})(${ + runtimeTemplate.outputOptions.globalObject + }, function(${externalsArguments(externals)}) {\nreturn `, + "webpack/universalModuleDefinition" + ), + source, + ";\n})" + ); } } -makeSerializable(ConcatenatedModule, "webpack/lib/optimize/ConcatenatedModule"); - -module.exports = ConcatenatedModule; +module.exports = UmdLibraryPlugin; /***/ }), -/***/ 91120: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { +/***/ 54667: +/***/ (function(__unused_webpack_module, exports) { "use strict"; /* @@ -103195,569 +100867,493 @@ module.exports = ConcatenatedModule; -const { STAGE_BASIC } = __webpack_require__(68145); +const LogType = Object.freeze({ + error: /** @type {"error"} */ ("error"), // message, c style arguments + warn: /** @type {"warn"} */ ("warn"), // message, c style arguments + info: /** @type {"info"} */ ("info"), // message, c style arguments + log: /** @type {"log"} */ ("log"), // message, c style arguments + debug: /** @type {"debug"} */ ("debug"), // message, c style arguments -/** @typedef {import("../Chunk")} Chunk */ -/** @typedef {import("../ChunkGroup")} ChunkGroup */ -/** @typedef {import("../Compiler")} Compiler */ + trace: /** @type {"trace"} */ ("trace"), // no arguments -class EnsureChunkConditionsPlugin { + group: /** @type {"group"} */ ("group"), // [label] + groupCollapsed: /** @type {"groupCollapsed"} */ ("groupCollapsed"), // [label] + groupEnd: /** @type {"groupEnd"} */ ("groupEnd"), // [label] + + profile: /** @type {"profile"} */ ("profile"), // [profileName] + profileEnd: /** @type {"profileEnd"} */ ("profileEnd"), // [profileName] + + time: /** @type {"time"} */ ("time"), // name, time as [seconds, nanoseconds] + + clear: /** @type {"clear"} */ ("clear"), // no arguments + status: /** @type {"status"} */ ("status") // message, arguments +}); + +exports.LogType = LogType; + +/** @typedef {typeof LogType[keyof typeof LogType]} LogTypeEnum */ + +const LOG_SYMBOL = Symbol("webpack logger raw log method"); +const TIMERS_SYMBOL = Symbol("webpack logger times"); +const TIMERS_AGGREGATES_SYMBOL = Symbol("webpack logger aggregated times"); + +class WebpackLogger { /** - * Apply the plugin - * @param {Compiler} compiler the compiler instance - * @returns {void} + * @param {function(LogTypeEnum, any[]=): void} log log function + * @param {function(string | function(): string): WebpackLogger} getChildLogger function to create child logger */ - apply(compiler) { - compiler.hooks.compilation.tap( - "EnsureChunkConditionsPlugin", - compilation => { - const handler = chunks => { - const chunkGraph = compilation.chunkGraph; - // These sets are hoisted here to save memory - // They are cleared at the end of every loop - /** @type {Set} */ - const sourceChunks = new Set(); - /** @type {Set} */ - const chunkGroups = new Set(); - for (const module of compilation.modules) { - if (!module.hasChunkCondition()) continue; - for (const chunk of chunkGraph.getModuleChunksIterable(module)) { - if (!module.chunkCondition(chunk, compilation)) { - sourceChunks.add(chunk); - for (const group of chunk.groupsIterable) { - chunkGroups.add(group); - } - } - } - if (sourceChunks.size === 0) continue; - /** @type {Set} */ - const targetChunks = new Set(); - chunkGroupLoop: for (const chunkGroup of chunkGroups) { - // Can module be placed in a chunk of this group? - for (const chunk of chunkGroup.chunks) { - if (module.chunkCondition(chunk, compilation)) { - targetChunks.add(chunk); - continue chunkGroupLoop; - } - } - // We reached the entrypoint: fail - if (chunkGroup.isInitial()) { - throw new Error( - "Cannot fullfil chunk condition of " + module.identifier() - ); - } - // Try placing in all parents - for (const group of chunkGroup.parentsIterable) { - chunkGroups.add(group); - } - } - for (const sourceChunk of sourceChunks) { - chunkGraph.disconnectChunkAndModule(sourceChunk, module); - } - for (const targetChunk of targetChunks) { - chunkGraph.connectChunkAndModule(targetChunk, module); - } - sourceChunks.clear(); - chunkGroups.clear(); - } - }; - compilation.hooks.optimizeChunks.tap( - { - name: "EnsureChunkConditionsPlugin", - stage: STAGE_BASIC - }, - handler - ); - } - ); + constructor(log, getChildLogger) { + this[LOG_SYMBOL] = log; + this.getChildLogger = getChildLogger; } -} -module.exports = EnsureChunkConditionsPlugin; + error(...args) { + this[LOG_SYMBOL](LogType.error, args); + } -/***/ }), - -/***/ 48424: -/***/ (function(module) { + warn(...args) { + this[LOG_SYMBOL](LogType.warn, args); + } -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ + info(...args) { + this[LOG_SYMBOL](LogType.info, args); + } + log(...args) { + this[LOG_SYMBOL](LogType.log, args); + } + debug(...args) { + this[LOG_SYMBOL](LogType.debug, args); + } -/** @typedef {import("../Chunk")} Chunk */ -/** @typedef {import("../Compiler")} Compiler */ -/** @typedef {import("../Module")} Module */ + assert(assertion, ...args) { + if (!assertion) { + this[LOG_SYMBOL](LogType.error, args); + } + } -class FlagIncludedChunksPlugin { - /** - * Apply the plugin - * @param {Compiler} compiler the compiler instance - * @returns {void} - */ - apply(compiler) { - compiler.hooks.compilation.tap("FlagIncludedChunksPlugin", compilation => { - compilation.hooks.optimizeChunkIds.tap( - "FlagIncludedChunksPlugin", - chunks => { - const chunkGraph = compilation.chunkGraph; + trace() { + this[LOG_SYMBOL](LogType.trace, ["Trace"]); + } - // prepare two bit integers for each module - // 2^31 is the max number represented as SMI in v8 - // we want the bits distributed this way: - // the bit 2^31 is pretty rar and only one module should get it - // so it has a probability of 1 / modulesCount - // the first bit (2^0) is the easiest and every module could get it - // if it doesn't get a better bit - // from bit 2^n to 2^(n+1) there is a probability of p - // so 1 / modulesCount == p^31 - // <=> p = sqrt31(1 / modulesCount) - // so we use a modulo of 1 / sqrt31(1 / modulesCount) - /** @type {WeakMap} */ - const moduleBits = new WeakMap(); - const modulesCount = compilation.modules.size; + clear() { + this[LOG_SYMBOL](LogType.clear); + } - // precalculate the modulo values for each bit - const modulo = 1 / Math.pow(1 / modulesCount, 1 / 31); - const modulos = Array.from( - { length: 31 }, - (x, i) => Math.pow(modulo, i) | 0 - ); + status(...args) { + this[LOG_SYMBOL](LogType.status, args); + } - // iterate all modules to generate bit values - let i = 0; - for (const module of compilation.modules) { - let bit = 30; - while (i % modulos[bit] !== 0) { - bit--; - } - moduleBits.set(module, 1 << bit); - i++; - } + group(...args) { + this[LOG_SYMBOL](LogType.group, args); + } - // iterate all chunks to generate bitmaps - /** @type {WeakMap} */ - const chunkModulesHash = new WeakMap(); - for (const chunk of chunks) { - let hash = 0; - for (const module of chunkGraph.getChunkModulesIterable(chunk)) { - hash |= moduleBits.get(module); - } - chunkModulesHash.set(chunk, hash); - } + groupCollapsed(...args) { + this[LOG_SYMBOL](LogType.groupCollapsed, args); + } - for (const chunkA of chunks) { - const chunkAHash = chunkModulesHash.get(chunkA); - const chunkAModulesCount = - chunkGraph.getNumberOfChunkModules(chunkA); - if (chunkAModulesCount === 0) continue; - let bestModule = undefined; - for (const module of chunkGraph.getChunkModulesIterable(chunkA)) { - if ( - bestModule === undefined || - chunkGraph.getNumberOfModuleChunks(bestModule) > - chunkGraph.getNumberOfModuleChunks(module) - ) - bestModule = module; - } - loopB: for (const chunkB of chunkGraph.getModuleChunksIterable( - bestModule - )) { - // as we iterate the same iterables twice - // skip if we find ourselves - if (chunkA === chunkB) continue; + groupEnd(...args) { + this[LOG_SYMBOL](LogType.groupEnd, args); + } - const chunkBModulesCount = - chunkGraph.getNumberOfChunkModules(chunkB); + profile(label) { + this[LOG_SYMBOL](LogType.profile, [label]); + } - // ids for empty chunks are not included - if (chunkBModulesCount === 0) continue; + profileEnd(label) { + this[LOG_SYMBOL](LogType.profileEnd, [label]); + } - // instead of swapping A and B just bail - // as we loop twice the current A will be B and B then A - if (chunkAModulesCount > chunkBModulesCount) continue; + time(label) { + this[TIMERS_SYMBOL] = this[TIMERS_SYMBOL] || new Map(); + this[TIMERS_SYMBOL].set(label, process.hrtime()); + } - // is chunkA in chunkB? + timeLog(label) { + const prev = this[TIMERS_SYMBOL] && this[TIMERS_SYMBOL].get(label); + if (!prev) { + throw new Error(`No such label '${label}' for WebpackLogger.timeLog()`); + } + const time = process.hrtime(prev); + this[LOG_SYMBOL](LogType.time, [label, ...time]); + } - // we do a cheap check for the hash value - const chunkBHash = chunkModulesHash.get(chunkB); - if ((chunkBHash & chunkAHash) !== chunkAHash) continue; + timeEnd(label) { + const prev = this[TIMERS_SYMBOL] && this[TIMERS_SYMBOL].get(label); + if (!prev) { + throw new Error(`No such label '${label}' for WebpackLogger.timeEnd()`); + } + const time = process.hrtime(prev); + this[TIMERS_SYMBOL].delete(label); + this[LOG_SYMBOL](LogType.time, [label, ...time]); + } - // compare all modules - for (const m of chunkGraph.getChunkModulesIterable(chunkA)) { - if (!chunkGraph.isModuleInChunk(m, chunkB)) continue loopB; - } - chunkB.ids.push(chunkA.id); - } - } - } + timeAggregate(label) { + const prev = this[TIMERS_SYMBOL] && this[TIMERS_SYMBOL].get(label); + if (!prev) { + throw new Error( + `No such label '${label}' for WebpackLogger.timeAggregate()` ); - }); + } + const time = process.hrtime(prev); + this[TIMERS_SYMBOL].delete(label); + this[TIMERS_AGGREGATES_SYMBOL] = + this[TIMERS_AGGREGATES_SYMBOL] || new Map(); + const current = this[TIMERS_AGGREGATES_SYMBOL].get(label); + if (current !== undefined) { + if (time[1] + current[1] > 1e9) { + time[0] += current[0] + 1; + time[1] = time[1] - 1e9 + current[1]; + } else { + time[0] += current[0]; + time[1] += current[1]; + } + } + this[TIMERS_AGGREGATES_SYMBOL].set(label, time); + } + + timeAggregateEnd(label) { + if (this[TIMERS_AGGREGATES_SYMBOL] === undefined) return; + const time = this[TIMERS_AGGREGATES_SYMBOL].get(label); + if (time === undefined) return; + this[TIMERS_AGGREGATES_SYMBOL].delete(label); + this[LOG_SYMBOL](LogType.time, [label, ...time]); } } -module.exports = FlagIncludedChunksPlugin; + +exports.Logger = WebpackLogger; /***/ }), -/***/ 92886: -/***/ (function(__unused_webpack_module, exports, __webpack_require__) { +/***/ 34820: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; /* MIT License http://www.opensource.org/licenses/mit-license.php - Author Sergey Melyukov @smelukov -*/ - - - -const { UsageState } = __webpack_require__(4295); - -/** @typedef {import("estree").Node} AnyNode */ -/** @typedef {import("../Dependency")} Dependency */ -/** @typedef {import("../ModuleGraph")} ModuleGraph */ -/** @typedef {import("../ModuleGraphConnection")} ModuleGraphConnection */ -/** @typedef {import("../ModuleGraphConnection").ConnectionState} ConnectionState */ -/** @typedef {import("../Parser").ParserState} ParserState */ -/** @typedef {import("../javascript/JavascriptParser")} JavascriptParser */ -/** @typedef {import("../util/runtime").RuntimeSpec} RuntimeSpec */ - -/** @typedef {Map | true>} InnerGraph */ -/** @typedef {function(boolean | Set | undefined): void} UsageCallback */ - -/** - * @typedef {Object} StateObject - * @property {InnerGraph} innerGraph - * @property {TopLevelSymbol=} currentTopLevelSymbol - * @property {Map>} usageCallbackMap - */ + Author Tobias Koppers @sokra +*/ -/** @typedef {false|StateObject} State */ -/** @type {WeakMap} */ -const parserStateMap = new WeakMap(); -const topLevelSymbolTag = Symbol("top level symbol"); -/** - * @param {ParserState} parserState parser state - * @returns {State} state - */ -function getState(parserState) { - return parserStateMap.get(parserState); -} +const { LogType } = __webpack_require__(54667); -/** - * @param {ParserState} parserState parser state - * @returns {void} - */ -exports.bailout = parserState => { - parserStateMap.set(parserState, false); -}; +/** @typedef {import("../../declarations/WebpackOptions").FilterItemTypes} FilterItemTypes */ +/** @typedef {import("../../declarations/WebpackOptions").FilterTypes} FilterTypes */ +/** @typedef {import("./Logger").LogTypeEnum} LogTypeEnum */ + +/** @typedef {function(string): boolean} FilterFunction */ /** - * @param {ParserState} parserState parser state - * @returns {void} + * @typedef {Object} LoggerConsole + * @property {function(): void} clear + * @property {function(): void} trace + * @property {(...args: any[]) => void} info + * @property {(...args: any[]) => void} log + * @property {(...args: any[]) => void} warn + * @property {(...args: any[]) => void} error + * @property {(...args: any[]) => void=} debug + * @property {(...args: any[]) => void=} group + * @property {(...args: any[]) => void=} groupCollapsed + * @property {(...args: any[]) => void=} groupEnd + * @property {(...args: any[]) => void=} status + * @property {(...args: any[]) => void=} profile + * @property {(...args: any[]) => void=} profileEnd + * @property {(...args: any[]) => void=} logTime */ -exports.enable = parserState => { - const state = parserStateMap.get(parserState); - if (state === false) { - return; - } - parserStateMap.set(parserState, { - innerGraph: new Map(), - currentTopLevelSymbol: undefined, - usageCallbackMap: new Map() - }); -}; /** - * @param {ParserState} parserState parser state - * @returns {boolean} true, when enabled + * @typedef {Object} LoggerOptions + * @property {false|true|"none"|"error"|"warn"|"info"|"log"|"verbose"} level loglevel + * @property {FilterTypes|boolean} debug filter for debug logging + * @property {LoggerConsole} console the console to log to */ -exports.isEnabled = parserState => { - const state = parserStateMap.get(parserState); - return !!state; -}; /** - * @param {ParserState} state parser state - * @param {TopLevelSymbol | null} symbol the symbol, or null for all symbols - * @param {string | TopLevelSymbol | true} usage usage data - * @returns {void} + * @param {FilterItemTypes} item an input item + * @returns {FilterFunction} filter function */ -exports.addUsage = (state, symbol, usage) => { - const innerGraphState = getState(state); - - if (innerGraphState) { - const { innerGraph } = innerGraphState; - const info = innerGraph.get(symbol); - if (usage === true) { - innerGraph.set(symbol, true); - } else if (info === undefined) { - innerGraph.set(symbol, new Set([usage])); - } else if (info !== true) { - info.add(usage); - } +const filterToFunction = item => { + if (typeof item === "string") { + const regExp = new RegExp( + `[\\\\/]${item.replace( + // eslint-disable-next-line no-useless-escape + /[-[\]{}()*+?.\\^$|]/g, + "\\$&" + )}([\\\\/]|$|!|\\?)` + ); + return ident => regExp.test(ident); + } + if (item && typeof item === "object" && typeof item.test === "function") { + return ident => item.test(ident); + } + if (typeof item === "function") { + return item; + } + if (typeof item === "boolean") { + return () => item; } }; /** - * @param {JavascriptParser} parser the parser - * @param {string} name name of variable - * @param {string | TopLevelSymbol | true} usage usage data - * @returns {void} + * @enum {number} */ -exports.addVariableUsage = (parser, name, usage) => { - const symbol = - /** @type {TopLevelSymbol} */ ( - parser.getTagData(name, topLevelSymbolTag) - ) || exports.tagTopLevelSymbol(parser, name); - if (symbol) { - exports.addUsage(parser.state, symbol, usage); - } +const LogLevel = { + none: 6, + false: 6, + error: 5, + warn: 4, + info: 3, + log: 2, + true: 2, + verbose: 1 }; /** - * @param {ParserState} state parser state - * @returns {void} + * @param {LoggerOptions} options options object + * @returns {function(string, LogTypeEnum, any[]): void} logging function */ -exports.inferDependencyUsage = state => { - const innerGraphState = getState(state); - - if (!innerGraphState) { - return; - } +module.exports = ({ level = "info", debug = false, console }) => { + const debugFilters = + typeof debug === "boolean" + ? [() => debug] + : /** @type {FilterItemTypes[]} */ ([]) + .concat(debug) + .map(filterToFunction); + /** @type {number} */ + const loglevel = LogLevel[`${level}`] || 0; - const { innerGraph, usageCallbackMap } = innerGraphState; - const processed = new Map(); - // flatten graph to terminal nodes (string, undefined or true) - const nonTerminal = new Set(innerGraph.keys()); - while (nonTerminal.size > 0) { - for (const key of nonTerminal) { - /** @type {Set | true} */ - let newSet = new Set(); - let isTerminal = true; - const value = innerGraph.get(key); - let alreadyProcessed = processed.get(key); - if (alreadyProcessed === undefined) { - alreadyProcessed = new Set(); - processed.set(key, alreadyProcessed); + /** + * @param {string} name name of the logger + * @param {LogTypeEnum} type type of the log entry + * @param {any[]} args arguments of the log entry + * @returns {void} + */ + const logger = (name, type, args) => { + const labeledArgs = () => { + if (Array.isArray(args)) { + if (args.length > 0 && typeof args[0] === "string") { + return [`[${name}] ${args[0]}`, ...args.slice(1)]; + } else { + return [`[${name}]`, ...args]; + } + } else { + return []; } - if (value !== true && value !== undefined) { - for (const item of value) { - alreadyProcessed.add(item); + }; + const debug = debugFilters.some(f => f(name)); + switch (type) { + case LogType.debug: + if (!debug) return; + // eslint-disable-next-line node/no-unsupported-features/node-builtins + if (typeof console.debug === "function") { + // eslint-disable-next-line node/no-unsupported-features/node-builtins + console.debug(...labeledArgs()); + } else { + console.log(...labeledArgs()); } - for (const item of value) { - if (typeof item === "string") { - newSet.add(item); + break; + case LogType.log: + if (!debug && loglevel > LogLevel.log) return; + console.log(...labeledArgs()); + break; + case LogType.info: + if (!debug && loglevel > LogLevel.info) return; + console.info(...labeledArgs()); + break; + case LogType.warn: + if (!debug && loglevel > LogLevel.warn) return; + console.warn(...labeledArgs()); + break; + case LogType.error: + if (!debug && loglevel > LogLevel.error) return; + console.error(...labeledArgs()); + break; + case LogType.trace: + if (!debug) return; + console.trace(); + break; + case LogType.groupCollapsed: + if (!debug && loglevel > LogLevel.log) return; + if (!debug && loglevel > LogLevel.verbose) { + // eslint-disable-next-line node/no-unsupported-features/node-builtins + if (typeof console.groupCollapsed === "function") { + // eslint-disable-next-line node/no-unsupported-features/node-builtins + console.groupCollapsed(...labeledArgs()); } else { - const itemValue = innerGraph.get(item); - if (itemValue === true) { - newSet = true; - break; - } - if (itemValue !== undefined) { - for (const i of itemValue) { - if (i === key) continue; - if (alreadyProcessed.has(i)) continue; - newSet.add(i); - if (typeof i !== "string") { - isTerminal = false; - } - } - } + console.log(...labeledArgs()); } + break; } - if (newSet === true) { - innerGraph.set(key, true); - } else if (newSet.size === 0) { - innerGraph.set(key, undefined); + // falls through + case LogType.group: + if (!debug && loglevel > LogLevel.log) return; + // eslint-disable-next-line node/no-unsupported-features/node-builtins + if (typeof console.group === "function") { + // eslint-disable-next-line node/no-unsupported-features/node-builtins + console.group(...labeledArgs()); } else { - innerGraph.set(key, newSet); + console.log(...labeledArgs()); + } + break; + case LogType.groupEnd: + if (!debug && loglevel > LogLevel.log) return; + // eslint-disable-next-line node/no-unsupported-features/node-builtins + if (typeof console.groupEnd === "function") { + // eslint-disable-next-line node/no-unsupported-features/node-builtins + console.groupEnd(); } + break; + case LogType.time: { + if (!debug && loglevel > LogLevel.log) return; + const ms = args[1] * 1000 + args[2] / 1000000; + const msg = `[${name}] ${args[0]}: ${ms} ms`; + if (typeof console.logTime === "function") { + console.logTime(msg); + } else { + console.log(msg); + } + break; } - if (isTerminal) { - nonTerminal.delete(key); - - // For the global key, merge with all other keys - if (key === null) { - const globalValue = innerGraph.get(null); - if (globalValue) { - for (const [key, value] of innerGraph) { - if (key !== null && value !== true) { - if (globalValue === true) { - innerGraph.set(key, true); - } else { - const newSet = new Set(value); - for (const item of globalValue) { - newSet.add(item); - } - innerGraph.set(key, newSet); - } - } - } + case LogType.profile: + // eslint-disable-next-line node/no-unsupported-features/node-builtins + if (typeof console.profile === "function") { + // eslint-disable-next-line node/no-unsupported-features/node-builtins + console.profile(...labeledArgs()); + } + break; + case LogType.profileEnd: + // eslint-disable-next-line node/no-unsupported-features/node-builtins + if (typeof console.profileEnd === "function") { + // eslint-disable-next-line node/no-unsupported-features/node-builtins + console.profileEnd(...labeledArgs()); + } + break; + case LogType.clear: + if (!debug && loglevel > LogLevel.log) return; + // eslint-disable-next-line node/no-unsupported-features/node-builtins + if (typeof console.clear === "function") { + // eslint-disable-next-line node/no-unsupported-features/node-builtins + console.clear(); + } + break; + case LogType.status: + if (!debug && loglevel > LogLevel.info) return; + if (typeof console.status === "function") { + if (args.length === 0) { + console.status(); + } else { + console.status(...labeledArgs()); + } + } else { + if (args.length !== 0) { + console.info(...labeledArgs()); } } - } - } - } - - /** @type {Map>} */ - for (const [symbol, callbacks] of usageCallbackMap) { - const usage = /** @type {true | Set | undefined} */ ( - innerGraph.get(symbol) - ); - for (const callback of callbacks) { - callback(usage === undefined ? false : usage); + break; + default: + throw new Error(`Unexpected LogType ${type}`); } - } + }; + return logger; }; -/** - * @param {ParserState} state parser state - * @param {UsageCallback} onUsageCallback on usage callback - */ -exports.onUsage = (state, onUsageCallback) => { - const innerGraphState = getState(state); - - if (innerGraphState) { - const { usageCallbackMap, currentTopLevelSymbol } = innerGraphState; - if (currentTopLevelSymbol) { - let callbacks = usageCallbackMap.get(currentTopLevelSymbol); - if (callbacks === undefined) { - callbacks = new Set(); - usageCallbackMap.set(currentTopLevelSymbol, callbacks); - } +/***/ }), - callbacks.add(onUsageCallback); - } else { - onUsageCallback(true); - } - } else { - onUsageCallback(undefined); - } -}; +/***/ 10072: +/***/ (function(module) { -/** - * @param {ParserState} state parser state - * @param {TopLevelSymbol} symbol the symbol - */ -exports.setTopLevelSymbol = (state, symbol) => { - const innerGraphState = getState(state); +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ - if (innerGraphState) { - innerGraphState.currentTopLevelSymbol = symbol; - } -}; -/** - * @param {ParserState} state parser state - * @returns {TopLevelSymbol|void} usage data - */ -exports.getTopLevelSymbol = state => { - const innerGraphState = getState(state); - if (innerGraphState) { - return innerGraphState.currentTopLevelSymbol; - } +const arraySum = array => { + let sum = 0; + for (const item of array) sum += item; + return sum; }; /** - * @param {JavascriptParser} parser parser - * @param {string} name name of variable - * @returns {TopLevelSymbol} symbol + * @param {any[]} args items to be truncated + * @param {number} maxLength maximum length of args including spaces between + * @returns {string[]} truncated args */ -exports.tagTopLevelSymbol = (parser, name) => { - const innerGraphState = getState(parser.state); - if (!innerGraphState) return; +const truncateArgs = (args, maxLength) => { + const lengths = args.map(a => `${a}`.length); + const availableLength = maxLength - lengths.length + 1; - parser.defineVariable(name); + if (availableLength > 0 && args.length === 1) { + if (availableLength >= args[0].length) { + return args; + } else if (availableLength > 3) { + return ["..." + args[0].slice(-availableLength + 3)]; + } else { + return [args[0].slice(-availableLength)]; + } + } - const existingTag = /** @type {TopLevelSymbol} */ ( - parser.getTagData(name, topLevelSymbolTag) - ); - if (existingTag) { - return existingTag; + // Check if there is space for at least 4 chars per arg + if (availableLength < arraySum(lengths.map(i => Math.min(i, 6)))) { + // remove args + if (args.length > 1) + return truncateArgs(args.slice(0, args.length - 1), maxLength); + return []; } - const fn = new TopLevelSymbol(name); - parser.tagVariable(name, topLevelSymbolTag, fn); - return fn; -}; + let currentLength = arraySum(lengths); -/** - * @param {Dependency} dependency the dependency - * @param {Set | boolean} usedByExports usedByExports info - * @param {ModuleGraph} moduleGraph moduleGraph - * @param {RuntimeSpec} runtime runtime - * @returns {boolean} false, when unused. Otherwise true - */ -exports.isDependencyUsedByExports = ( - dependency, - usedByExports, - moduleGraph, - runtime -) => { - if (usedByExports === false) return false; - if (usedByExports !== true && usedByExports !== undefined) { - const selfModule = moduleGraph.getParentModule(dependency); - const exportsInfo = moduleGraph.getExportsInfo(selfModule); - let used = false; - for (const exportName of usedByExports) { - if (exportsInfo.getUsed(exportName, runtime) !== UsageState.Unused) - used = true; - } - if (!used) return false; - } - return true; -}; + // Check if all fits into maxLength + if (currentLength <= availableLength) return args; -/** - * @param {Dependency} dependency the dependency - * @param {Set | boolean} usedByExports usedByExports info - * @param {ModuleGraph} moduleGraph moduleGraph - * @returns {null | false | function(ModuleGraphConnection, RuntimeSpec): ConnectionState} function to determine if the connection is active - */ -exports.getDependencyUsedByExportsCondition = ( - dependency, - usedByExports, - moduleGraph -) => { - if (usedByExports === false) return false; - if (usedByExports !== true && usedByExports !== undefined) { - const selfModule = moduleGraph.getParentModule(dependency); - const exportsInfo = moduleGraph.getExportsInfo(selfModule); - return (connections, runtime) => { - for (const exportName of usedByExports) { - if (exportsInfo.getUsed(exportName, runtime) !== UsageState.Unused) - return true; + // Try to remove chars from the longest items until it fits + while (currentLength > availableLength) { + const maxLength = Math.max(...lengths); + const shorterItems = lengths.filter(l => l !== maxLength); + const nextToMaxLength = + shorterItems.length > 0 ? Math.max(...shorterItems) : 0; + const maxReduce = maxLength - nextToMaxLength; + let maxItems = lengths.length - shorterItems.length; + let overrun = currentLength - availableLength; + for (let i = 0; i < lengths.length; i++) { + if (lengths[i] === maxLength) { + const reduce = Math.min(Math.floor(overrun / maxItems), maxReduce); + lengths[i] -= reduce; + currentLength -= reduce; + overrun -= reduce; + maxItems--; } - return false; - }; + } } - return null; -}; -class TopLevelSymbol { - /** - * @param {string} name name of the variable - */ - constructor(name) { - this.name = name; - } -} + // Return args reduced to length in lengths + return args.map((a, i) => { + const str = `${a}`; + const length = lengths[i]; + if (str.length === length) { + return str; + } else if (length > 5) { + return "..." + str.slice(-length + 3); + } else if (length > 0) { + return str.slice(-length); + } else { + return ""; + } + }); +}; -exports.TopLevelSymbol = TopLevelSymbol; -exports.topLevelSymbolTag = topLevelSymbolTag; +module.exports = truncateArgs; /***/ }), -/***/ 57997: +/***/ 32610: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; @@ -103768,372 +101364,292 @@ exports.topLevelSymbolTag = topLevelSymbolTag; -const PureExpressionDependency = __webpack_require__(24746); -const InnerGraph = __webpack_require__(92886); +const RuntimeGlobals = __webpack_require__(49404); +const StartupChunkDependenciesPlugin = __webpack_require__(23613); -/** @typedef {import("estree").ClassDeclaration} ClassDeclarationNode */ -/** @typedef {import("estree").ClassExpression} ClassExpressionNode */ -/** @typedef {import("estree").Node} Node */ -/** @typedef {import("estree").VariableDeclarator} VariableDeclaratorNode */ /** @typedef {import("../Compiler")} Compiler */ -/** @typedef {import("../Dependency")} Dependency */ -/** @typedef {import("../dependencies/HarmonyImportSpecifierDependency")} HarmonyImportSpecifierDependency */ -/** @typedef {import("../javascript/JavascriptParser")} JavascriptParser */ -/** @typedef {import("./InnerGraph").InnerGraph} InnerGraph */ -/** @typedef {import("./InnerGraph").TopLevelSymbol} TopLevelSymbol */ -const { topLevelSymbolTag } = InnerGraph; +class CommonJsChunkLoadingPlugin { + constructor(options) { + options = options || {}; + this._asyncChunkLoading = options.asyncChunkLoading; + } -class InnerGraphPlugin { /** * Apply the plugin * @param {Compiler} compiler the compiler instance * @returns {void} */ apply(compiler) { - compiler.hooks.compilation.tap( - "InnerGraphPlugin", - (compilation, { normalModuleFactory }) => { - const logger = compilation.getLogger("webpack.InnerGraphPlugin"); - - compilation.dependencyTemplates.set( - PureExpressionDependency, - new PureExpressionDependency.Template() - ); + const ChunkLoadingRuntimeModule = this._asyncChunkLoading + ? __webpack_require__(71842) + : __webpack_require__(37181); + const chunkLoadingValue = this._asyncChunkLoading + ? "async-node" + : "require"; + new StartupChunkDependenciesPlugin({ + chunkLoading: chunkLoadingValue, + asyncChunkLoading: this._asyncChunkLoading + }).apply(compiler); + compiler.hooks.thisCompilation.tap( + "CommonJsChunkLoadingPlugin", + compilation => { + const globalChunkLoading = compilation.outputOptions.chunkLoading; + const isEnabledForChunk = chunk => { + const options = chunk.getEntryOptions(); + const chunkLoading = + options && options.chunkLoading !== undefined + ? options.chunkLoading + : globalChunkLoading; + return chunkLoading === chunkLoadingValue; + }; + const onceForChunkSet = new WeakSet(); + const handler = (chunk, set) => { + if (onceForChunkSet.has(chunk)) return; + onceForChunkSet.add(chunk); + if (!isEnabledForChunk(chunk)) return; + set.add(RuntimeGlobals.moduleFactoriesAddOnly); + set.add(RuntimeGlobals.hasOwnProperty); + compilation.addRuntimeModule( + chunk, + new ChunkLoadingRuntimeModule(set) + ); + }; - /** - * @param {JavascriptParser} parser the parser - * @param {Object} parserOptions options - * @returns {void} - */ - const handler = (parser, parserOptions) => { - const onUsageSuper = sup => { - InnerGraph.onUsage(parser.state, usedByExports => { - switch (usedByExports) { - case undefined: - case true: - return; - default: { - const dep = new PureExpressionDependency(sup.range); - dep.loc = sup.loc; - dep.usedByExports = usedByExports; - parser.state.module.addDependency(dep); - break; - } - } - }); - }; + compilation.hooks.runtimeRequirementInTree + .for(RuntimeGlobals.ensureChunkHandlers) + .tap("CommonJsChunkLoadingPlugin", handler); + compilation.hooks.runtimeRequirementInTree + .for(RuntimeGlobals.hmrDownloadUpdateHandlers) + .tap("CommonJsChunkLoadingPlugin", handler); + compilation.hooks.runtimeRequirementInTree + .for(RuntimeGlobals.hmrDownloadManifest) + .tap("CommonJsChunkLoadingPlugin", handler); + compilation.hooks.runtimeRequirementInTree + .for(RuntimeGlobals.baseURI) + .tap("CommonJsChunkLoadingPlugin", handler); + compilation.hooks.runtimeRequirementInTree + .for(RuntimeGlobals.externalInstallChunk) + .tap("CommonJsChunkLoadingPlugin", handler); + compilation.hooks.runtimeRequirementInTree + .for(RuntimeGlobals.onChunksLoaded) + .tap("CommonJsChunkLoadingPlugin", handler); - parser.hooks.program.tap("InnerGraphPlugin", () => { - InnerGraph.enable(parser.state); + compilation.hooks.runtimeRequirementInTree + .for(RuntimeGlobals.ensureChunkHandlers) + .tap("CommonJsChunkLoadingPlugin", (chunk, set) => { + if (!isEnabledForChunk(chunk)) return; + set.add(RuntimeGlobals.getChunkScriptFilename); + }); + compilation.hooks.runtimeRequirementInTree + .for(RuntimeGlobals.hmrDownloadUpdateHandlers) + .tap("CommonJsChunkLoadingPlugin", (chunk, set) => { + if (!isEnabledForChunk(chunk)) return; + set.add(RuntimeGlobals.getChunkUpdateScriptFilename); + set.add(RuntimeGlobals.moduleCache); + set.add(RuntimeGlobals.hmrModuleData); + set.add(RuntimeGlobals.moduleFactoriesAddOnly); + }); + compilation.hooks.runtimeRequirementInTree + .for(RuntimeGlobals.hmrDownloadManifest) + .tap("CommonJsChunkLoadingPlugin", (chunk, set) => { + if (!isEnabledForChunk(chunk)) return; + set.add(RuntimeGlobals.getUpdateManifestFilename); }); + } + ); + } +} - parser.hooks.finish.tap("InnerGraphPlugin", () => { - if (!InnerGraph.isEnabled(parser.state)) return; +module.exports = CommonJsChunkLoadingPlugin; - logger.time("infer dependency usage"); - InnerGraph.inferDependencyUsage(parser.state); - logger.timeAggregate("infer dependency usage"); - }); - // During prewalking the following datastructures are filled with - // nodes that have a TopLevelSymbol assigned and - // variables are tagged with the assigned TopLevelSymbol +/***/ }), - // We differ 3 types of nodes: - // 1. full statements (export default, function declaration) - // 2. classes (class declaration, class expression) - // 3. variable declarators (const x = ...) +/***/ 38857: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - /** @type {WeakMap} */ - const statementWithTopLevelSymbol = new WeakMap(); - /** @type {WeakMap} */ - const statementPurePart = new WeakMap(); +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ - /** @type {WeakMap} */ - const classWithTopLevelSymbol = new WeakMap(); - /** @type {WeakMap} */ - const declWithTopLevelSymbol = new WeakMap(); - /** @type {WeakSet} */ - const pureDeclarators = new WeakSet(); - // The following hooks are used during prewalking: +const CachedInputFileSystem = __webpack_require__(26785); +const fs = __webpack_require__(82161); +const createConsoleLogger = __webpack_require__(34820); +const NodeWatchFileSystem = __webpack_require__(31495); +const nodeConsole = __webpack_require__(10152); - parser.hooks.preStatement.tap("InnerGraphPlugin", statement => { - if (!InnerGraph.isEnabled(parser.state)) return; +/** @typedef {import("../../declarations/WebpackOptions").InfrastructureLogging} InfrastructureLogging */ +/** @typedef {import("../Compiler")} Compiler */ - if (parser.scope.topLevelScope === true) { - if (statement.type === "FunctionDeclaration") { - const name = statement.id ? statement.id.name : "*default*"; - const fn = InnerGraph.tagTopLevelSymbol(parser, name); - statementWithTopLevelSymbol.set(statement, fn); - return true; - } - } - }); +class NodeEnvironmentPlugin { + /** + * @param {Object} options options + * @param {InfrastructureLogging} options.infrastructureLogging infrastructure logging options + */ + constructor(options) { + this.options = options; + } - parser.hooks.blockPreStatement.tap("InnerGraphPlugin", statement => { - if (!InnerGraph.isEnabled(parser.state)) return; + /** + * Apply the plugin + * @param {Compiler} compiler the compiler instance + * @returns {void} + */ + apply(compiler) { + const { infrastructureLogging } = this.options; + compiler.infrastructureLogger = createConsoleLogger({ + level: infrastructureLogging.level || "info", + debug: infrastructureLogging.debug || false, + console: + infrastructureLogging.console || + nodeConsole({ + colors: infrastructureLogging.colors, + appendOnly: infrastructureLogging.appendOnly, + stream: infrastructureLogging.stream + }) + }); + compiler.inputFileSystem = new CachedInputFileSystem(fs, 60000); + const inputFileSystem = compiler.inputFileSystem; + compiler.outputFileSystem = fs; + compiler.intermediateFileSystem = fs; + compiler.watchFileSystem = new NodeWatchFileSystem( + compiler.inputFileSystem + ); + compiler.hooks.beforeRun.tap("NodeEnvironmentPlugin", compiler => { + if (compiler.inputFileSystem === inputFileSystem) { + compiler.fsStartTime = Date.now(); + inputFileSystem.purge(); + } + }); + } +} - if (parser.scope.topLevelScope === true) { - if (statement.type === "ClassDeclaration") { - const name = statement.id ? statement.id.name : "*default*"; - const fn = InnerGraph.tagTopLevelSymbol(parser, name); - classWithTopLevelSymbol.set(statement, fn); - return true; - } - if (statement.type === "ExportDefaultDeclaration") { - const name = "*default*"; - const fn = InnerGraph.tagTopLevelSymbol(parser, name); - const decl = statement.declaration; - if ( - decl.type === "ClassExpression" || - decl.type === "ClassDeclaration" - ) { - classWithTopLevelSymbol.set(decl, fn); - } else if (parser.isPure(decl, statement.range[0])) { - statementWithTopLevelSymbol.set(statement, fn); - if ( - !decl.type.endsWith("FunctionExpression") && - !decl.type.endsWith("Declaration") && - decl.type !== "Literal" - ) { - statementPurePart.set(statement, decl); - } - } - } - } - }); +module.exports = NodeEnvironmentPlugin; - parser.hooks.preDeclarator.tap( - "InnerGraphPlugin", - (decl, statement) => { - if (!InnerGraph.isEnabled(parser.state)) return; - if ( - parser.scope.topLevelScope === true && - decl.init && - decl.id.type === "Identifier" - ) { - const name = decl.id.name; - if (decl.init.type === "ClassExpression") { - const fn = InnerGraph.tagTopLevelSymbol(parser, name); - classWithTopLevelSymbol.set(decl.init, fn); - } else if (parser.isPure(decl.init, decl.id.range[1])) { - const fn = InnerGraph.tagTopLevelSymbol(parser, name); - declWithTopLevelSymbol.set(decl, fn); - if ( - !decl.init.type.endsWith("FunctionExpression") && - decl.init.type !== "Literal" - ) { - pureDeclarators.add(decl); - } - return true; - } - } - } - ); - // During real walking we set the TopLevelSymbol state to the assigned - // TopLevelSymbol by using the fill datastructures. +/***/ }), - // In addition to tracking TopLevelSymbols, we sometimes need to - // add a PureExpressionDependency. This is needed to skip execution - // of pure expressions, even when they are not dropped due to - // minimizing. Otherwise symbols used there might not exist anymore - // as they are removed as unused by this optimization +/***/ 13313: +/***/ (function(module) { - // When we find a reference to a TopLevelSymbol, we register a - // TopLevelSymbol dependency from TopLevelSymbol in state to the - // referenced TopLevelSymbol. This way we get a graph of all - // TopLevelSymbols. +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ - // The following hooks are called during walking: - parser.hooks.statement.tap("InnerGraphPlugin", statement => { - if (!InnerGraph.isEnabled(parser.state)) return; - if (parser.scope.topLevelScope === true) { - InnerGraph.setTopLevelSymbol(parser.state, undefined); - const fn = statementWithTopLevelSymbol.get(statement); - if (fn) { - InnerGraph.setTopLevelSymbol(parser.state, fn); - const purePart = statementPurePart.get(statement); - if (purePart) { - InnerGraph.onUsage(parser.state, usedByExports => { - switch (usedByExports) { - case undefined: - case true: - return; - default: { - const dep = new PureExpressionDependency( - purePart.range - ); - dep.loc = statement.loc; - dep.usedByExports = usedByExports; - parser.state.module.addDependency(dep); - break; - } - } - }); - } - } - } - }); +/** @typedef {import("../Compiler")} Compiler */ - parser.hooks.classExtendsExpression.tap( - "InnerGraphPlugin", - (expr, statement) => { - if (!InnerGraph.isEnabled(parser.state)) return; - if (parser.scope.topLevelScope === true) { - const fn = classWithTopLevelSymbol.get(statement); - if ( - fn && - parser.isPure( - expr, - statement.id ? statement.id.range[1] : statement.range[0] - ) - ) { - InnerGraph.setTopLevelSymbol(parser.state, fn); - onUsageSuper(expr); - } - } - } - ); +class NodeSourcePlugin { + /** + * Apply the plugin + * @param {Compiler} compiler the compiler instance + * @returns {void} + */ + apply(compiler) {} +} - parser.hooks.classBodyElement.tap( - "InnerGraphPlugin", - (element, classDefinition) => { - if (!InnerGraph.isEnabled(parser.state)) return; - if (parser.scope.topLevelScope === true) { - const fn = classWithTopLevelSymbol.get(classDefinition); - if (fn) { - InnerGraph.setTopLevelSymbol(parser.state, undefined); - } - } - } - ); +module.exports = NodeSourcePlugin; - parser.hooks.classBodyValue.tap( - "InnerGraphPlugin", - (expression, element, classDefinition) => { - if (!InnerGraph.isEnabled(parser.state)) return; - if (parser.scope.topLevelScope === true) { - const fn = classWithTopLevelSymbol.get(classDefinition); - if (fn) { - if ( - !element.static || - parser.isPure( - expression, - element.key ? element.key.range[1] : element.range[0] - ) - ) { - InnerGraph.setTopLevelSymbol(parser.state, fn); - if (element.type !== "MethodDefinition" && element.static) { - InnerGraph.onUsage(parser.state, usedByExports => { - switch (usedByExports) { - case undefined: - case true: - return; - default: { - const dep = new PureExpressionDependency( - expression.range - ); - dep.loc = expression.loc; - dep.usedByExports = usedByExports; - parser.state.module.addDependency(dep); - break; - } - } - }); - } - } else { - InnerGraph.setTopLevelSymbol(parser.state, undefined); - } - } - } - } - ); - parser.hooks.declarator.tap("InnerGraphPlugin", (decl, statement) => { - if (!InnerGraph.isEnabled(parser.state)) return; - const fn = declWithTopLevelSymbol.get(decl); +/***/ }), - if (fn) { - InnerGraph.setTopLevelSymbol(parser.state, fn); - if (pureDeclarators.has(decl)) { - if (decl.init.type === "ClassExpression") { - if (decl.init.superClass) { - onUsageSuper(decl.init.superClass); - } - } else { - InnerGraph.onUsage(parser.state, usedByExports => { - switch (usedByExports) { - case undefined: - case true: - return; - default: { - const dep = new PureExpressionDependency( - decl.init.range - ); - dep.loc = decl.loc; - dep.usedByExports = usedByExports; - parser.state.module.addDependency(dep); - break; - } - } - }); - } - } - parser.walkExpression(decl.init); - InnerGraph.setTopLevelSymbol(parser.state, undefined); - return true; - } - }); +/***/ 28037: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ + + + +const ExternalsPlugin = __webpack_require__(361); + +/** @typedef {import("../Compiler")} Compiler */ + +const builtins = [ + "assert", + "async_hooks", + "buffer", + "child_process", + "cluster", + "console", + "constants", + "crypto", + "dgram", + "diagnostics_channel", + "dns", + "dns/promises", + "domain", + "events", + "fs", + "fs/promises", + "http", + "http2", + "https", + "inspector", + "module", + "net", + "os", + "path", + "path/posix", + "path/win32", + "perf_hooks", + "process", + "punycode", + "querystring", + "readline", + "repl", + "stream", + "stream/promises", + "stream/web", + "string_decoder", + "sys", + "timers", + "timers/promises", + "tls", + "trace_events", + "tty", + "url", + "util", + "v8", + "vm", + "wasi", + "worker_threads", + "zlib", + /^node:/, - parser.hooks.expression - .for(topLevelSymbolTag) - .tap("InnerGraphPlugin", () => { - const topLevelSymbol = /** @type {TopLevelSymbol} */ ( - parser.currentTagData - ); - const currentTopLevelSymbol = InnerGraph.getTopLevelSymbol( - parser.state - ); - InnerGraph.addUsage( - parser.state, - topLevelSymbol, - currentTopLevelSymbol || true - ); - }); - parser.hooks.assign - .for(topLevelSymbolTag) - .tap("InnerGraphPlugin", expr => { - if (!InnerGraph.isEnabled(parser.state)) return; - if (expr.operator === "=") return true; - }); - }; - normalModuleFactory.hooks.parser - .for("javascript/auto") - .tap("InnerGraphPlugin", handler); - normalModuleFactory.hooks.parser - .for("javascript/esm") - .tap("InnerGraphPlugin", handler); + // cspell:word pnpapi + // Yarn PnP adds pnpapi as "builtin" + "pnpapi" +]; - compilation.hooks.finishModules.tap("InnerGraphPlugin", () => { - logger.timeAggregateEnd("infer dependency usage"); - }); - } - ); +class NodeTargetPlugin { + /** + * Apply the plugin + * @param {Compiler} compiler the compiler instance + * @returns {void} + */ + apply(compiler) { + new ExternalsPlugin("node-commonjs", builtins).apply(compiler); } } -module.exports = InnerGraphPlugin; +module.exports = NodeTargetPlugin; /***/ }), -/***/ 22119: +/***/ 47087: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; @@ -104144,260 +101660,37 @@ module.exports = InnerGraphPlugin; -const { STAGE_ADVANCED } = __webpack_require__(68145); -const LazyBucketSortedSet = __webpack_require__(79300); -const { compareChunks } = __webpack_require__(26296); -const createSchemaValidation = __webpack_require__(77695); +const CommonJsChunkFormatPlugin = __webpack_require__(57634); +const EnableChunkLoadingPlugin = __webpack_require__(34726); -/** @typedef {import("../../declarations/plugins/optimize/LimitChunkCountPlugin").LimitChunkCountPluginOptions} LimitChunkCountPluginOptions */ -/** @typedef {import("../Chunk")} Chunk */ /** @typedef {import("../Compiler")} Compiler */ -const validate = createSchemaValidation( - __webpack_require__(70831), - () => __webpack_require__(58898), - { - name: "Limit Chunk Count Plugin", - baseDataPath: "options" - } -); - -/** - * @typedef {Object} ChunkCombination - * @property {boolean} deleted this is set to true when combination was removed - * @property {number} sizeDiff - * @property {number} integratedSize - * @property {Chunk} a - * @property {Chunk} b - * @property {number} aIdx - * @property {number} bIdx - * @property {number} aSize - * @property {number} bSize - */ - -const addToSetMap = (map, key, value) => { - const set = map.get(key); - if (set === undefined) { - map.set(key, new Set([value])); - } else { - set.add(value); - } -}; - -class LimitChunkCountPlugin { - /** - * @param {LimitChunkCountPluginOptions=} options options object - */ +class NodeTemplatePlugin { constructor(options) { - validate(options); - this.options = options; + this._options = options || {}; } /** - * @param {Compiler} compiler the webpack compiler + * Apply the plugin + * @param {Compiler} compiler the compiler instance * @returns {void} */ apply(compiler) { - const options = this.options; - compiler.hooks.compilation.tap("LimitChunkCountPlugin", compilation => { - compilation.hooks.optimizeChunks.tap( - { - name: "LimitChunkCountPlugin", - stage: STAGE_ADVANCED - }, - chunks => { - const chunkGraph = compilation.chunkGraph; - const maxChunks = options.maxChunks; - if (!maxChunks) return; - if (maxChunks < 1) return; - if (compilation.chunks.size <= maxChunks) return; - - let remainingChunksToMerge = compilation.chunks.size - maxChunks; - - // order chunks in a deterministic way - const compareChunksWithGraph = compareChunks(chunkGraph); - const orderedChunks = Array.from(chunks).sort(compareChunksWithGraph); - - // create a lazy sorted data structure to keep all combinations - // this is large. Size = chunks * (chunks - 1) / 2 - // It uses a multi layer bucket sort plus normal sort in the last layer - // It's also lazy so only accessed buckets are sorted - const combinations = new LazyBucketSortedSet( - // Layer 1: ordered by largest size benefit - c => c.sizeDiff, - (a, b) => b - a, - // Layer 2: ordered by smallest combined size - c => c.integratedSize, - (a, b) => a - b, - // Layer 3: ordered by position difference in orderedChunk (-> to be deterministic) - c => c.bIdx - c.aIdx, - (a, b) => a - b, - // Layer 4: ordered by position in orderedChunk (-> to be deterministic) - (a, b) => a.bIdx - b.bIdx - ); - - // we keep a mapping from chunk to all combinations - // but this mapping is not kept up-to-date with deletions - // so `deleted` flag need to be considered when iterating this - /** @type {Map>} */ - const combinationsByChunk = new Map(); - - orderedChunks.forEach((b, bIdx) => { - // create combination pairs with size and integrated size - for (let aIdx = 0; aIdx < bIdx; aIdx++) { - const a = orderedChunks[aIdx]; - // filter pairs that can not be integrated! - if (!chunkGraph.canChunksBeIntegrated(a, b)) continue; - - const integratedSize = chunkGraph.getIntegratedChunksSize( - a, - b, - options - ); - - const aSize = chunkGraph.getChunkSize(a, options); - const bSize = chunkGraph.getChunkSize(b, options); - const c = { - deleted: false, - sizeDiff: aSize + bSize - integratedSize, - integratedSize, - a, - b, - aIdx, - bIdx, - aSize, - bSize - }; - combinations.add(c); - addToSetMap(combinationsByChunk, a, c); - addToSetMap(combinationsByChunk, b, c); - } - return combinations; - }); - - // list of modified chunks during this run - // combinations affected by this change are skipped to allow - // further optimizations - /** @type {Set} */ - const modifiedChunks = new Set(); - - let changed = false; - // eslint-disable-next-line no-constant-condition - loop: while (true) { - const combination = combinations.popFirst(); - if (combination === undefined) break; - - combination.deleted = true; - const { a, b, integratedSize } = combination; - - // skip over pair when - // one of the already merged chunks is a parent of one of the chunks - if (modifiedChunks.size > 0) { - const queue = new Set(a.groupsIterable); - for (const group of b.groupsIterable) { - queue.add(group); - } - for (const group of queue) { - for (const mChunk of modifiedChunks) { - if (mChunk !== a && mChunk !== b && mChunk.isInGroup(group)) { - // This is a potential pair which needs recalculation - // We can't do that now, but it merge before following pairs - // so we leave space for it, and consider chunks as modified - // just for the worse case - remainingChunksToMerge--; - if (remainingChunksToMerge <= 0) break loop; - modifiedChunks.add(a); - modifiedChunks.add(b); - continue loop; - } - } - for (const parent of group.parentsIterable) { - queue.add(parent); - } - } - } - - // merge the chunks - if (chunkGraph.canChunksBeIntegrated(a, b)) { - chunkGraph.integrateChunks(a, b); - compilation.chunks.delete(b); - - // flag chunk a as modified as further optimization are possible for all children here - modifiedChunks.add(a); - - changed = true; - remainingChunksToMerge--; - if (remainingChunksToMerge <= 0) break; - - // Update all affected combinations - // delete all combination with the removed chunk - // we will use combinations with the kept chunk instead - for (const combination of combinationsByChunk.get(a)) { - if (combination.deleted) continue; - combination.deleted = true; - combinations.delete(combination); - } - - // Update combinations with the kept chunk with new sizes - for (const combination of combinationsByChunk.get(b)) { - if (combination.deleted) continue; - if (combination.a === b) { - if (!chunkGraph.canChunksBeIntegrated(a, combination.b)) { - combination.deleted = true; - combinations.delete(combination); - continue; - } - // Update size - const newIntegratedSize = chunkGraph.getIntegratedChunksSize( - a, - combination.b, - options - ); - const finishUpdate = combinations.startUpdate(combination); - combination.a = a; - combination.integratedSize = newIntegratedSize; - combination.aSize = integratedSize; - combination.sizeDiff = - combination.bSize + integratedSize - newIntegratedSize; - finishUpdate(); - } else if (combination.b === b) { - if (!chunkGraph.canChunksBeIntegrated(combination.a, a)) { - combination.deleted = true; - combinations.delete(combination); - continue; - } - // Update size - const newIntegratedSize = chunkGraph.getIntegratedChunksSize( - combination.a, - a, - options - ); - - const finishUpdate = combinations.startUpdate(combination); - combination.b = a; - combination.integratedSize = newIntegratedSize; - combination.bSize = integratedSize; - combination.sizeDiff = - integratedSize + combination.aSize - newIntegratedSize; - finishUpdate(); - } - } - combinationsByChunk.set(a, combinationsByChunk.get(b)); - combinationsByChunk.delete(b); - } - } - if (changed) return true; - } - ); - }); + const chunkLoading = this._options.asyncChunkLoading + ? "async-node" + : "require"; + compiler.options.output.chunkLoading = chunkLoading; + new CommonJsChunkFormatPlugin().apply(compiler); + new EnableChunkLoadingPlugin(chunkLoading).apply(compiler); } } -module.exports = LimitChunkCountPlugin; + +module.exports = NodeTemplatePlugin; /***/ }), -/***/ 7281: +/***/ 31495: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; @@ -104408,181 +101701,428 @@ module.exports = LimitChunkCountPlugin; -const { UsageState } = __webpack_require__(4295); -const { - numberToIdentifier, - NUMBER_OF_IDENTIFIER_START_CHARS, - NUMBER_OF_IDENTIFIER_CONTINUATION_CHARS -} = __webpack_require__(92066); -const { assignDeterministicIds } = __webpack_require__(72922); -const { compareSelect, compareStringsNumeric } = __webpack_require__(26296); +const Watchpack = __webpack_require__(29149); -/** @typedef {import("../Compiler")} Compiler */ -/** @typedef {import("../ExportsInfo")} ExportsInfo */ -/** @typedef {import("../ExportsInfo").ExportInfo} ExportInfo */ +/** @typedef {import("../../declarations/WebpackOptions").WatchOptions} WatchOptions */ +/** @typedef {import("../FileSystemInfo").FileSystemInfoEntry} FileSystemInfoEntry */ +/** @typedef {import("../util/fs").WatchFileSystem} WatchFileSystem */ +/** @typedef {import("../util/fs").WatchMethod} WatchMethod */ +/** @typedef {import("../util/fs").Watcher} Watcher */ -/** - * @param {ExportsInfo} exportsInfo exports info - * @returns {boolean} mangle is possible - */ -const canMangle = exportsInfo => { - if (exportsInfo.otherExportsInfo.getUsed(undefined) !== UsageState.Unused) - return false; - let hasSomethingToMangle = false; - for (const exportInfo of exportsInfo.exports) { - if (exportInfo.canMangle === true) { - hasSomethingToMangle = true; - } +class NodeWatchFileSystem { + constructor(inputFileSystem) { + this.inputFileSystem = inputFileSystem; + this.watcherOptions = { + aggregateTimeout: 0 + }; + this.watcher = new Watchpack(this.watcherOptions); } - return hasSomethingToMangle; -}; - -// Sort by name -const comparator = compareSelect(e => e.name, compareStringsNumeric); -/** - * @param {boolean} deterministic use deterministic names - * @param {ExportsInfo} exportsInfo exports info - * @param {boolean} isNamespace is namespace object - * @returns {void} - */ -const mangleExportsInfo = (deterministic, exportsInfo, isNamespace) => { - if (!canMangle(exportsInfo)) return; - const usedNames = new Set(); - /** @type {ExportInfo[]} */ - const mangleableExports = []; - // Avoid to renamed exports that are not provided when - // 1. it's not a namespace export: non-provided exports can be found in prototype chain - // 2. there are other provided exports and deterministic mode is chosen: - // non-provided exports would break the determinism - let avoidMangleNonProvided = !isNamespace; - if (!avoidMangleNonProvided && deterministic) { - for (const exportInfo of exportsInfo.ownedExports) { - if (exportInfo.provided !== false) { - avoidMangleNonProvided = true; - break; - } + /** + * @param {Iterable} files watched files + * @param {Iterable} directories watched directories + * @param {Iterable} missing watched exitance entries + * @param {number} startTime timestamp of start time + * @param {WatchOptions} options options object + * @param {function(Error=, Map, Map, Set, Set): void} callback aggregated callback + * @param {function(string, number): void} callbackUndelayed callback when the first change was detected + * @returns {Watcher} a watcher + */ + watch( + files, + directories, + missing, + startTime, + options, + callback, + callbackUndelayed + ) { + if (!files || typeof files[Symbol.iterator] !== "function") { + throw new Error("Invalid arguments: 'files'"); } - } - for (const exportInfo of exportsInfo.ownedExports) { - const name = exportInfo.name; - if (!exportInfo.hasUsedName()) { - if ( - // Can the export be mangled? - exportInfo.canMangle !== true || - // Never rename 1 char exports - (name.length === 1 && /^[a-zA-Z0-9_$]/.test(name)) || - // Don't rename 2 char exports in deterministic mode - (deterministic && - name.length === 2 && - /^[a-zA-Z_$][a-zA-Z0-9_$]|^[1-9][0-9]/.test(name)) || - // Don't rename exports that are not provided - (avoidMangleNonProvided && exportInfo.provided !== true) - ) { - exportInfo.setUsedName(name); - usedNames.add(name); - } else { - mangleableExports.push(exportInfo); - } + if (!directories || typeof directories[Symbol.iterator] !== "function") { + throw new Error("Invalid arguments: 'directories'"); } - if (exportInfo.exportsInfoOwned) { - const used = exportInfo.getUsed(undefined); - if ( - used === UsageState.OnlyPropertiesUsed || - used === UsageState.Unused - ) { - mangleExportsInfo(deterministic, exportInfo.exportsInfo, false); + if (!missing || typeof missing[Symbol.iterator] !== "function") { + throw new Error("Invalid arguments: 'missing'"); + } + if (typeof callback !== "function") { + throw new Error("Invalid arguments: 'callback'"); + } + if (typeof startTime !== "number" && startTime) { + throw new Error("Invalid arguments: 'startTime'"); + } + if (typeof options !== "object") { + throw new Error("Invalid arguments: 'options'"); + } + if (typeof callbackUndelayed !== "function" && callbackUndelayed) { + throw new Error("Invalid arguments: 'callbackUndelayed'"); + } + const oldWatcher = this.watcher; + this.watcher = new Watchpack(options); + + if (callbackUndelayed) { + this.watcher.once("change", callbackUndelayed); + } + this.watcher.once("aggregated", (changes, removals) => { + if (this.inputFileSystem && this.inputFileSystem.purge) { + const fs = this.inputFileSystem; + for (const item of changes) { + fs.purge(item); + } + for (const item of removals) { + fs.purge(item); + } } + const times = this.watcher.getTimeInfoEntries(); + callback(null, times, times, changes, removals); + }); + + this.watcher.watch({ files, directories, missing, startTime }); + + if (oldWatcher) { + oldWatcher.close(); } - } - if (deterministic) { - assignDeterministicIds( - mangleableExports, - e => e.name, - comparator, - (e, id) => { - const name = numberToIdentifier(id); - const size = usedNames.size; - usedNames.add(name); - if (size === usedNames.size) return false; - e.setUsedName(name); - return true; + return { + close: () => { + if (this.watcher) { + this.watcher.close(); + this.watcher = null; + } + }, + pause: () => { + if (this.watcher) { + this.watcher.pause(); + } + }, + getAggregatedRemovals: () => { + const items = this.watcher && this.watcher.aggregatedRemovals; + if (items && this.inputFileSystem && this.inputFileSystem.purge) { + const fs = this.inputFileSystem; + for (const item of items) { + fs.purge(item); + } + } + return items; + }, + getAggregatedChanges: () => { + const items = this.watcher && this.watcher.aggregatedChanges; + if (items && this.inputFileSystem && this.inputFileSystem.purge) { + const fs = this.inputFileSystem; + for (const item of items) { + fs.purge(item); + } + } + return items; + }, + getFileTimeInfoEntries: () => { + if (this.watcher) { + return this.watcher.getTimeInfoEntries(); + } else { + return new Map(); + } }, - [ - NUMBER_OF_IDENTIFIER_START_CHARS, - NUMBER_OF_IDENTIFIER_START_CHARS * - NUMBER_OF_IDENTIFIER_CONTINUATION_CHARS - ], - NUMBER_OF_IDENTIFIER_CONTINUATION_CHARS, - usedNames.size - ); - } else { - const usedExports = []; - const unusedExports = []; - for (const exportInfo of mangleableExports) { - if (exportInfo.getUsed(undefined) === UsageState.Unused) { - unusedExports.push(exportInfo); - } else { - usedExports.push(exportInfo); - } - } - usedExports.sort(comparator); - unusedExports.sort(comparator); - let i = 0; - for (const list of [usedExports, unusedExports]) { - for (const exportInfo of list) { - let name; - do { - name = numberToIdentifier(i++); - } while (usedNames.has(name)); - exportInfo.setUsedName(name); + getContextTimeInfoEntries: () => { + if (this.watcher) { + return this.watcher.getTimeInfoEntries(); + } else { + return new Map(); + } } - } + }; } -}; +} -class MangleExportsPlugin { - /** - * @param {boolean} deterministic use deterministic names - */ - constructor(deterministic) { - this._deterministic = deterministic; +module.exports = NodeWatchFileSystem; + + +/***/ }), + +/***/ 71842: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php +*/ + + + +const RuntimeGlobals = __webpack_require__(49404); +const RuntimeModule = __webpack_require__(61439); +const Template = __webpack_require__(92066); +const { + chunkHasJs, + getChunkFilenameTemplate +} = __webpack_require__(76767); +const { getInitialChunkIds } = __webpack_require__(30951); +const compileBooleanMatcher = __webpack_require__(356); +const { getUndoPath } = __webpack_require__(96236); + +class ReadFileChunkLoadingRuntimeModule extends RuntimeModule { + constructor(runtimeRequirements) { + super("readFile chunk loading", RuntimeModule.STAGE_ATTACH); + this.runtimeRequirements = runtimeRequirements; } + /** - * Apply the plugin - * @param {Compiler} compiler the compiler instance - * @returns {void} + * @returns {string} runtime code */ - apply(compiler) { - const { _deterministic: deterministic } = this; - compiler.hooks.compilation.tap("MangleExportsPlugin", compilation => { - const moduleGraph = compilation.moduleGraph; - compilation.hooks.optimizeCodeGeneration.tap( - "MangleExportsPlugin", - modules => { - if (compilation.moduleMemCaches) { - throw new Error( - "optimization.mangleExports can't be used with cacheUnaffected as export mangling is a global effect" - ); - } - for (const module of modules) { - const isNamespace = - module.buildMeta && module.buildMeta.exportsType === "namespace"; - const exportsInfo = moduleGraph.getExportsInfo(module); - mangleExportsInfo(deterministic, exportsInfo, isNamespace); - } - } - ); - }); + generate() { + const { chunkGraph, chunk } = this; + const { runtimeTemplate } = this.compilation; + const fn = RuntimeGlobals.ensureChunkHandlers; + const withBaseURI = this.runtimeRequirements.has(RuntimeGlobals.baseURI); + const withExternalInstallChunk = this.runtimeRequirements.has( + RuntimeGlobals.externalInstallChunk + ); + const withOnChunkLoad = this.runtimeRequirements.has( + RuntimeGlobals.onChunksLoaded + ); + const withLoading = this.runtimeRequirements.has( + RuntimeGlobals.ensureChunkHandlers + ); + const withHmr = this.runtimeRequirements.has( + RuntimeGlobals.hmrDownloadUpdateHandlers + ); + const withHmrManifest = this.runtimeRequirements.has( + RuntimeGlobals.hmrDownloadManifest + ); + const conditionMap = chunkGraph.getChunkConditionMap(chunk, chunkHasJs); + const hasJsMatcher = compileBooleanMatcher(conditionMap); + const initialChunkIds = getInitialChunkIds(chunk, chunkGraph); + + const outputName = this.compilation.getPath( + getChunkFilenameTemplate(chunk, this.compilation.outputOptions), + { + chunk, + contentHashType: "javascript" + } + ); + const rootOutputDir = getUndoPath( + outputName, + this.compilation.outputOptions.path, + false + ); + + const stateExpression = withHmr + ? `${RuntimeGlobals.hmrRuntimeStatePrefix}_readFileVm` + : undefined; + + return Template.asString([ + withBaseURI + ? Template.asString([ + `${RuntimeGlobals.baseURI} = require("url").pathToFileURL(${ + rootOutputDir + ? `__dirname + ${JSON.stringify("/" + rootOutputDir)}` + : "__filename" + });` + ]) + : "// no baseURI", + "", + "// object to store loaded chunks", + '// "0" means "already loaded", Promise means loading', + `var installedChunks = ${ + stateExpression ? `${stateExpression} = ${stateExpression} || ` : "" + }{`, + Template.indent( + Array.from(initialChunkIds, id => `${JSON.stringify(id)}: 0`).join( + ",\n" + ) + ), + "};", + "", + withOnChunkLoad + ? `${ + RuntimeGlobals.onChunksLoaded + }.readFileVm = ${runtimeTemplate.returningFunction( + "installedChunks[chunkId] === 0", + "chunkId" + )};` + : "// no on chunks loaded", + "", + withLoading || withExternalInstallChunk + ? `var installChunk = ${runtimeTemplate.basicFunction("chunk", [ + "var moreModules = chunk.modules, chunkIds = chunk.ids, runtime = chunk.runtime;", + "for(var moduleId in moreModules) {", + Template.indent([ + `if(${RuntimeGlobals.hasOwnProperty}(moreModules, moduleId)) {`, + Template.indent([ + `${RuntimeGlobals.moduleFactories}[moduleId] = moreModules[moduleId];` + ]), + "}" + ]), + "}", + `if(runtime) runtime(__webpack_require__);`, + "for(var i = 0; i < chunkIds.length; i++) {", + Template.indent([ + "if(installedChunks[chunkIds[i]]) {", + Template.indent(["installedChunks[chunkIds[i]][0]();"]), + "}", + "installedChunks[chunkIds[i]] = 0;" + ]), + "}", + withOnChunkLoad ? `${RuntimeGlobals.onChunksLoaded}();` : "" + ])};` + : "// no chunk install function needed", + "", + withLoading + ? Template.asString([ + "// ReadFile + VM.run chunk loading for javascript", + `${fn}.readFileVm = function(chunkId, promises) {`, + hasJsMatcher !== false + ? Template.indent([ + "", + "var installedChunkData = installedChunks[chunkId];", + 'if(installedChunkData !== 0) { // 0 means "already installed".', + Template.indent([ + '// array of [resolve, reject, promise] means "currently loading"', + "if(installedChunkData) {", + Template.indent(["promises.push(installedChunkData[2]);"]), + "} else {", + Template.indent([ + hasJsMatcher === true + ? "if(true) { // all chunks have JS" + : `if(${hasJsMatcher("chunkId")}) {`, + Template.indent([ + "// load the chunk and return promise to it", + "var promise = new Promise(function(resolve, reject) {", + Template.indent([ + "installedChunkData = installedChunks[chunkId] = [resolve, reject];", + `var filename = require('path').join(__dirname, ${JSON.stringify( + rootOutputDir + )} + ${ + RuntimeGlobals.getChunkScriptFilename + }(chunkId));`, + "require('fs').readFile(filename, 'utf-8', function(err, content) {", + Template.indent([ + "if(err) return reject(err);", + "var chunk = {};", + "require('vm').runInThisContext('(function(exports, require, __dirname, __filename) {' + content + '\\n})', filename)" + + "(chunk, require, require('path').dirname(filename), filename);", + "installChunk(chunk);" + ]), + "});" + ]), + "});", + "promises.push(installedChunkData[2] = promise);" + ]), + "} else installedChunks[chunkId] = 0;" + ]), + "}" + ]), + "}" + ]) + : Template.indent(["installedChunks[chunkId] = 0;"]), + "};" + ]) + : "// no chunk loading", + "", + withExternalInstallChunk + ? Template.asString([ + "module.exports = __webpack_require__;", + `${RuntimeGlobals.externalInstallChunk} = installChunk;` + ]) + : "// no external install chunk", + "", + withHmr + ? Template.asString([ + "function loadUpdateChunk(chunkId, updatedModulesList) {", + Template.indent([ + "return new Promise(function(resolve, reject) {", + Template.indent([ + `var filename = require('path').join(__dirname, ${JSON.stringify( + rootOutputDir + )} + ${RuntimeGlobals.getChunkUpdateScriptFilename}(chunkId));`, + "require('fs').readFile(filename, 'utf-8', function(err, content) {", + Template.indent([ + "if(err) return reject(err);", + "var update = {};", + "require('vm').runInThisContext('(function(exports, require, __dirname, __filename) {' + content + '\\n})', filename)" + + "(update, require, require('path').dirname(filename), filename);", + "var updatedModules = update.modules;", + "var runtime = update.runtime;", + "for(var moduleId in updatedModules) {", + Template.indent([ + `if(${RuntimeGlobals.hasOwnProperty}(updatedModules, moduleId)) {`, + Template.indent([ + `currentUpdate[moduleId] = updatedModules[moduleId];`, + "if(updatedModulesList) updatedModulesList.push(moduleId);" + ]), + "}" + ]), + "}", + "if(runtime) currentUpdateRuntime.push(runtime);", + "resolve();" + ]), + "});" + ]), + "});" + ]), + "}", + "", + Template.getFunctionContent( + require('./JavascriptHotModuleReplacement.runtime.js') + ) + .replace(/\$key\$/g, "readFileVm") + .replace(/\$installedChunks\$/g, "installedChunks") + .replace(/\$loadUpdateChunk\$/g, "loadUpdateChunk") + .replace(/\$moduleCache\$/g, RuntimeGlobals.moduleCache) + .replace(/\$moduleFactories\$/g, RuntimeGlobals.moduleFactories) + .replace( + /\$ensureChunkHandlers\$/g, + RuntimeGlobals.ensureChunkHandlers + ) + .replace(/\$hasOwnProperty\$/g, RuntimeGlobals.hasOwnProperty) + .replace(/\$hmrModuleData\$/g, RuntimeGlobals.hmrModuleData) + .replace( + /\$hmrDownloadUpdateHandlers\$/g, + RuntimeGlobals.hmrDownloadUpdateHandlers + ) + .replace( + /\$hmrInvalidateModuleHandlers\$/g, + RuntimeGlobals.hmrInvalidateModuleHandlers + ) + ]) + : "// no HMR", + "", + withHmrManifest + ? Template.asString([ + `${RuntimeGlobals.hmrDownloadManifest} = function() {`, + Template.indent([ + "return new Promise(function(resolve, reject) {", + Template.indent([ + `var filename = require('path').join(__dirname, ${JSON.stringify( + rootOutputDir + )} + ${RuntimeGlobals.getUpdateManifestFilename}());`, + "require('fs').readFile(filename, 'utf-8', function(err, content) {", + Template.indent([ + "if(err) {", + Template.indent([ + 'if(err.code === "ENOENT") return resolve();', + "return reject(err);" + ]), + "}", + "try { resolve(JSON.parse(content)); }", + "catch(e) { reject(e); }" + ]), + "});" + ]), + "});" + ]), + "}" + ]) + : "// no HMR manifest" + ]); } } -module.exports = MangleExportsPlugin; +module.exports = ReadFileChunkLoadingRuntimeModule; /***/ }), -/***/ 54450: +/***/ 82138: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; @@ -104593,119 +102133,111 @@ module.exports = MangleExportsPlugin; -const { STAGE_BASIC } = __webpack_require__(68145); -const { runtimeEqual } = __webpack_require__(19655); +const RuntimeGlobals = __webpack_require__(49404); +const Template = __webpack_require__(92066); +const AsyncWasmLoadingRuntimeModule = __webpack_require__(84465); /** @typedef {import("../Compiler")} Compiler */ -class MergeDuplicateChunksPlugin { +class ReadFileCompileAsyncWasmPlugin { + constructor({ type = "async-node", import: useImport = false } = {}) { + this._type = type; + this._import = useImport; + } /** - * @param {Compiler} compiler the compiler + * Apply the plugin + * @param {Compiler} compiler the compiler instance * @returns {void} */ apply(compiler) { - compiler.hooks.compilation.tap( - "MergeDuplicateChunksPlugin", + compiler.hooks.thisCompilation.tap( + "ReadFileCompileAsyncWasmPlugin", compilation => { - compilation.hooks.optimizeChunks.tap( - { - name: "MergeDuplicateChunksPlugin", - stage: STAGE_BASIC - }, - chunks => { - const { chunkGraph, moduleGraph } = compilation; - - // remember already tested chunks for performance - const notDuplicates = new Set(); - - // for each chunk - for (const chunk of chunks) { - // track a Set of all chunk that could be duplicates - let possibleDuplicates; - for (const module of chunkGraph.getChunkModulesIterable(chunk)) { - if (possibleDuplicates === undefined) { - // when possibleDuplicates is not yet set, - // create a new Set from chunks of the current module - // including only chunks with the same number of modules - for (const dup of chunkGraph.getModuleChunksIterable( - module - )) { - if ( - dup !== chunk && - chunkGraph.getNumberOfChunkModules(chunk) === - chunkGraph.getNumberOfChunkModules(dup) && - !notDuplicates.has(dup) - ) { - // delay allocating the new Set until here, reduce memory pressure - if (possibleDuplicates === undefined) { - possibleDuplicates = new Set(); - } - possibleDuplicates.add(dup); - } - } - // when no chunk is possible we can break here - if (possibleDuplicates === undefined) break; - } else { - // validate existing possible duplicates - for (const dup of possibleDuplicates) { - // remove possible duplicate when module is not contained - if (!chunkGraph.isModuleInChunk(module, dup)) { - possibleDuplicates.delete(dup); - } - } - // when all chunks has been removed we can break here - if (possibleDuplicates.size === 0) break; - } - } - - // when we found duplicates - if ( - possibleDuplicates !== undefined && - possibleDuplicates.size > 0 - ) { - outer: for (const otherChunk of possibleDuplicates) { - if (otherChunk.hasRuntime() !== chunk.hasRuntime()) continue; - if (chunkGraph.getNumberOfEntryModules(chunk) > 0) continue; - if (chunkGraph.getNumberOfEntryModules(otherChunk) > 0) - continue; - if (!runtimeEqual(chunk.runtime, otherChunk.runtime)) { - for (const module of chunkGraph.getChunkModulesIterable( - chunk - )) { - const exportsInfo = moduleGraph.getExportsInfo(module); - if ( - !exportsInfo.isEquallyUsed( - chunk.runtime, - otherChunk.runtime - ) - ) { - continue outer; - } - } - } - // merge them - if (chunkGraph.canChunksBeIntegrated(chunk, otherChunk)) { - chunkGraph.integrateChunks(chunk, otherChunk); - compilation.chunks.delete(otherChunk); - } - } - } + const globalWasmLoading = compilation.outputOptions.wasmLoading; + const isEnabledForChunk = chunk => { + const options = chunk.getEntryOptions(); + const wasmLoading = + options && options.wasmLoading !== undefined + ? options.wasmLoading + : globalWasmLoading; + return wasmLoading === this._type; + }; + const generateLoadBinaryCode = this._import + ? path => + Template.asString([ + "Promise.all([import('fs'), import('url')]).then(([{ readFile }, { URL }]) => new Promise((resolve, reject) => {", + Template.indent([ + `readFile(new URL(${path}, import.meta.url), (err, buffer) => {`, + Template.indent([ + "if (err) return reject(err);", + "", + "// Fake fetch response", + "resolve({", + Template.indent(["arrayBuffer() { return buffer; }"]), + "});" + ]), + "});" + ]), + "}))" + ]) + : path => + Template.asString([ + "new Promise(function (resolve, reject) {", + Template.indent([ + "try {", + Template.indent([ + "var { readFile } = require('fs');", + "var { join } = require('path');", + "", + `readFile(join(__dirname, ${path}), function(err, buffer){`, + Template.indent([ + "if (err) return reject(err);", + "", + "// Fake fetch response", + "resolve({", + Template.indent(["arrayBuffer() { return buffer; }"]), + "});" + ]), + "});" + ]), + "} catch (err) { reject(err); }" + ]), + "})" + ]); - // don't check already processed chunks twice - notDuplicates.add(chunk); + compilation.hooks.runtimeRequirementInTree + .for(RuntimeGlobals.instantiateWasm) + .tap("ReadFileCompileAsyncWasmPlugin", (chunk, set) => { + if (!isEnabledForChunk(chunk)) return; + const chunkGraph = compilation.chunkGraph; + if ( + !chunkGraph.hasModuleInGraph( + chunk, + m => m.type === "webassembly/async" + ) + ) { + return; } - } - ); + set.add(RuntimeGlobals.publicPath); + compilation.addRuntimeModule( + chunk, + new AsyncWasmLoadingRuntimeModule({ + generateLoadBinaryCode, + supportsStreaming: false + }) + ); + }); } ); } } -module.exports = MergeDuplicateChunksPlugin; + +module.exports = ReadFileCompileAsyncWasmPlugin; /***/ }), -/***/ 85813: +/***/ 98724: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; @@ -104716,29 +102248,17 @@ module.exports = MergeDuplicateChunksPlugin; -const { STAGE_ADVANCED } = __webpack_require__(68145); -const createSchemaValidation = __webpack_require__(77695); +const RuntimeGlobals = __webpack_require__(49404); +const Template = __webpack_require__(92066); +const WasmChunkLoadingRuntimeModule = __webpack_require__(92153); -/** @typedef {import("../../declarations/plugins/optimize/MinChunkSizePlugin").MinChunkSizePluginOptions} MinChunkSizePluginOptions */ -/** @typedef {import("../Chunk")} Chunk */ /** @typedef {import("../Compiler")} Compiler */ -const validate = createSchemaValidation( - __webpack_require__(60902), - () => __webpack_require__(66480), - { - name: "Min Chunk Size Plugin", - baseDataPath: "options" - } -); +// TODO webpack 6 remove -class MinChunkSizePlugin { - /** - * @param {MinChunkSizePluginOptions} options options object - */ +class ReadFileCompileWasmPlugin { constructor(options) { - validate(options); - this.options = options; + this.options = options || {}; } /** @@ -104747,86 +102267,309 @@ class MinChunkSizePlugin { * @returns {void} */ apply(compiler) { - const options = this.options; - const minChunkSize = options.minChunkSize; - compiler.hooks.compilation.tap("MinChunkSizePlugin", compilation => { - compilation.hooks.optimizeChunks.tap( - { - name: "MinChunkSizePlugin", - stage: STAGE_ADVANCED - }, - chunks => { - const chunkGraph = compilation.chunkGraph; - const equalOptions = { - chunkOverhead: 1, - entryChunkMultiplicator: 1 - }; + compiler.hooks.thisCompilation.tap( + "ReadFileCompileWasmPlugin", + compilation => { + const globalWasmLoading = compilation.outputOptions.wasmLoading; + const isEnabledForChunk = chunk => { + const options = chunk.getEntryOptions(); + const wasmLoading = + options && options.wasmLoading !== undefined + ? options.wasmLoading + : globalWasmLoading; + return wasmLoading === "async-node"; + }; + const generateLoadBinaryCode = path => + Template.asString([ + "new Promise(function (resolve, reject) {", + Template.indent([ + "var { readFile } = require('fs');", + "var { join } = require('path');", + "", + "try {", + Template.indent([ + `readFile(join(__dirname, ${path}), function(err, buffer){`, + Template.indent([ + "if (err) return reject(err);", + "", + "// Fake fetch response", + "resolve({", + Template.indent(["arrayBuffer() { return buffer; }"]), + "});" + ]), + "});" + ]), + "} catch (err) { reject(err); }" + ]), + "})" + ]); - const chunkSizesMap = new Map(); - /** @type {[Chunk, Chunk][]} */ - const combinations = []; - /** @type {Chunk[]} */ - const smallChunks = []; - const visitedChunks = []; - for (const a of chunks) { - // check if one of the chunks sizes is smaller than the minChunkSize - // and filter pairs that can NOT be integrated! - if (chunkGraph.getChunkSize(a, equalOptions) < minChunkSize) { - smallChunks.push(a); - for (const b of visitedChunks) { - if (chunkGraph.canChunksBeIntegrated(b, a)) - combinations.push([b, a]); - } - } else { - for (const b of smallChunks) { - if (chunkGraph.canChunksBeIntegrated(b, a)) - combinations.push([b, a]); - } + compilation.hooks.runtimeRequirementInTree + .for(RuntimeGlobals.ensureChunkHandlers) + .tap("ReadFileCompileWasmPlugin", (chunk, set) => { + if (!isEnabledForChunk(chunk)) return; + const chunkGraph = compilation.chunkGraph; + if ( + !chunkGraph.hasModuleInGraph( + chunk, + m => m.type === "webassembly/sync" + ) + ) { + return; } - chunkSizesMap.set(a, chunkGraph.getChunkSize(a, options)); - visitedChunks.push(a); - } + set.add(RuntimeGlobals.moduleCache); + compilation.addRuntimeModule( + chunk, + new WasmChunkLoadingRuntimeModule({ + generateLoadBinaryCode, + supportsStreaming: false, + mangleImports: this.options.mangleImports, + runtimeRequirements: set + }) + ); + }); + } + ); + } +} - const sortedSizeFilteredExtendedPairCombinations = combinations - .map(pair => { - // extend combination pairs with size and integrated size - const a = chunkSizesMap.get(pair[0]); - const b = chunkSizesMap.get(pair[1]); - const ab = chunkGraph.getIntegratedChunksSize( - pair[0], - pair[1], - options - ); - /** @type {[number, number, Chunk, Chunk]} */ - const extendedPair = [a + b - ab, ab, pair[0], pair[1]]; - return extendedPair; - }) - .sort((a, b) => { - // sadly javascript does an in place sort here - // sort by size - const diff = b[0] - a[0]; - if (diff !== 0) return diff; - return a[1] - b[1]; - }); +module.exports = ReadFileCompileWasmPlugin; - if (sortedSizeFilteredExtendedPairCombinations.length === 0) return; - const pair = sortedSizeFilteredExtendedPairCombinations[0]; +/***/ }), - chunkGraph.integrateChunks(pair[2], pair[3]); - compilation.chunks.delete(pair[3]); - return true; - } - ); - }); +/***/ 37181: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php +*/ + + + +const RuntimeGlobals = __webpack_require__(49404); +const RuntimeModule = __webpack_require__(61439); +const Template = __webpack_require__(92066); +const { + chunkHasJs, + getChunkFilenameTemplate +} = __webpack_require__(76767); +const { getInitialChunkIds } = __webpack_require__(30951); +const compileBooleanMatcher = __webpack_require__(356); +const { getUndoPath } = __webpack_require__(96236); + +class RequireChunkLoadingRuntimeModule extends RuntimeModule { + constructor(runtimeRequirements) { + super("require chunk loading", RuntimeModule.STAGE_ATTACH); + this.runtimeRequirements = runtimeRequirements; + } + + /** + * @returns {string} runtime code + */ + generate() { + const { chunkGraph, chunk } = this; + const { runtimeTemplate } = this.compilation; + const fn = RuntimeGlobals.ensureChunkHandlers; + const withBaseURI = this.runtimeRequirements.has(RuntimeGlobals.baseURI); + const withExternalInstallChunk = this.runtimeRequirements.has( + RuntimeGlobals.externalInstallChunk + ); + const withOnChunkLoad = this.runtimeRequirements.has( + RuntimeGlobals.onChunksLoaded + ); + const withLoading = this.runtimeRequirements.has( + RuntimeGlobals.ensureChunkHandlers + ); + const withHmr = this.runtimeRequirements.has( + RuntimeGlobals.hmrDownloadUpdateHandlers + ); + const withHmrManifest = this.runtimeRequirements.has( + RuntimeGlobals.hmrDownloadManifest + ); + const conditionMap = chunkGraph.getChunkConditionMap(chunk, chunkHasJs); + const hasJsMatcher = compileBooleanMatcher(conditionMap); + const initialChunkIds = getInitialChunkIds(chunk, chunkGraph); + + const outputName = this.compilation.getPath( + getChunkFilenameTemplate(chunk, this.compilation.outputOptions), + { + chunk, + contentHashType: "javascript" + } + ); + const rootOutputDir = getUndoPath( + outputName, + this.compilation.outputOptions.path, + true + ); + + const stateExpression = withHmr + ? `${RuntimeGlobals.hmrRuntimeStatePrefix}_require` + : undefined; + + return Template.asString([ + withBaseURI + ? Template.asString([ + `${RuntimeGlobals.baseURI} = require("url").pathToFileURL(${ + rootOutputDir !== "./" + ? `__dirname + ${JSON.stringify("/" + rootOutputDir)}` + : "__filename" + });` + ]) + : "// no baseURI", + "", + "// object to store loaded chunks", + '// "1" means "loaded", otherwise not loaded yet', + `var installedChunks = ${ + stateExpression ? `${stateExpression} = ${stateExpression} || ` : "" + }{`, + Template.indent( + Array.from(initialChunkIds, id => `${JSON.stringify(id)}: 1`).join( + ",\n" + ) + ), + "};", + "", + withOnChunkLoad + ? `${ + RuntimeGlobals.onChunksLoaded + }.require = ${runtimeTemplate.returningFunction( + "installedChunks[chunkId]", + "chunkId" + )};` + : "// no on chunks loaded", + "", + withLoading || withExternalInstallChunk + ? `var installChunk = ${runtimeTemplate.basicFunction("chunk", [ + "var moreModules = chunk.modules, chunkIds = chunk.ids, runtime = chunk.runtime;", + "for(var moduleId in moreModules) {", + Template.indent([ + `if(${RuntimeGlobals.hasOwnProperty}(moreModules, moduleId)) {`, + Template.indent([ + `${RuntimeGlobals.moduleFactories}[moduleId] = moreModules[moduleId];` + ]), + "}" + ]), + "}", + `if(runtime) runtime(__webpack_require__);`, + "for(var i = 0; i < chunkIds.length; i++)", + Template.indent("installedChunks[chunkIds[i]] = 1;"), + withOnChunkLoad ? `${RuntimeGlobals.onChunksLoaded}();` : "" + ])};` + : "// no chunk install function needed", + "", + withLoading + ? Template.asString([ + "// require() chunk loading for javascript", + `${fn}.require = ${runtimeTemplate.basicFunction( + "chunkId, promises", + hasJsMatcher !== false + ? [ + '// "1" is the signal for "already loaded"', + "if(!installedChunks[chunkId]) {", + Template.indent([ + hasJsMatcher === true + ? "if(true) { // all chunks have JS" + : `if(${hasJsMatcher("chunkId")}) {`, + Template.indent([ + `installChunk(require(${JSON.stringify( + rootOutputDir + )} + ${ + RuntimeGlobals.getChunkScriptFilename + }(chunkId)));` + ]), + "} else installedChunks[chunkId] = 1;", + "" + ]), + "}" + ] + : "installedChunks[chunkId] = 1;" + )};` + ]) + : "// no chunk loading", + "", + withExternalInstallChunk + ? Template.asString([ + "module.exports = __webpack_require__;", + `${RuntimeGlobals.externalInstallChunk} = installChunk;` + ]) + : "// no external install chunk", + "", + withHmr + ? Template.asString([ + "function loadUpdateChunk(chunkId, updatedModulesList) {", + Template.indent([ + `var update = require(${JSON.stringify(rootOutputDir)} + ${ + RuntimeGlobals.getChunkUpdateScriptFilename + }(chunkId));`, + "var updatedModules = update.modules;", + "var runtime = update.runtime;", + "for(var moduleId in updatedModules) {", + Template.indent([ + `if(${RuntimeGlobals.hasOwnProperty}(updatedModules, moduleId)) {`, + Template.indent([ + `currentUpdate[moduleId] = updatedModules[moduleId];`, + "if(updatedModulesList) updatedModulesList.push(moduleId);" + ]), + "}" + ]), + "}", + "if(runtime) currentUpdateRuntime.push(runtime);" + ]), + "}", + "", + Template.getFunctionContent( + require('./JavascriptHotModuleReplacement.runtime.js') + ) + .replace(/\$key\$/g, "require") + .replace(/\$installedChunks\$/g, "installedChunks") + .replace(/\$loadUpdateChunk\$/g, "loadUpdateChunk") + .replace(/\$moduleCache\$/g, RuntimeGlobals.moduleCache) + .replace(/\$moduleFactories\$/g, RuntimeGlobals.moduleFactories) + .replace( + /\$ensureChunkHandlers\$/g, + RuntimeGlobals.ensureChunkHandlers + ) + .replace(/\$hasOwnProperty\$/g, RuntimeGlobals.hasOwnProperty) + .replace(/\$hmrModuleData\$/g, RuntimeGlobals.hmrModuleData) + .replace( + /\$hmrDownloadUpdateHandlers\$/g, + RuntimeGlobals.hmrDownloadUpdateHandlers + ) + .replace( + /\$hmrInvalidateModuleHandlers\$/g, + RuntimeGlobals.hmrInvalidateModuleHandlers + ) + ]) + : "// no HMR", + "", + withHmrManifest + ? Template.asString([ + `${RuntimeGlobals.hmrDownloadManifest} = function() {`, + Template.indent([ + "return Promise.resolve().then(function() {", + Template.indent([ + `return require(${JSON.stringify(rootOutputDir)} + ${ + RuntimeGlobals.getUpdateManifestFilename + }());` + ]), + "})['catch'](function(err) { if(err.code !== 'MODULE_NOT_FOUND') throw err; });" + ]), + "}" + ]) + : "// no HMR manifest" + ]); } } -module.exports = MinChunkSizePlugin; + +module.exports = RequireChunkLoadingRuntimeModule; /***/ }), -/***/ 46681: +/***/ 10152: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; @@ -104837,34 +102580,147 @@ module.exports = MinChunkSizePlugin; -const SizeFormatHelpers = __webpack_require__(15979); -const WebpackError = __webpack_require__(68422); +const util = __webpack_require__(31669); +const truncateArgs = __webpack_require__(10072); -class MinMaxSizeWarning extends WebpackError { - constructor(keys, minSize, maxSize) { - let keysMessage = "Fallback cache group"; - if (keys) { - keysMessage = - keys.length > 1 - ? `Cache groups ${keys.sort().join(", ")}` - : `Cache group ${keys[0]}`; +module.exports = ({ colors, appendOnly, stream }) => { + let currentStatusMessage = undefined; + let hasStatusMessage = false; + let currentIndent = ""; + let currentCollapsed = 0; + + const indent = (str, prefix, colorPrefix, colorSuffix) => { + if (str === "") return str; + prefix = currentIndent + prefix; + if (colors) { + return ( + prefix + + colorPrefix + + str.replace(/\n/g, colorSuffix + "\n" + prefix + colorPrefix) + + colorSuffix + ); + } else { + return prefix + str.replace(/\n/g, "\n" + prefix); } - super( - `SplitChunksPlugin\n` + - `${keysMessage}\n` + - `Configured minSize (${SizeFormatHelpers.formatSize(minSize)}) is ` + - `bigger than maxSize (${SizeFormatHelpers.formatSize(maxSize)}).\n` + - "This seem to be a invalid optimization.splitChunks configuration." - ); - } -} + }; -module.exports = MinMaxSizeWarning; + const clearStatusMessage = () => { + if (hasStatusMessage) { + stream.write("\x1b[2K\r"); + hasStatusMessage = false; + } + }; + + const writeStatusMessage = () => { + if (!currentStatusMessage) return; + const l = stream.columns; + const args = l + ? truncateArgs(currentStatusMessage, l - 1) + : currentStatusMessage; + const str = args.join(" "); + const coloredStr = `\u001b[1m${str}\u001b[39m\u001b[22m`; + stream.write(`\x1b[2K\r${coloredStr}`); + hasStatusMessage = true; + }; + + const writeColored = (prefix, colorPrefix, colorSuffix) => { + return (...args) => { + if (currentCollapsed > 0) return; + clearStatusMessage(); + const str = indent( + util.format(...args), + prefix, + colorPrefix, + colorSuffix + ); + stream.write(str + "\n"); + writeStatusMessage(); + }; + }; + + const writeGroupMessage = writeColored( + "<-> ", + "\u001b[1m\u001b[36m", + "\u001b[39m\u001b[22m" + ); + + const writeGroupCollapsedMessage = writeColored( + "<+> ", + "\u001b[1m\u001b[36m", + "\u001b[39m\u001b[22m" + ); + + return { + log: writeColored(" ", "\u001b[1m", "\u001b[22m"), + debug: writeColored(" ", "", ""), + trace: writeColored(" ", "", ""), + info: writeColored(" ", "\u001b[1m\u001b[32m", "\u001b[39m\u001b[22m"), + warn: writeColored(" ", "\u001b[1m\u001b[33m", "\u001b[39m\u001b[22m"), + error: writeColored(" ", "\u001b[1m\u001b[31m", "\u001b[39m\u001b[22m"), + logTime: writeColored( + " ", + "\u001b[1m\u001b[35m", + "\u001b[39m\u001b[22m" + ), + group: (...args) => { + writeGroupMessage(...args); + if (currentCollapsed > 0) { + currentCollapsed++; + } else { + currentIndent += " "; + } + }, + groupCollapsed: (...args) => { + writeGroupCollapsedMessage(...args); + currentCollapsed++; + }, + groupEnd: () => { + if (currentCollapsed > 0) currentCollapsed--; + else if (currentIndent.length >= 2) + currentIndent = currentIndent.slice(0, currentIndent.length - 2); + }, + // eslint-disable-next-line node/no-unsupported-features/node-builtins + profile: console.profile && (name => console.profile(name)), + // eslint-disable-next-line node/no-unsupported-features/node-builtins + profileEnd: console.profileEnd && (name => console.profileEnd(name)), + clear: + !appendOnly && + // eslint-disable-next-line node/no-unsupported-features/node-builtins + console.clear && + (() => { + clearStatusMessage(); + // eslint-disable-next-line node/no-unsupported-features/node-builtins + console.clear(); + writeStatusMessage(); + }), + status: appendOnly + ? writeColored(" ", "", "") + : (name, ...args) => { + args = args.filter(Boolean); + if (name === undefined && args.length === 0) { + clearStatusMessage(); + currentStatusMessage = undefined; + } else if ( + typeof name === "string" && + name.startsWith("[webpack.Progress] ") + ) { + currentStatusMessage = [name.slice(19), ...args]; + writeStatusMessage(); + } else if (name === "[webpack.Progress]") { + currentStatusMessage = [...args]; + writeStatusMessage(); + } else { + currentStatusMessage = [name, ...args]; + writeStatusMessage(); + } + } + }; +}; /***/ }), -/***/ 29585: +/***/ 8239: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; @@ -104875,49 +102731,22 @@ module.exports = MinMaxSizeWarning; -const asyncLib = __webpack_require__(36386); -const ChunkGraph = __webpack_require__(97860); -const ModuleGraph = __webpack_require__(20258); -const { STAGE_DEFAULT } = __webpack_require__(68145); -const HarmonyImportDependency = __webpack_require__(19577); -const { compareModulesByIdentifier } = __webpack_require__(26296); -const { - intersectRuntime, - mergeRuntimeOwned, - filterRuntime, - runtimeToString, - mergeRuntime -} = __webpack_require__(19655); -const ConcatenatedModule = __webpack_require__(1881); +const { STAGE_ADVANCED } = __webpack_require__(68145); -/** @typedef {import("../Compilation")} Compilation */ +/** @typedef {import("../Chunk")} Chunk */ /** @typedef {import("../Compiler")} Compiler */ -/** @typedef {import("../Module")} Module */ -/** @typedef {import("../RequestShortener")} RequestShortener */ -/** @typedef {import("../util/runtime").RuntimeSpec} RuntimeSpec */ - -/** - * @typedef {Object} Statistics - * @property {number} cached - * @property {number} alreadyInConfig - * @property {number} invalidModule - * @property {number} incorrectChunks - * @property {number} incorrectDependency - * @property {number} incorrectModuleDependency - * @property {number} incorrectChunksOfImporter - * @property {number} incorrectRuntimeCondition - * @property {number} importerFailed - * @property {number} added - */ - -const formatBailoutReason = msg => { - return "ModuleConcatenation bailout: " + msg; -}; -class ModuleConcatenationPlugin { +class AggressiveMergingPlugin { constructor(options) { - if (typeof options !== "object") options = {}; - this.options = options; + if ( + (options !== undefined && typeof options !== "object") || + Array.isArray(options) + ) { + throw new Error( + "Argument should be an options object. To use defaults, pass in nothing.\nFor more info on options, see https://webpack.js.org/plugins/" + ); + } + this.options = options || {}; } /** @@ -104926,819 +102755,409 @@ class ModuleConcatenationPlugin { * @returns {void} */ apply(compiler) { - const { _backCompat: backCompat } = compiler; - compiler.hooks.compilation.tap("ModuleConcatenationPlugin", compilation => { - const moduleGraph = compilation.moduleGraph; - const bailoutReasonMap = new Map(); - - const setBailoutReason = (module, reason) => { - setInnerBailoutReason(module, reason); - moduleGraph - .getOptimizationBailout(module) - .push( - typeof reason === "function" - ? rs => formatBailoutReason(reason(rs)) - : formatBailoutReason(reason) - ); - }; - - const setInnerBailoutReason = (module, reason) => { - bailoutReasonMap.set(module, reason); - }; - - const getInnerBailoutReason = (module, requestShortener) => { - const reason = bailoutReasonMap.get(module); - if (typeof reason === "function") return reason(requestShortener); - return reason; - }; - - const formatBailoutWarning = (module, problem) => requestShortener => { - if (typeof problem === "function") { - return formatBailoutReason( - `Cannot concat with ${module.readableIdentifier( - requestShortener - )}: ${problem(requestShortener)}` - ); - } - const reason = getInnerBailoutReason(module, requestShortener); - const reasonWithPrefix = reason ? `: ${reason}` : ""; - if (module === problem) { - return formatBailoutReason( - `Cannot concat with ${module.readableIdentifier( - requestShortener - )}${reasonWithPrefix}` - ); - } else { - return formatBailoutReason( - `Cannot concat with ${module.readableIdentifier( - requestShortener - )} because of ${problem.readableIdentifier( - requestShortener - )}${reasonWithPrefix}` - ); - } - }; - - compilation.hooks.optimizeChunkModules.tapAsync( - { - name: "ModuleConcatenationPlugin", - stage: STAGE_DEFAULT - }, - (allChunks, modules, callback) => { - const logger = compilation.getLogger( - "webpack.ModuleConcatenationPlugin" - ); - const { chunkGraph, moduleGraph } = compilation; - const relevantModules = []; - const possibleInners = new Set(); - const context = { - chunkGraph, - moduleGraph - }; - logger.time("select relevant modules"); - for (const module of modules) { - let canBeRoot = true; - let canBeInner = true; - - const bailoutReason = module.getConcatenationBailoutReason(context); - if (bailoutReason) { - setBailoutReason(module, bailoutReason); - continue; - } - - // Must not be an async module - if (moduleGraph.isAsync(module)) { - setBailoutReason(module, `Module is async`); - continue; - } - - // Must be in strict mode - if (!module.buildInfo.strict) { - setBailoutReason(module, `Module is not in strict mode`); - continue; - } - - // Module must be in any chunk (we don't want to do useless work) - if (chunkGraph.getNumberOfModuleChunks(module) === 0) { - setBailoutReason(module, "Module is not in any chunk"); - continue; - } - - // Exports must be known (and not dynamic) - const exportsInfo = moduleGraph.getExportsInfo(module); - const relevantExports = exportsInfo.getRelevantExports(undefined); - const unknownReexports = relevantExports.filter(exportInfo => { - return ( - exportInfo.isReexport() && !exportInfo.getTarget(moduleGraph) - ); - }); - if (unknownReexports.length > 0) { - setBailoutReason( - module, - `Reexports in this module do not have a static target (${Array.from( - unknownReexports, - exportInfo => - `${ - exportInfo.name || "other exports" - }: ${exportInfo.getUsedInfo()}` - ).join(", ")})` - ); - continue; - } - - // Root modules must have a static list of exports - const unknownProvidedExports = relevantExports.filter( - exportInfo => { - return exportInfo.provided !== true; - } - ); - if (unknownProvidedExports.length > 0) { - setBailoutReason( - module, - `List of module exports is dynamic (${Array.from( - unknownProvidedExports, - exportInfo => - `${ - exportInfo.name || "other exports" - }: ${exportInfo.getProvidedInfo()} and ${exportInfo.getUsedInfo()}` - ).join(", ")})` - ); - canBeRoot = false; - } - - // Module must not be an entry point - if (chunkGraph.isEntryModule(module)) { - setInnerBailoutReason(module, "Module is an entry point"); - canBeInner = false; - } - - if (canBeRoot) relevantModules.push(module); - if (canBeInner) possibleInners.add(module); - } - logger.timeEnd("select relevant modules"); - logger.debug( - `${relevantModules.length} potential root modules, ${possibleInners.size} potential inner modules` - ); - // sort by depth - // modules with lower depth are more likely suited as roots - // this improves performance, because modules already selected as inner are skipped - logger.time("sort relevant modules"); - relevantModules.sort((a, b) => { - return moduleGraph.getDepth(a) - moduleGraph.getDepth(b); - }); - logger.timeEnd("sort relevant modules"); - - /** @type {Statistics} */ - const stats = { - cached: 0, - alreadyInConfig: 0, - invalidModule: 0, - incorrectChunks: 0, - incorrectDependency: 0, - incorrectModuleDependency: 0, - incorrectChunksOfImporter: 0, - incorrectRuntimeCondition: 0, - importerFailed: 0, - added: 0 - }; - let statsCandidates = 0; - let statsSizeSum = 0; - let statsEmptyConfigurations = 0; - - logger.time("find modules to concatenate"); - const concatConfigurations = []; - const usedAsInner = new Set(); - for (const currentRoot of relevantModules) { - // when used by another configuration as inner: - // the other configuration is better and we can skip this one - // TODO reconsider that when it's only used in a different runtime - if (usedAsInner.has(currentRoot)) continue; - - let chunkRuntime = undefined; - for (const r of chunkGraph.getModuleRuntimes(currentRoot)) { - chunkRuntime = mergeRuntimeOwned(chunkRuntime, r); - } - const exportsInfo = moduleGraph.getExportsInfo(currentRoot); - const filteredRuntime = filterRuntime(chunkRuntime, r => - exportsInfo.isModuleUsed(r) - ); - const activeRuntime = - filteredRuntime === true - ? chunkRuntime - : filteredRuntime === false - ? undefined - : filteredRuntime; - - // create a configuration with the root - const currentConfiguration = new ConcatConfiguration( - currentRoot, - activeRuntime - ); - - // cache failures to add modules - const failureCache = new Map(); - - // potential optional import candidates - /** @type {Set} */ - const candidates = new Set(); - - // try to add all imports - for (const imp of this._getImports( - compilation, - currentRoot, - activeRuntime - )) { - candidates.add(imp); - } - - for (const imp of candidates) { - const impCandidates = new Set(); - const problem = this._tryToAdd( - compilation, - currentConfiguration, - imp, - chunkRuntime, - activeRuntime, - possibleInners, - impCandidates, - failureCache, - chunkGraph, - true, - stats - ); - if (problem) { - failureCache.set(imp, problem); - currentConfiguration.addWarning(imp, problem); - } else { - for (const c of impCandidates) { - candidates.add(c); - } - } - } - statsCandidates += candidates.size; - if (!currentConfiguration.isEmpty()) { - const modules = currentConfiguration.getModules(); - statsSizeSum += modules.size; - concatConfigurations.push(currentConfiguration); - for (const module of modules) { - if (module !== currentConfiguration.rootModule) { - usedAsInner.add(module); - } - } - } else { - statsEmptyConfigurations++; - const optimizationBailouts = - moduleGraph.getOptimizationBailout(currentRoot); - for (const warning of currentConfiguration.getWarningsSorted()) { - optimizationBailouts.push( - formatBailoutWarning(warning[0], warning[1]) - ); - } - } - } - logger.timeEnd("find modules to concatenate"); - logger.debug( - `${ - concatConfigurations.length - } successful concat configurations (avg size: ${ - statsSizeSum / concatConfigurations.length - }), ${statsEmptyConfigurations} bailed out completely` - ); - logger.debug( - `${statsCandidates} candidates were considered for adding (${stats.cached} cached failure, ${stats.alreadyInConfig} already in config, ${stats.invalidModule} invalid module, ${stats.incorrectChunks} incorrect chunks, ${stats.incorrectDependency} incorrect dependency, ${stats.incorrectChunksOfImporter} incorrect chunks of importer, ${stats.incorrectModuleDependency} incorrect module dependency, ${stats.incorrectRuntimeCondition} incorrect runtime condition, ${stats.importerFailed} importer failed, ${stats.added} added)` - ); - // HACK: Sort configurations by length and start with the longest one - // to get the biggest groups possible. Used modules are marked with usedModules - // TODO: Allow to reuse existing configuration while trying to add dependencies. - // This would improve performance. O(n^2) -> O(n) - logger.time(`sort concat configurations`); - concatConfigurations.sort((a, b) => { - return b.modules.size - a.modules.size; - }); - logger.timeEnd(`sort concat configurations`); - const usedModules = new Set(); - - logger.time("create concatenated modules"); - asyncLib.each( - concatConfigurations, - (concatConfiguration, callback) => { - const rootModule = concatConfiguration.rootModule; - - // Avoid overlapping configurations - // TODO: remove this when todo above is fixed - if (usedModules.has(rootModule)) return callback(); - const modules = concatConfiguration.getModules(); - for (const m of modules) { - usedModules.add(m); - } - - // Create a new ConcatenatedModule - let newModule = ConcatenatedModule.create( - rootModule, - modules, - concatConfiguration.runtime, - compiler.root, - compilation.outputOptions.hashFunction - ); - - const build = () => { - newModule.build( - compiler.options, - compilation, - null, - null, - err => { - if (err) { - if (!err.module) { - err.module = newModule; - } - return callback(err); - } - integrate(); - } - ); - }; - - const integrate = () => { - if (backCompat) { - ChunkGraph.setChunkGraphForModule(newModule, chunkGraph); - ModuleGraph.setModuleGraphForModule(newModule, moduleGraph); - } + const options = this.options; + const minSizeReduce = options.minSizeReduce || 1.5; - for (const warning of concatConfiguration.getWarningsSorted()) { - moduleGraph - .getOptimizationBailout(newModule) - .push(formatBailoutWarning(warning[0], warning[1])); - } - moduleGraph.cloneModuleAttributes(rootModule, newModule); - for (const m of modules) { - // add to builtModules when one of the included modules was built - if (compilation.builtModules.has(m)) { - compilation.builtModules.add(newModule); - } - if (m !== rootModule) { - // attach external references to the concatenated module too - moduleGraph.copyOutgoingModuleConnections( - m, - newModule, - c => { - return ( - c.originModule === m && - !( - c.dependency instanceof HarmonyImportDependency && - modules.has(c.module) - ) - ); - } - ); - // remove module from chunk - for (const chunk of chunkGraph.getModuleChunksIterable( - rootModule - )) { - chunkGraph.disconnectChunkAndModule(chunk, m); - } - } + compiler.hooks.thisCompilation.tap( + "AggressiveMergingPlugin", + compilation => { + compilation.hooks.optimizeChunks.tap( + { + name: "AggressiveMergingPlugin", + stage: STAGE_ADVANCED + }, + chunks => { + const chunkGraph = compilation.chunkGraph; + /** @type {{a: Chunk, b: Chunk, improvement: number}[]} */ + let combinations = []; + for (const a of chunks) { + if (a.canBeInitial()) continue; + for (const b of chunks) { + if (b.canBeInitial()) continue; + if (b === a) break; + if (!chunkGraph.canChunksBeIntegrated(a, b)) { + continue; } - compilation.modules.delete(rootModule); - ChunkGraph.clearChunkGraphForModule(rootModule); - ModuleGraph.clearModuleGraphForModule(rootModule); - - // remove module from chunk - chunkGraph.replaceModule(rootModule, newModule); - // replace module references with the concatenated module - moduleGraph.moveModuleConnections(rootModule, newModule, c => { - const otherModule = - c.module === rootModule ? c.originModule : c.module; - const innerConnection = - c.dependency instanceof HarmonyImportDependency && - modules.has(otherModule); - return !innerConnection; + const aSize = chunkGraph.getChunkSize(b, { + chunkOverhead: 0 + }); + const bSize = chunkGraph.getChunkSize(a, { + chunkOverhead: 0 }); - // add concatenated module to the compilation - compilation.modules.add(newModule); - - callback(); - }; - - build(); - }, - err => { - logger.timeEnd("create concatenated modules"); - process.nextTick(callback.bind(null, err)); + const abSize = chunkGraph.getIntegratedChunksSize(b, a, { + chunkOverhead: 0 + }); + const improvement = (aSize + bSize) / abSize; + combinations.push({ + a, + b, + improvement + }); + } } - ); - } - ); - }); - } - /** - * @param {Compilation} compilation the compilation - * @param {Module} module the module to be added - * @param {RuntimeSpec} runtime the runtime scope - * @returns {Set} the imported modules - */ - _getImports(compilation, module, runtime) { - const moduleGraph = compilation.moduleGraph; - const set = new Set(); - for (const dep of module.dependencies) { - // Get reference info only for harmony Dependencies - if (!(dep instanceof HarmonyImportDependency)) continue; + combinations.sort((a, b) => { + return b.improvement - a.improvement; + }); - const connection = moduleGraph.getConnection(dep); - // Reference is valid and has a module - if ( - !connection || - !connection.module || - !connection.isTargetActive(runtime) - ) { - continue; - } + const pair = combinations[0]; - const importedNames = compilation.getDependencyReferencedExports( - dep, - undefined - ); + if (!pair) return; + if (pair.improvement < minSizeReduce) return; - if ( - importedNames.every(i => - Array.isArray(i) ? i.length > 0 : i.name.length > 0 - ) || - Array.isArray(moduleGraph.getProvidedExports(module)) - ) { - set.add(connection.module); + chunkGraph.integrateChunks(pair.b, pair.a); + compilation.chunks.delete(pair.a); + return true; + } + ); } - } - return set; + ); } +} - /** - * @param {Compilation} compilation webpack compilation - * @param {ConcatConfiguration} config concat configuration (will be modified when added) - * @param {Module} module the module to be added - * @param {RuntimeSpec} runtime the runtime scope of the generated code - * @param {RuntimeSpec} activeRuntime the runtime scope of the root module - * @param {Set} possibleModules modules that are candidates - * @param {Set} candidates list of potential candidates (will be added to) - * @param {Map} failureCache cache for problematic modules to be more performant - * @param {ChunkGraph} chunkGraph the chunk graph - * @param {boolean} avoidMutateOnFailure avoid mutating the config when adding fails - * @param {Statistics} statistics gathering metrics - * @returns {Module | function(RequestShortener): string} the problematic module - */ - _tryToAdd( - compilation, - config, - module, - runtime, - activeRuntime, - possibleModules, - candidates, - failureCache, - chunkGraph, - avoidMutateOnFailure, - statistics - ) { - const cacheEntry = failureCache.get(module); - if (cacheEntry) { - statistics.cached++; - return cacheEntry; - } +module.exports = AggressiveMergingPlugin; - // Already added? - if (config.has(module)) { - statistics.alreadyInConfig++; - return null; - } - // Not possible to add? - if (!possibleModules.has(module)) { - statistics.invalidModule++; - failureCache.set(module, module); // cache failures for performance - return module; - } +/***/ }), - // Module must be in the correct chunks - const missingChunks = Array.from( - chunkGraph.getModuleChunksIterable(config.rootModule) - ).filter(chunk => !chunkGraph.isModuleInChunk(module, chunk)); - if (missingChunks.length > 0) { - const problem = requestShortener => { - const missingChunksList = Array.from( - new Set(missingChunks.map(chunk => chunk.name || "unnamed chunk(s)")) - ).sort(); - const chunks = Array.from( - new Set( - Array.from(chunkGraph.getModuleChunksIterable(module)).map( - chunk => chunk.name || "unnamed chunk(s)" - ) - ) - ).sort(); - return `Module ${module.readableIdentifier( - requestShortener - )} is not in the same chunk(s) (expected in chunk(s) ${missingChunksList.join( - ", " - )}, module is in chunk(s) ${chunks.join(", ")})`; - }; - statistics.incorrectChunks++; - failureCache.set(module, problem); // cache failures for performance - return problem; - } +/***/ 10055: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - const moduleGraph = compilation.moduleGraph; +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ - const incomingConnections = - moduleGraph.getIncomingConnectionsByOriginModule(module); - const incomingConnectionsFromNonModules = - incomingConnections.get(null) || incomingConnections.get(undefined); - if (incomingConnectionsFromNonModules) { - const activeNonModulesConnections = - incomingConnectionsFromNonModules.filter(connection => { - // We are not interested in inactive connections - // or connections without dependency - return connection.isActive(runtime) || connection.dependency; - }); - if (activeNonModulesConnections.length > 0) { - const problem = requestShortener => { - const importingExplanations = new Set( - activeNonModulesConnections.map(c => c.explanation).filter(Boolean) - ); - const explanations = Array.from(importingExplanations).sort(); - return `Module ${module.readableIdentifier( - requestShortener - )} is referenced ${ - explanations.length > 0 - ? `by: ${explanations.join(", ")}` - : "in an unsupported way" - }`; - }; - statistics.incorrectDependency++; - failureCache.set(module, problem); // cache failures for performance - return problem; - } - } - /** @type {Map} */ - const incomingConnectionsFromModules = new Map(); - for (const [originModule, connections] of incomingConnections) { - if (originModule) { - // Ignore connection from orphan modules - if (chunkGraph.getNumberOfModuleChunks(originModule) === 0) continue; +const { STAGE_ADVANCED } = __webpack_require__(68145); +const { intersect } = __webpack_require__(34715); +const { + compareModulesByIdentifier, + compareChunks +} = __webpack_require__(26296); +const createSchemaValidation = __webpack_require__(77695); +const identifierUtils = __webpack_require__(96236); - // We don't care for connections from other runtimes - let originRuntime = undefined; - for (const r of chunkGraph.getModuleRuntimes(originModule)) { - originRuntime = mergeRuntimeOwned(originRuntime, r); - } +/** @typedef {import("../../declarations/plugins/optimize/AggressiveSplittingPlugin").AggressiveSplittingPluginOptions} AggressiveSplittingPluginOptions */ +/** @typedef {import("../Chunk")} Chunk */ +/** @typedef {import("../ChunkGraph")} ChunkGraph */ +/** @typedef {import("../Compiler")} Compiler */ +/** @typedef {import("../Module")} Module */ - if (!intersectRuntime(runtime, originRuntime)) continue; +const validate = createSchemaValidation( + __webpack_require__(70603), + () => + __webpack_require__(3572), + { + name: "Aggressive Splitting Plugin", + baseDataPath: "options" + } +); - // We are not interested in inactive connections - const activeConnections = connections.filter(connection => - connection.isActive(runtime) - ); - if (activeConnections.length > 0) - incomingConnectionsFromModules.set(originModule, activeConnections); - } - } +const moveModuleBetween = (chunkGraph, oldChunk, newChunk) => { + return module => { + chunkGraph.disconnectChunkAndModule(oldChunk, module); + chunkGraph.connectChunkAndModule(newChunk, module); + }; +}; - const incomingModules = Array.from(incomingConnectionsFromModules.keys()); +/** + * @param {ChunkGraph} chunkGraph the chunk graph + * @param {Chunk} chunk the chunk + * @returns {function(Module): boolean} filter for entry module + */ +const isNotAEntryModule = (chunkGraph, chunk) => { + return module => { + return !chunkGraph.isEntryModuleInChunk(module, chunk); + }; +}; - // Module must be in the same chunks like the referencing module - const otherChunkModules = incomingModules.filter(originModule => { - for (const chunk of chunkGraph.getModuleChunksIterable( - config.rootModule - )) { - if (!chunkGraph.isModuleInChunk(originModule, chunk)) { - return true; - } - } - return false; - }); - if (otherChunkModules.length > 0) { - const problem = requestShortener => { - const names = otherChunkModules - .map(m => m.readableIdentifier(requestShortener)) - .sort(); - return `Module ${module.readableIdentifier( - requestShortener - )} is referenced from different chunks by these modules: ${names.join( - ", " - )}`; - }; - statistics.incorrectChunksOfImporter++; - failureCache.set(module, problem); // cache failures for performance - return problem; - } +/** @type {WeakSet} */ +const recordedChunks = new WeakSet(); - /** @type {Map} */ - const nonHarmonyConnections = new Map(); - for (const [originModule, connections] of incomingConnectionsFromModules) { - const selected = connections.filter( - connection => - !connection.dependency || - !(connection.dependency instanceof HarmonyImportDependency) - ); - if (selected.length > 0) - nonHarmonyConnections.set(originModule, connections); +class AggressiveSplittingPlugin { + /** + * @param {AggressiveSplittingPluginOptions=} options options object + */ + constructor(options = {}) { + validate(options); + + this.options = options; + if (typeof this.options.minSize !== "number") { + this.options.minSize = 30 * 1024; } - if (nonHarmonyConnections.size > 0) { - const problem = requestShortener => { - const names = Array.from(nonHarmonyConnections) - .map(([originModule, connections]) => { - return `${originModule.readableIdentifier( - requestShortener - )} (referenced with ${Array.from( - new Set( - connections - .map(c => c.dependency && c.dependency.type) - .filter(Boolean) - ) - ) - .sort() - .join(", ")})`; - }) - .sort(); - return `Module ${module.readableIdentifier( - requestShortener - )} is referenced from these modules with unsupported syntax: ${names.join( - ", " - )}`; - }; - statistics.incorrectModuleDependency++; - failureCache.set(module, problem); // cache failures for performance - return problem; + if (typeof this.options.maxSize !== "number") { + this.options.maxSize = 50 * 1024; } - - if (runtime !== undefined && typeof runtime !== "string") { - // Module must be consistently referenced in the same runtimes - /** @type {{ originModule: Module, runtimeCondition: RuntimeSpec }[]} */ - const otherRuntimeConnections = []; - outer: for (const [ - originModule, - connections - ] of incomingConnectionsFromModules) { - /** @type {false | RuntimeSpec} */ - let currentRuntimeCondition = false; - for (const connection of connections) { - const runtimeCondition = filterRuntime(runtime, runtime => { - return connection.isTargetActive(runtime); - }); - if (runtimeCondition === false) continue; - if (runtimeCondition === true) continue outer; - if (currentRuntimeCondition !== false) { - currentRuntimeCondition = mergeRuntime( - currentRuntimeCondition, - runtimeCondition - ); - } else { - currentRuntimeCondition = runtimeCondition; - } - } - if (currentRuntimeCondition !== false) { - otherRuntimeConnections.push({ - originModule, - runtimeCondition: currentRuntimeCondition - }); - } - } - if (otherRuntimeConnections.length > 0) { - const problem = requestShortener => { - return `Module ${module.readableIdentifier( - requestShortener - )} is runtime-dependent referenced by these modules: ${Array.from( - otherRuntimeConnections, - ({ originModule, runtimeCondition }) => - `${originModule.readableIdentifier( - requestShortener - )} (expected runtime ${runtimeToString( - runtime - )}, module is only referenced in ${runtimeToString( - /** @type {RuntimeSpec} */ (runtimeCondition) - )})` - ).join(", ")}`; - }; - statistics.incorrectRuntimeCondition++; - failureCache.set(module, problem); // cache failures for performance - return problem; - } + if (typeof this.options.chunkOverhead !== "number") { + this.options.chunkOverhead = 0; } - - let backup; - if (avoidMutateOnFailure) { - backup = config.snapshot(); + if (typeof this.options.entryChunkMultiplicator !== "number") { + this.options.entryChunkMultiplicator = 1; } + } - // Add the module - config.add(module); + /** + * @param {Chunk} chunk the chunk to test + * @returns {boolean} true if the chunk was recorded + */ + static wasChunkRecorded(chunk) { + return recordedChunks.has(chunk); + } - incomingModules.sort(compareModulesByIdentifier); + /** + * Apply the plugin + * @param {Compiler} compiler the compiler instance + * @returns {void} + */ + apply(compiler) { + compiler.hooks.thisCompilation.tap( + "AggressiveSplittingPlugin", + compilation => { + let needAdditionalSeal = false; + let newSplits; + let fromAggressiveSplittingSet; + let chunkSplitDataMap; + compilation.hooks.optimize.tap("AggressiveSplittingPlugin", () => { + newSplits = []; + fromAggressiveSplittingSet = new Set(); + chunkSplitDataMap = new Map(); + }); + compilation.hooks.optimizeChunks.tap( + { + name: "AggressiveSplittingPlugin", + stage: STAGE_ADVANCED + }, + chunks => { + const chunkGraph = compilation.chunkGraph; + // Precompute stuff + const nameToModuleMap = new Map(); + const moduleToNameMap = new Map(); + const makePathsRelative = + identifierUtils.makePathsRelative.bindContextCache( + compiler.context, + compiler.root + ); + for (const m of compilation.modules) { + const name = makePathsRelative(m.identifier()); + nameToModuleMap.set(name, m); + moduleToNameMap.set(m, name); + } - // Every module which depends on the added module must be in the configuration too. - for (const originModule of incomingModules) { - const problem = this._tryToAdd( - compilation, - config, - originModule, - runtime, - activeRuntime, - possibleModules, - candidates, - failureCache, - chunkGraph, - false, - statistics - ); - if (problem) { - if (backup !== undefined) config.rollback(backup); - statistics.importerFailed++; - failureCache.set(module, problem); // cache failures for performance - return problem; - } - } + // Check used chunk ids + const usedIds = new Set(); + for (const chunk of chunks) { + usedIds.add(chunk.id); + } - // Add imports to possible candidates list - for (const imp of this._getImports(compilation, module, runtime)) { - candidates.add(imp); - } - statistics.added++; - return null; - } -} + const recordedSplits = + (compilation.records && compilation.records.aggressiveSplits) || + []; + const usedSplits = newSplits + ? recordedSplits.concat(newSplits) + : recordedSplits; + + const minSize = this.options.minSize; + const maxSize = this.options.maxSize; + + const applySplit = splitData => { + // Cannot split if id is already taken + if (splitData.id !== undefined && usedIds.has(splitData.id)) { + return false; + } + + // Get module objects from names + const selectedModules = splitData.modules.map(name => + nameToModuleMap.get(name) + ); + + // Does the modules exist at all? + if (!selectedModules.every(Boolean)) return false; + + // Check if size matches (faster than waiting for hash) + let size = 0; + for (const m of selectedModules) size += m.size(); + if (size !== splitData.size) return false; + + // get chunks with all modules + const selectedChunks = intersect( + selectedModules.map( + m => new Set(chunkGraph.getModuleChunksIterable(m)) + ) + ); + + // No relevant chunks found + if (selectedChunks.size === 0) return false; + + // The found chunk is already the split or similar + if ( + selectedChunks.size === 1 && + chunkGraph.getNumberOfChunkModules( + Array.from(selectedChunks)[0] + ) === selectedModules.length + ) { + const chunk = Array.from(selectedChunks)[0]; + if (fromAggressiveSplittingSet.has(chunk)) return false; + fromAggressiveSplittingSet.add(chunk); + chunkSplitDataMap.set(chunk, splitData); + return true; + } -class ConcatConfiguration { - /** - * @param {Module} rootModule the root module - * @param {RuntimeSpec} runtime the runtime - */ - constructor(rootModule, runtime) { - this.rootModule = rootModule; - this.runtime = runtime; - /** @type {Set} */ - this.modules = new Set(); - this.modules.add(rootModule); - /** @type {Map} */ - this.warnings = new Map(); - } + // split the chunk into two parts + const newChunk = compilation.addChunk(); + newChunk.chunkReason = "aggressive splitted"; + for (const chunk of selectedChunks) { + selectedModules.forEach( + moveModuleBetween(chunkGraph, chunk, newChunk) + ); + chunk.split(newChunk); + chunk.name = null; + } + fromAggressiveSplittingSet.add(newChunk); + chunkSplitDataMap.set(newChunk, splitData); - add(module) { - this.modules.add(module); - } + if (splitData.id !== null && splitData.id !== undefined) { + newChunk.id = splitData.id; + newChunk.ids = [splitData.id]; + } + return true; + }; - has(module) { - return this.modules.has(module); - } + // try to restore to recorded splitting + let changed = false; + for (let j = 0; j < usedSplits.length; j++) { + const splitData = usedSplits[j]; + if (applySplit(splitData)) changed = true; + } - isEmpty() { - return this.modules.size === 1; - } + // for any chunk which isn't splitted yet, split it and create a new entry + // start with the biggest chunk + const cmpFn = compareChunks(chunkGraph); + const sortedChunks = Array.from(chunks).sort((a, b) => { + const diff1 = + chunkGraph.getChunkModulesSize(b) - + chunkGraph.getChunkModulesSize(a); + if (diff1) return diff1; + const diff2 = + chunkGraph.getNumberOfChunkModules(a) - + chunkGraph.getNumberOfChunkModules(b); + if (diff2) return diff2; + return cmpFn(a, b); + }); + for (const chunk of sortedChunks) { + if (fromAggressiveSplittingSet.has(chunk)) continue; + const size = chunkGraph.getChunkModulesSize(chunk); + if ( + size > maxSize && + chunkGraph.getNumberOfChunkModules(chunk) > 1 + ) { + const modules = chunkGraph + .getOrderedChunkModules(chunk, compareModulesByIdentifier) + .filter(isNotAEntryModule(chunkGraph, chunk)); + const selectedModules = []; + let selectedModulesSize = 0; + for (let k = 0; k < modules.length; k++) { + const module = modules[k]; + const newSize = selectedModulesSize + module.size(); + if (newSize > maxSize && selectedModulesSize >= minSize) { + break; + } + selectedModulesSize = newSize; + selectedModules.push(module); + } + if (selectedModules.length === 0) continue; + const splitData = { + modules: selectedModules + .map(m => moduleToNameMap.get(m)) + .sort(), + size: selectedModulesSize + }; - addWarning(module, problem) { - this.warnings.set(module, problem); - } + if (applySplit(splitData)) { + newSplits = (newSplits || []).concat(splitData); + changed = true; + } + } + } + if (changed) return true; + } + ); + compilation.hooks.recordHash.tap( + "AggressiveSplittingPlugin", + records => { + // 4. save made splittings to records + const allSplits = new Set(); + const invalidSplits = new Set(); - getWarningsSorted() { - return new Map( - Array.from(this.warnings).sort((a, b) => { - const ai = a[0].identifier(); - const bi = b[0].identifier(); - if (ai < bi) return -1; - if (ai > bi) return 1; - return 0; - }) - ); - } + // Check if some splittings are invalid + // We remove invalid splittings and try again + for (const chunk of compilation.chunks) { + const splitData = chunkSplitDataMap.get(chunk); + if (splitData !== undefined) { + if (splitData.hash && chunk.hash !== splitData.hash) { + // Split was successful, but hash doesn't equal + // We can throw away the split since it's useless now + invalidSplits.add(splitData); + } + } + } - /** - * @returns {Set} modules as set - */ - getModules() { - return this.modules; - } + if (invalidSplits.size > 0) { + records.aggressiveSplits = records.aggressiveSplits.filter( + splitData => !invalidSplits.has(splitData) + ); + needAdditionalSeal = true; + } else { + // set hash and id values on all (new) splittings + for (const chunk of compilation.chunks) { + const splitData = chunkSplitDataMap.get(chunk); + if (splitData !== undefined) { + splitData.hash = chunk.hash; + splitData.id = chunk.id; + allSplits.add(splitData); + // set flag for stats + recordedChunks.add(chunk); + } + } - snapshot() { - return this.modules.size; - } + // Also add all unused historical splits (after the used ones) + // They can still be used in some future compilation + const recordedSplits = + compilation.records && compilation.records.aggressiveSplits; + if (recordedSplits) { + for (const splitData of recordedSplits) { + if (!invalidSplits.has(splitData)) allSplits.add(splitData); + } + } - rollback(snapshot) { - const modules = this.modules; - for (const m of modules) { - if (snapshot === 0) { - modules.delete(m); - } else { - snapshot--; + // record all splits + records.aggressiveSplits = Array.from(allSplits); + + needAdditionalSeal = false; + } + } + ); + compilation.hooks.needAdditionalSeal.tap( + "AggressiveSplittingPlugin", + () => { + if (needAdditionalSeal) { + needAdditionalSeal = false; + return true; + } + } + ); } - } + ); } } - -module.exports = ModuleConcatenationPlugin; +module.exports = AggressiveSplittingPlugin; /***/ }), -/***/ 6669: +/***/ 1881: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; @@ -105749,3070 +103168,3269 @@ module.exports = ModuleConcatenationPlugin; -const { SyncBailHook } = __webpack_require__(34718); -const { RawSource, CachedSource, CompatSource } = __webpack_require__(96192); -const Compilation = __webpack_require__(59622); -const WebpackError = __webpack_require__(68422); -const { compareSelect, compareStrings } = __webpack_require__(26296); +const eslintScope = __webpack_require__(26839); +const Referencer = __webpack_require__(96988); +const { + CachedSource, + ConcatSource, + ReplaceSource +} = __webpack_require__(96192); +const ConcatenationScope = __webpack_require__(14067); +const { UsageState } = __webpack_require__(4295); +const Module = __webpack_require__(85887); +const RuntimeGlobals = __webpack_require__(49404); +const Template = __webpack_require__(92066); +const HarmonyImportDependency = __webpack_require__(19577); +const JavascriptParser = __webpack_require__(42060); +const { equals } = __webpack_require__(21537); +const LazySet = __webpack_require__(59534); +const { concatComparators, keepOriginalOrder } = __webpack_require__(26296); const createHash = __webpack_require__(24123); +const { makePathsRelative } = __webpack_require__(96236); +const makeSerializable = __webpack_require__(26522); +const propertyAccess = __webpack_require__(86709); +const { + filterRuntime, + intersectRuntime, + mergeRuntimeCondition, + mergeRuntimeConditionNonFalse, + runtimeConditionToString, + subtractRuntimeCondition +} = __webpack_require__(19655); +/** @typedef {import("eslint-scope").Scope} Scope */ /** @typedef {import("webpack-sources").Source} Source */ -/** @typedef {import("../Compilation").AssetInfo} AssetInfo */ -/** @typedef {import("../Compiler")} Compiler */ +/** @typedef {import("../../declarations/WebpackOptions").WebpackOptionsNormalized} WebpackOptions */ +/** @typedef {import("../ChunkGraph")} ChunkGraph */ +/** @typedef {import("../Compilation")} Compilation */ +/** @typedef {import("../Dependency")} Dependency */ +/** @typedef {import("../Dependency").UpdateHashContext} UpdateHashContext */ +/** @typedef {import("../DependencyTemplate").DependencyTemplateContext} DependencyTemplateContext */ +/** @typedef {import("../DependencyTemplates")} DependencyTemplates */ +/** @typedef {import("../ExportsInfo").ExportInfo} ExportInfo */ +/** @template T @typedef {import("../InitFragment")} InitFragment */ +/** @typedef {import("../Module").CodeGenerationContext} CodeGenerationContext */ +/** @typedef {import("../Module").CodeGenerationResult} CodeGenerationResult */ +/** @typedef {import("../Module").LibIdentOptions} LibIdentOptions */ +/** @typedef {import("../ModuleGraph")} ModuleGraph */ +/** @typedef {import("../ModuleGraphConnection")} ModuleGraphConnection */ +/** @typedef {import("../ModuleGraphConnection").ConnectionState} ConnectionState */ +/** @typedef {import("../RequestShortener")} RequestShortener */ +/** @typedef {import("../ResolverFactory").ResolverWithOptions} ResolverWithOptions */ +/** @typedef {import("../RuntimeTemplate")} RuntimeTemplate */ +/** @typedef {import("../WebpackError")} WebpackError */ +/** @typedef {import("../javascript/JavascriptModulesPlugin").ChunkRenderContext} ChunkRenderContext */ +/** @typedef {import("../util/Hash")} Hash */ +/** @typedef {typeof import("../util/Hash")} HashConstructor */ +/** @typedef {import("../util/fs").InputFileSystem} InputFileSystem */ +/** @typedef {import("../util/runtime").RuntimeSpec} RuntimeSpec */ -const EMPTY_SET = new Set(); +// fix eslint-scope to support class properties correctly +// cspell:word Referencer +const ReferencerClass = Referencer; +if (!ReferencerClass.prototype.PropertyDefinition) { + ReferencerClass.prototype.PropertyDefinition = + ReferencerClass.prototype.Property; +} -const addToList = (itemOrItems, list) => { - if (Array.isArray(itemOrItems)) { - for (const item of itemOrItems) { - list.add(item); - } - } else if (itemOrItems) { - list.add(itemOrItems); - } -}; +/** + * @typedef {Object} ReexportInfo + * @property {Module} module + * @property {string[]} export + */ + +/** @typedef {RawBinding | SymbolBinding} Binding */ /** - * @template T - * @param {T[]} input list - * @param {function(T): Buffer} fn map function - * @returns {Buffer[]} buffers without duplicates + * @typedef {Object} RawBinding + * @property {ModuleInfo} info + * @property {string} rawName + * @property {string=} comment + * @property {string[]} ids + * @property {string[]} exportName */ -const mapAndDeduplicateBuffers = (input, fn) => { - // Buffer.equals compares size first so this should be efficient enough - // If it becomes a performance problem we can use a map and group by size - // instead of looping over all assets. - const result = []; - outer: for (const value of input) { - const buf = fn(value); - for (const other of result) { - if (buf.equals(other)) continue outer; - } - result.push(buf); - } - return result; -}; /** - * Escapes regular expression metacharacters - * @param {string} str String to quote - * @returns {string} Escaped string + * @typedef {Object} SymbolBinding + * @property {ConcatenatedModuleInfo} info + * @property {string} name + * @property {string=} comment + * @property {string[]} ids + * @property {string[]} exportName */ -const quoteMeta = str => { - return str.replace(/[-[\]\\/{}()*+?.^$|]/g, "\\$&"); -}; -const cachedSourceMap = new WeakMap(); +/** @typedef {ConcatenatedModuleInfo | ExternalModuleInfo } ModuleInfo */ +/** @typedef {ConcatenatedModuleInfo | ExternalModuleInfo | ReferenceToModuleInfo } ModuleInfoOrReference */ -const toCachedSource = source => { - if (source instanceof CachedSource) { - return source; - } - const entry = cachedSourceMap.get(source); - if (entry !== undefined) return entry; - const newSource = new CachedSource(CompatSource.from(source)); - cachedSourceMap.set(source, newSource); - return newSource; -}; +/** + * @typedef {Object} ConcatenatedModuleInfo + * @property {"concatenated"} type + * @property {Module} module + * @property {number} index + * @property {Object} ast + * @property {Source} internalSource + * @property {ReplaceSource} source + * @property {InitFragment[]=} chunkInitFragments + * @property {Iterable} runtimeRequirements + * @property {Scope} globalScope + * @property {Scope} moduleScope + * @property {Map} internalNames + * @property {Map} exportMap + * @property {Map} rawExportMap + * @property {string=} namespaceExportSymbol + * @property {string} namespaceObjectName + * @property {boolean} interopNamespaceObjectUsed + * @property {string} interopNamespaceObjectName + * @property {boolean} interopNamespaceObject2Used + * @property {string} interopNamespaceObject2Name + * @property {boolean} interopDefaultAccessUsed + * @property {string} interopDefaultAccessName + */ /** - * @typedef {Object} AssetInfoForRealContentHash + * @typedef {Object} ExternalModuleInfo + * @property {"external"} type + * @property {Module} module + * @property {RuntimeSpec | boolean} runtimeCondition + * @property {number} index * @property {string} name - * @property {AssetInfo} info - * @property {Source} source - * @property {RawSource | undefined} newSource - * @property {RawSource | undefined} newSourceWithoutOwn - * @property {string} content - * @property {Set} ownHashes - * @property {Promise} contentComputePromise - * @property {Promise} contentComputeWithoutOwnPromise - * @property {Set} referencedHashes - * @property {Set} hashes + * @property {boolean} interopNamespaceObjectUsed + * @property {string} interopNamespaceObjectName + * @property {boolean} interopNamespaceObject2Used + * @property {string} interopNamespaceObject2Name + * @property {boolean} interopDefaultAccessUsed + * @property {string} interopDefaultAccessName */ /** - * @typedef {Object} CompilationHooks - * @property {SyncBailHook<[Buffer[], string], string>} updateHash + * @typedef {Object} ReferenceToModuleInfo + * @property {"reference"} type + * @property {RuntimeSpec | boolean} runtimeCondition + * @property {ConcatenatedModuleInfo | ExternalModuleInfo} target */ -/** @type {WeakMap} */ -const compilationHooksMap = new WeakMap(); +const RESERVED_NAMES = new Set( + [ + // internal names (should always be renamed) + ConcatenationScope.DEFAULT_EXPORT, + ConcatenationScope.NAMESPACE_OBJECT_EXPORT, -class RealContentHashPlugin { - /** - * @param {Compilation} compilation the compilation - * @returns {CompilationHooks} the attached hooks - */ - static getCompilationHooks(compilation) { - if (!(compilation instanceof Compilation)) { - throw new TypeError( - "The 'compilation' argument must be an instance of Compilation" - ); + // keywords + "abstract,arguments,async,await,boolean,break,byte,case,catch,char,class,const,continue", + "debugger,default,delete,do,double,else,enum,eval,export,extends,false,final,finally,float", + "for,function,goto,if,implements,import,in,instanceof,int,interface,let,long,native,new,null", + "package,private,protected,public,return,short,static,super,switch,synchronized,this,throw", + "throws,transient,true,try,typeof,var,void,volatile,while,with,yield", + + // commonjs/amd + "module,__dirname,__filename,exports,require,define", + + // js globals + "Array,Date,eval,function,hasOwnProperty,Infinity,isFinite,isNaN,isPrototypeOf,length,Math", + "NaN,name,Number,Object,prototype,String,toString,undefined,valueOf", + + // browser globals + "alert,all,anchor,anchors,area,assign,blur,button,checkbox,clearInterval,clearTimeout", + "clientInformation,close,closed,confirm,constructor,crypto,decodeURI,decodeURIComponent", + "defaultStatus,document,element,elements,embed,embeds,encodeURI,encodeURIComponent,escape", + "event,fileUpload,focus,form,forms,frame,innerHeight,innerWidth,layer,layers,link,location", + "mimeTypes,navigate,navigator,frames,frameRate,hidden,history,image,images,offscreenBuffering", + "open,opener,option,outerHeight,outerWidth,packages,pageXOffset,pageYOffset,parent,parseFloat", + "parseInt,password,pkcs11,plugin,prompt,propertyIsEnum,radio,reset,screenX,screenY,scroll", + "secure,select,self,setInterval,setTimeout,status,submit,taint,text,textarea,top,unescape", + "untaint,window", + + // window events + "onblur,onclick,onerror,onfocus,onkeydown,onkeypress,onkeyup,onmouseover,onload,onmouseup,onmousedown,onsubmit" + ] + .join(",") + .split(",") +); + +const bySourceOrder = (a, b) => { + const aOrder = a.sourceOrder; + const bOrder = b.sourceOrder; + if (isNaN(aOrder)) { + if (!isNaN(bOrder)) { + return 1; } - let hooks = compilationHooksMap.get(compilation); - if (hooks === undefined) { - hooks = { - updateHash: new SyncBailHook(["content", "oldHash"]) - }; - compilationHooksMap.set(compilation, hooks); + } else { + if (isNaN(bOrder)) { + return -1; + } + if (aOrder !== bOrder) { + return aOrder < bOrder ? -1 : 1; + } + } + return 0; +}; + +const joinIterableWithComma = iterable => { + // This is more performant than Array.from().join(", ") + // as it doesn't create an array + let str = ""; + let first = true; + for (const item of iterable) { + if (first) { + first = false; + } else { + str += ", "; + } + str += item; + } + return str; +}; + +/** + * @typedef {Object} ConcatenationEntry + * @property {"concatenated" | "external"} type + * @property {Module} module + * @property {RuntimeSpec | boolean} runtimeCondition + */ + +/** + * @param {ModuleGraph} moduleGraph the module graph + * @param {ModuleInfo} info module info + * @param {string[]} exportName exportName + * @param {Map} moduleToInfoMap moduleToInfoMap + * @param {RuntimeSpec} runtime for which runtime + * @param {RequestShortener} requestShortener the request shortener + * @param {RuntimeTemplate} runtimeTemplate the runtime template + * @param {Set} neededNamespaceObjects modules for which a namespace object should be generated + * @param {boolean} asCall asCall + * @param {boolean} strictHarmonyModule strictHarmonyModule + * @param {boolean | undefined} asiSafe asiSafe + * @param {Set} alreadyVisited alreadyVisited + * @returns {Binding} the final variable + */ +const getFinalBinding = ( + moduleGraph, + info, + exportName, + moduleToInfoMap, + runtime, + requestShortener, + runtimeTemplate, + neededNamespaceObjects, + asCall, + strictHarmonyModule, + asiSafe, + alreadyVisited = new Set() +) => { + const exportsType = info.module.getExportsType( + moduleGraph, + strictHarmonyModule + ); + if (exportName.length === 0) { + switch (exportsType) { + case "default-only": + info.interopNamespaceObject2Used = true; + return { + info, + rawName: info.interopNamespaceObject2Name, + ids: exportName, + exportName + }; + case "default-with-named": + info.interopNamespaceObjectUsed = true; + return { + info, + rawName: info.interopNamespaceObjectName, + ids: exportName, + exportName + }; + case "namespace": + case "dynamic": + break; + default: + throw new Error(`Unexpected exportsType ${exportsType}`); } - return hooks; - } - - constructor({ hashFunction, hashDigest }) { - this._hashFunction = hashFunction; - this._hashDigest = hashDigest; - } - - /** - * Apply the plugin - * @param {Compiler} compiler the compiler instance - * @returns {void} - */ - apply(compiler) { - compiler.hooks.compilation.tap("RealContentHashPlugin", compilation => { - const cacheAnalyse = compilation.getCache( - "RealContentHashPlugin|analyse" - ); - const cacheGenerate = compilation.getCache( - "RealContentHashPlugin|generate" - ); - const hooks = RealContentHashPlugin.getCompilationHooks(compilation); - compilation.hooks.processAssets.tapPromise( - { - name: "RealContentHashPlugin", - stage: Compilation.PROCESS_ASSETS_STAGE_OPTIMIZE_HASH - }, - async () => { - const assets = compilation.getAssets(); - /** @type {AssetInfoForRealContentHash[]} */ - const assetsWithInfo = []; - const hashToAssets = new Map(); - for (const { source, info, name } of assets) { - const cachedSource = toCachedSource(source); - const content = cachedSource.source(); - /** @type {Set} */ - const hashes = new Set(); - addToList(info.contenthash, hashes); - const data = { - name, + } else { + switch (exportsType) { + case "namespace": + break; + case "default-with-named": + switch (exportName[0]) { + case "default": + exportName = exportName.slice(1); + break; + case "__esModule": + return { info, - source: cachedSource, - /** @type {RawSource | undefined} */ - newSource: undefined, - /** @type {RawSource | undefined} */ - newSourceWithoutOwn: undefined, - content, - /** @type {Set} */ - ownHashes: undefined, - contentComputePromise: undefined, - contentComputeWithoutOwnPromise: undefined, - /** @type {Set} */ - referencedHashes: undefined, - hashes + rawName: "/* __esModule */true", + ids: exportName.slice(1), + exportName }; - assetsWithInfo.push(data); - for (const hash of hashes) { - const list = hashToAssets.get(hash); - if (list === undefined) { - hashToAssets.set(hash, [data]); - } else { - list.push(data); - } - } - } - if (hashToAssets.size === 0) return; - const hashRegExp = new RegExp( - Array.from(hashToAssets.keys(), quoteMeta).join("|"), - "g" - ); - await Promise.all( - assetsWithInfo.map(async asset => { - const { name, source, content, hashes } = asset; - if (Buffer.isBuffer(content)) { - asset.referencedHashes = EMPTY_SET; - asset.ownHashes = EMPTY_SET; - return; - } - const etag = cacheAnalyse.mergeEtags( - cacheAnalyse.getLazyHashedEtag(source), - Array.from(hashes).join("|") - ); - [asset.referencedHashes, asset.ownHashes] = - await cacheAnalyse.providePromise(name, etag, () => { - const referencedHashes = new Set(); - let ownHashes = new Set(); - const inContent = content.match(hashRegExp); - if (inContent) { - for (const hash of inContent) { - if (hashes.has(hash)) { - ownHashes.add(hash); - continue; - } - referencedHashes.add(hash); - } - } - return [referencedHashes, ownHashes]; - }); - }) - ); - const getDependencies = hash => { - const assets = hashToAssets.get(hash); - if (!assets) { - const referencingAssets = assetsWithInfo.filter(asset => - asset.referencedHashes.has(hash) - ); - const err = new WebpackError(`RealContentHashPlugin -Some kind of unexpected caching problem occurred. -An asset was cached with a reference to another asset (${hash}) that's not in the compilation anymore. -Either the asset was incorrectly cached, or the referenced asset should also be restored from cache. -Referenced by: -${referencingAssets - .map(a => { - const match = new RegExp(`.{0,20}${quoteMeta(hash)}.{0,20}`).exec( - a.content - ); - return ` - ${a.name}: ...${match ? match[0] : "???"}...`; - }) - .join("\n")}`); - compilation.errors.push(err); - return undefined; - } - const hashes = new Set(); - for (const { referencedHashes, ownHashes } of assets) { - if (!ownHashes.has(hash)) { - for (const hash of ownHashes) { - hashes.add(hash); - } - } - for (const hash of referencedHashes) { - hashes.add(hash); - } - } - return hashes; + } + break; + case "default-only": { + const exportId = exportName[0]; + if (exportId === "__esModule") { + return { + info, + rawName: "/* __esModule */true", + ids: exportName.slice(1), + exportName }; - const hashInfo = hash => { - const assets = hashToAssets.get(hash); - return `${hash} (${Array.from(assets, a => a.name)})`; + } + exportName = exportName.slice(1); + if (exportId !== "default") { + return { + info, + rawName: + "/* non-default import from default-exporting module */undefined", + ids: exportName, + exportName }; - const hashesInOrder = new Set(); - for (const hash of hashToAssets.keys()) { - const add = (hash, stack) => { - const deps = getDependencies(hash); - if (!deps) return; - stack.add(hash); - for (const dep of deps) { - if (hashesInOrder.has(dep)) continue; - if (stack.has(dep)) { - throw new Error( - `Circular hash dependency ${Array.from( - stack, - hashInfo - ).join(" -> ")} -> ${hashInfo(dep)}` - ); - } - add(dep, stack); - } - hashesInOrder.add(hash); - stack.delete(hash); + } + break; + } + case "dynamic": + switch (exportName[0]) { + case "default": { + exportName = exportName.slice(1); + info.interopDefaultAccessUsed = true; + const defaultExport = asCall + ? `${info.interopDefaultAccessName}()` + : asiSafe + ? `(${info.interopDefaultAccessName}())` + : asiSafe === false + ? `;(${info.interopDefaultAccessName}())` + : `${info.interopDefaultAccessName}.a`; + return { + info, + rawName: defaultExport, + ids: exportName, + exportName }; - if (hashesInOrder.has(hash)) continue; - add(hash, new Set()); } - const hashToNewHash = new Map(); - const getEtag = asset => - cacheGenerate.mergeEtags( - cacheGenerate.getLazyHashedEtag(asset.source), - Array.from(asset.referencedHashes, hash => - hashToNewHash.get(hash) - ).join("|") - ); - const computeNewContent = asset => { - if (asset.contentComputePromise) return asset.contentComputePromise; - return (asset.contentComputePromise = (async () => { - if ( - asset.ownHashes.size > 0 || - Array.from(asset.referencedHashes).some( - hash => hashToNewHash.get(hash) !== hash - ) - ) { - const identifier = asset.name; - const etag = getEtag(asset); - asset.newSource = await cacheGenerate.providePromise( - identifier, - etag, - () => { - const newContent = asset.content.replace(hashRegExp, hash => - hashToNewHash.get(hash) - ); - return new RawSource(newContent); - } - ); - } - })()); - }; - const computeNewContentWithoutOwn = asset => { - if (asset.contentComputeWithoutOwnPromise) - return asset.contentComputeWithoutOwnPromise; - return (asset.contentComputeWithoutOwnPromise = (async () => { - if ( - asset.ownHashes.size > 0 || - Array.from(asset.referencedHashes).some( - hash => hashToNewHash.get(hash) !== hash - ) - ) { - const identifier = asset.name + "|without-own"; - const etag = getEtag(asset); - asset.newSourceWithoutOwn = await cacheGenerate.providePromise( - identifier, - etag, - () => { - const newContent = asset.content.replace( - hashRegExp, - hash => { - if (asset.ownHashes.has(hash)) { - return ""; - } - return hashToNewHash.get(hash); - } - ); - return new RawSource(newContent); - } - ); - } - })()); + case "__esModule": + return { + info, + rawName: "/* __esModule */true", + ids: exportName.slice(1), + exportName + }; + } + break; + default: + throw new Error(`Unexpected exportsType ${exportsType}`); + } + } + if (exportName.length === 0) { + switch (info.type) { + case "concatenated": + neededNamespaceObjects.add(info); + return { + info, + rawName: info.namespaceObjectName, + ids: exportName, + exportName + }; + case "external": + return { info, rawName: info.name, ids: exportName, exportName }; + } + } + const exportsInfo = moduleGraph.getExportsInfo(info.module); + const exportInfo = exportsInfo.getExportInfo(exportName[0]); + if (alreadyVisited.has(exportInfo)) { + return { + info, + rawName: "/* circular reexport */ Object(function x() { x() }())", + ids: [], + exportName + }; + } + alreadyVisited.add(exportInfo); + switch (info.type) { + case "concatenated": { + const exportId = exportName[0]; + if (exportInfo.provided === false) { + // It's not provided, but it could be on the prototype + neededNamespaceObjects.add(info); + return { + info, + rawName: info.namespaceObjectName, + ids: exportName, + exportName + }; + } + const directExport = info.exportMap && info.exportMap.get(exportId); + if (directExport) { + const usedName = /** @type {string[]} */ ( + exportsInfo.getUsedName(exportName, runtime) + ); + if (!usedName) { + return { + info, + rawName: "/* unused export */ undefined", + ids: exportName.slice(1), + exportName }; - const comparator = compareSelect(a => a.name, compareStrings); - for (const oldHash of hashesInOrder) { - const assets = hashToAssets.get(oldHash); - assets.sort(comparator); - const hash = createHash(this._hashFunction); - await Promise.all( - assets.map(asset => - asset.ownHashes.has(oldHash) - ? computeNewContentWithoutOwn(asset) - : computeNewContent(asset) - ) - ); - const assetsContent = mapAndDeduplicateBuffers(assets, asset => { - if (asset.ownHashes.has(oldHash)) { - return asset.newSourceWithoutOwn - ? asset.newSourceWithoutOwn.buffer() - : asset.source.buffer(); - } else { - return asset.newSource - ? asset.newSource.buffer() - : asset.source.buffer(); - } - }); - let newHash = hooks.updateHash.call(assetsContent, oldHash); - if (!newHash) { - for (const content of assetsContent) { - hash.update(content); - } - const digest = hash.digest(this._hashDigest); - newHash = /** @type {string} */ (digest.slice(0, oldHash.length)); - } - hashToNewHash.set(oldHash, newHash); - } - await Promise.all( - assetsWithInfo.map(async asset => { - await computeNewContent(asset); - const newName = asset.name.replace(hashRegExp, hash => - hashToNewHash.get(hash) - ); + } + return { + info, + name: directExport, + ids: usedName.slice(1), + exportName + }; + } + const rawExport = info.rawExportMap && info.rawExportMap.get(exportId); + if (rawExport) { + return { + info, + rawName: rawExport, + ids: exportName.slice(1), + exportName + }; + } + const reexport = exportInfo.findTarget(moduleGraph, module => + moduleToInfoMap.has(module) + ); + if (reexport === false) { + throw new Error( + `Target module of reexport from '${info.module.readableIdentifier( + requestShortener + )}' is not part of the concatenation (export '${exportId}')\nModules in the concatenation:\n${Array.from( + moduleToInfoMap, + ([m, info]) => + ` * ${info.type} ${m.readableIdentifier(requestShortener)}` + ).join("\n")}` + ); + } + if (reexport) { + const refInfo = moduleToInfoMap.get(reexport.module); + return getFinalBinding( + moduleGraph, + refInfo, + reexport.export + ? [...reexport.export, ...exportName.slice(1)] + : exportName.slice(1), + moduleToInfoMap, + runtime, + requestShortener, + runtimeTemplate, + neededNamespaceObjects, + asCall, + info.module.buildMeta.strictHarmonyModule, + asiSafe, + alreadyVisited + ); + } + if (info.namespaceExportSymbol) { + const usedName = /** @type {string[]} */ ( + exportsInfo.getUsedName(exportName, runtime) + ); + return { + info, + rawName: info.namespaceObjectName, + ids: usedName, + exportName + }; + } + throw new Error( + `Cannot get final name for export '${exportName.join( + "." + )}' of ${info.module.readableIdentifier(requestShortener)}` + ); + } - const infoUpdate = {}; - const hash = asset.info.contenthash; - infoUpdate.contenthash = Array.isArray(hash) - ? hash.map(hash => hashToNewHash.get(hash)) - : hashToNewHash.get(hash); + case "external": { + const used = /** @type {string[]} */ ( + exportsInfo.getUsedName(exportName, runtime) + ); + if (!used) { + return { + info, + rawName: "/* unused export */ undefined", + ids: exportName.slice(1), + exportName + }; + } + const comment = equals(used, exportName) + ? "" + : Template.toNormalComment(`${exportName.join(".")}`); + return { info, rawName: info.name + comment, ids: used, exportName }; + } + } +}; - if (asset.newSource !== undefined) { - compilation.updateAsset( - asset.name, - asset.newSource, - infoUpdate - ); - } else { - compilation.updateAsset(asset.name, asset.source, infoUpdate); - } +/** + * @param {ModuleGraph} moduleGraph the module graph + * @param {ModuleInfo} info module info + * @param {string[]} exportName exportName + * @param {Map} moduleToInfoMap moduleToInfoMap + * @param {RuntimeSpec} runtime for which runtime + * @param {RequestShortener} requestShortener the request shortener + * @param {RuntimeTemplate} runtimeTemplate the runtime template + * @param {Set} neededNamespaceObjects modules for which a namespace object should be generated + * @param {boolean} asCall asCall + * @param {boolean} callContext callContext + * @param {boolean} strictHarmonyModule strictHarmonyModule + * @param {boolean | undefined} asiSafe asiSafe + * @returns {string} the final name + */ +const getFinalName = ( + moduleGraph, + info, + exportName, + moduleToInfoMap, + runtime, + requestShortener, + runtimeTemplate, + neededNamespaceObjects, + asCall, + callContext, + strictHarmonyModule, + asiSafe +) => { + const binding = getFinalBinding( + moduleGraph, + info, + exportName, + moduleToInfoMap, + runtime, + requestShortener, + runtimeTemplate, + neededNamespaceObjects, + asCall, + strictHarmonyModule, + asiSafe + ); + { + const { ids, comment } = binding; + let reference; + let isPropertyAccess; + if ("rawName" in binding) { + reference = `${binding.rawName}${comment || ""}${propertyAccess(ids)}`; + isPropertyAccess = ids.length > 0; + } else { + const { info, name: exportId } = binding; + const name = info.internalNames.get(exportId); + if (!name) { + throw new Error( + `The export "${exportId}" in "${info.module.readableIdentifier( + requestShortener + )}" has no internal name (existing names: ${ + Array.from( + info.internalNames, + ([name, symbol]) => `${name}: ${symbol}` + ).join(", ") || "none" + })` + ); + } + reference = `${name}${comment || ""}${propertyAccess(ids)}`; + isPropertyAccess = ids.length > 1; + } + if (isPropertyAccess && asCall && callContext === false) { + return asiSafe + ? `(0,${reference})` + : asiSafe === false + ? `;(0,${reference})` + : `/*#__PURE__*/Object(${reference})`; + } + return reference; + } +}; - if (asset.name !== newName) { - compilation.renameAsset(asset.name, newName); - } - }) - ); - } - ); - }); +const addScopeSymbols = (s, nameSet, scopeSet1, scopeSet2) => { + let scope = s; + while (scope) { + if (scopeSet1.has(scope)) break; + if (scopeSet2.has(scope)) break; + scopeSet1.add(scope); + for (const variable of scope.variables) { + nameSet.add(variable.name); + } + scope = scope.upper; } -} +}; -module.exports = RealContentHashPlugin; +const getAllReferences = variable => { + let set = variable.references; + // Look for inner scope variables too (like in class Foo { t() { Foo } }) + const identifiers = new Set(variable.identifiers); + for (const scope of variable.scope.childScopes) { + for (const innerVar of scope.variables) { + if (innerVar.identifiers.some(id => identifiers.has(id))) { + set = set.concat(innerVar.references); + break; + } + } + } + return set; +}; +const getPathInAst = (ast, node) => { + if (ast === node) { + return []; + } -/***/ }), + const nr = node.range; -/***/ 66290: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + const enterNode = n => { + if (!n) return undefined; + const r = n.range; + if (r) { + if (r[0] <= nr[0] && r[1] >= nr[1]) { + const path = getPathInAst(n, node); + if (path) { + path.push(n); + return path; + } + } + } + return undefined; + }; -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ + if (Array.isArray(ast)) { + for (let i = 0; i < ast.length; i++) { + const enterResult = enterNode(ast[i]); + if (enterResult !== undefined) return enterResult; + } + } else if (ast && typeof ast === "object") { + const keys = Object.keys(ast); + for (let i = 0; i < keys.length; i++) { + const value = ast[keys[i]]; + if (Array.isArray(value)) { + const pathResult = getPathInAst(value, node); + if (pathResult !== undefined) return pathResult; + } else if (value && typeof value === "object") { + const enterResult = enterNode(value); + if (enterResult !== undefined) return enterResult; + } + } + } +}; +const TYPES = new Set(["javascript"]); +class ConcatenatedModule extends Module { + /** + * @param {Module} rootModule the root module of the concatenation + * @param {Set} modules all modules in the concatenation (including the root module) + * @param {RuntimeSpec} runtime the runtime + * @param {Object=} associatedObjectForCache object for caching + * @param {string | HashConstructor=} hashFunction hash function to use + * @returns {ConcatenatedModule} the module + */ + static create( + rootModule, + modules, + runtime, + associatedObjectForCache, + hashFunction = "md4" + ) { + const identifier = ConcatenatedModule._createIdentifier( + rootModule, + modules, + associatedObjectForCache, + hashFunction + ); + return new ConcatenatedModule({ + identifier, + rootModule, + modules, + runtime + }); + } -const { STAGE_BASIC, STAGE_ADVANCED } = __webpack_require__(68145); + /** + * @param {Object} options options + * @param {string} options.identifier the identifier of the module + * @param {Module=} options.rootModule the root module of the concatenation + * @param {RuntimeSpec} options.runtime the selected runtime + * @param {Set=} options.modules all concatenated modules + */ + constructor({ identifier, rootModule, modules, runtime }) { + super("javascript/esm", null, rootModule && rootModule.layer); -/** @typedef {import("../Chunk")} Chunk */ -/** @typedef {import("../Compiler")} Compiler */ + // Info from Factory + /** @type {string} */ + this._identifier = identifier; + /** @type {Module} */ + this.rootModule = rootModule; + /** @type {Set} */ + this._modules = modules; + this._runtime = runtime; + this.factoryMeta = rootModule && rootModule.factoryMeta; + } -class RemoveEmptyChunksPlugin { /** - * Apply the plugin - * @param {Compiler} compiler the compiler instance + * Assuming this module is in the cache. Update the (cached) module with + * the fresh module from the factory. Usually updates internal references + * and properties. + * @param {Module} module fresh module * @returns {void} */ - apply(compiler) { - compiler.hooks.compilation.tap("RemoveEmptyChunksPlugin", compilation => { - /** - * @param {Iterable} chunks the chunks array - * @returns {void} - */ - const handler = chunks => { - const chunkGraph = compilation.chunkGraph; - for (const chunk of chunks) { - if ( - chunkGraph.getNumberOfChunkModules(chunk) === 0 && - !chunk.hasRuntime() && - chunkGraph.getNumberOfEntryModules(chunk) === 0 - ) { - compilation.chunkGraph.disconnectChunk(chunk); - compilation.chunks.delete(chunk); - } - } - }; - - // TODO do it once - compilation.hooks.optimizeChunks.tap( - { - name: "RemoveEmptyChunksPlugin", - stage: STAGE_BASIC - }, - handler - ); - compilation.hooks.optimizeChunks.tap( - { - name: "RemoveEmptyChunksPlugin", - stage: STAGE_ADVANCED - }, - handler - ); - }); + updateCacheModule(module) { + throw new Error("Must not be called"); } -} -module.exports = RemoveEmptyChunksPlugin; - -/***/ }), + /** + * @returns {Set} types available (do not mutate) + */ + getSourceTypes() { + return TYPES; + } -/***/ 75072: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + get modules() { + return Array.from(this._modules); + } -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ + /** + * @returns {string} a unique identifier of the module + */ + identifier() { + return this._identifier; + } + /** + * @param {RequestShortener} requestShortener the request shortener + * @returns {string} a user readable identifier of the module + */ + readableIdentifier(requestShortener) { + return ( + this.rootModule.readableIdentifier(requestShortener) + + ` + ${this._modules.size - 1} modules` + ); + } + /** + * @param {LibIdentOptions} options options + * @returns {string | null} an identifier for library inclusion + */ + libIdent(options) { + return this.rootModule.libIdent(options); + } -const { STAGE_BASIC } = __webpack_require__(68145); -const Queue = __webpack_require__(65753); -const { intersect } = __webpack_require__(34715); + /** + * @returns {string | null} absolute path which should be used for condition matching (usually the resource path) + */ + nameForCondition() { + return this.rootModule.nameForCondition(); + } -/** @typedef {import("../Compiler")} Compiler */ + /** + * @param {ModuleGraph} moduleGraph the module graph + * @returns {ConnectionState} how this module should be connected to referencing modules when consumed for side-effects only + */ + getSideEffectsConnectionState(moduleGraph) { + return this.rootModule.getSideEffectsConnectionState(moduleGraph); + } -class RemoveParentModulesPlugin { /** - * @param {Compiler} compiler the compiler + * @param {WebpackOptions} options webpack options + * @param {Compilation} compilation the compilation + * @param {ResolverWithOptions} resolver the resolver + * @param {InputFileSystem} fs the file system + * @param {function(WebpackError=): void} callback callback function * @returns {void} */ - apply(compiler) { - compiler.hooks.compilation.tap("RemoveParentModulesPlugin", compilation => { - const handler = (chunks, chunkGroups) => { - const chunkGraph = compilation.chunkGraph; - const queue = new Queue(); - const availableModulesMap = new WeakMap(); + build(options, compilation, resolver, fs, callback) { + const { rootModule } = this; + this.buildInfo = { + strict: true, + cacheable: true, + moduleArgument: rootModule.buildInfo.moduleArgument, + exportsArgument: rootModule.buildInfo.exportsArgument, + fileDependencies: new LazySet(), + contextDependencies: new LazySet(), + missingDependencies: new LazySet(), + topLevelDeclarations: new Set(), + assets: undefined + }; + this.buildMeta = rootModule.buildMeta; + this.clearDependenciesAndBlocks(); + this.clearWarningsAndErrors(); - for (const chunkGroup of compilation.entrypoints.values()) { - // initialize available modules for chunks without parents - availableModulesMap.set(chunkGroup, new Set()); - for (const child of chunkGroup.childrenIterable) { - queue.enqueue(child); - } + for (const m of this._modules) { + // populate cacheable + if (!m.buildInfo.cacheable) { + this.buildInfo.cacheable = false; + } + + // populate dependencies + for (const d of m.dependencies.filter( + dep => + !(dep instanceof HarmonyImportDependency) || + !this._modules.has(compilation.moduleGraph.getModule(dep)) + )) { + this.dependencies.push(d); + } + // populate blocks + for (const d of m.blocks) { + this.blocks.push(d); + } + + // populate warnings + const warnings = m.getWarnings(); + if (warnings !== undefined) { + for (const warning of warnings) { + this.addWarning(warning); } - for (const chunkGroup of compilation.asyncEntrypoints) { - // initialize available modules for chunks without parents - availableModulesMap.set(chunkGroup, new Set()); - for (const child of chunkGroup.childrenIterable) { - queue.enqueue(child); - } + } + + // populate errors + const errors = m.getErrors(); + if (errors !== undefined) { + for (const error of errors) { + this.addError(error); } + } - while (queue.length > 0) { - const chunkGroup = queue.dequeue(); - let availableModules = availableModulesMap.get(chunkGroup); - let changed = false; - for (const parent of chunkGroup.parentsIterable) { - const availableModulesInParent = availableModulesMap.get(parent); - if (availableModulesInParent !== undefined) { - // If we know the available modules in parent: process these - if (availableModules === undefined) { - // if we have not own info yet: create new entry - availableModules = new Set(availableModulesInParent); - for (const chunk of parent.chunks) { - for (const m of chunkGraph.getChunkModulesIterable(chunk)) { - availableModules.add(m); - } - } - availableModulesMap.set(chunkGroup, availableModules); - changed = true; - } else { - for (const m of availableModules) { - if ( - !chunkGraph.isModuleInChunkGroup(m, parent) && - !availableModulesInParent.has(m) - ) { - availableModules.delete(m); - changed = true; - } - } - } - } - } - if (changed) { - // if something changed: enqueue our children - for (const child of chunkGroup.childrenIterable) { - queue.enqueue(child); - } + // populate topLevelDeclarations + if (m.buildInfo.topLevelDeclarations) { + const topLevelDeclarations = this.buildInfo.topLevelDeclarations; + if (topLevelDeclarations !== undefined) { + for (const decl of m.buildInfo.topLevelDeclarations) { + // reserved names will always be renamed + if (RESERVED_NAMES.has(decl)) continue; + // TODO actually this is incorrect since with renaming there could be more + // We should do the renaming during build + topLevelDeclarations.add(decl); } } + } else { + this.buildInfo.topLevelDeclarations = undefined; + } + + // populate assets + if (m.buildInfo.assets) { + if (this.buildInfo.assets === undefined) { + this.buildInfo.assets = Object.create(null); + } + Object.assign(this.buildInfo.assets, m.buildInfo.assets); + } + if (m.buildInfo.assetsInfo) { + if (this.buildInfo.assetsInfo === undefined) { + this.buildInfo.assetsInfo = new Map(); + } + for (const [key, value] of m.buildInfo.assetsInfo) { + this.buildInfo.assetsInfo.set(key, value); + } + } + } + callback(); + } + + /** + * @param {string=} type the source type for which the size should be estimated + * @returns {number} the estimated size of the module (must be non-zero) + */ + size(type) { + // Guess size from embedded modules + let size = 0; + for (const module of this._modules) { + size += module.size(type); + } + return size; + } + + /** + * @private + * @param {Module} rootModule the root of the concatenation + * @param {Set} modulesSet a set of modules which should be concatenated + * @param {RuntimeSpec} runtime for this runtime + * @param {ModuleGraph} moduleGraph the module graph + * @returns {ConcatenationEntry[]} concatenation list + */ + _createConcatenationList(rootModule, modulesSet, runtime, moduleGraph) { + /** @type {ConcatenationEntry[]} */ + const list = []; + /** @type {Map} */ + const existingEntries = new Map(); + + /** + * @param {Module} module a module + * @returns {Iterable<{ connection: ModuleGraphConnection, runtimeCondition: RuntimeSpec | true }>} imported modules in order + */ + const getConcatenatedImports = module => { + let connections = Array.from(moduleGraph.getOutgoingConnections(module)); + if (module === rootModule) { + for (const c of moduleGraph.getOutgoingConnections(this)) + connections.push(c); + } + const references = connections + .filter(connection => { + if (!(connection.dependency instanceof HarmonyImportDependency)) + return false; + return ( + connection && + connection.resolvedOriginModule === module && + connection.module && + connection.isTargetActive(runtime) + ); + }) + .map(connection => ({ + connection, + sourceOrder: /** @type {HarmonyImportDependency} */ ( + connection.dependency + ).sourceOrder + })); + references.sort( + concatComparators(bySourceOrder, keepOriginalOrder(references)) + ); + /** @type {Map} */ + const referencesMap = new Map(); + for (const { connection } of references) { + const runtimeCondition = filterRuntime(runtime, r => + connection.isTargetActive(r) + ); + if (runtimeCondition === false) continue; + const module = connection.module; + const entry = referencesMap.get(module); + if (entry === undefined) { + referencesMap.set(module, { connection, runtimeCondition }); + continue; + } + entry.runtimeCondition = mergeRuntimeConditionNonFalse( + entry.runtimeCondition, + runtimeCondition, + runtime + ); + } + return referencesMap.values(); + }; - // now we have available modules for every chunk - for (const chunk of chunks) { - const availableModulesSets = Array.from( - chunk.groupsIterable, - chunkGroup => availableModulesMap.get(chunkGroup) + /** + * @param {ModuleGraphConnection} connection graph connection + * @param {RuntimeSpec | true} runtimeCondition runtime condition + * @returns {void} + */ + const enterModule = (connection, runtimeCondition) => { + const module = connection.module; + if (!module) return; + const existingEntry = existingEntries.get(module); + if (existingEntry === true) { + return; + } + if (modulesSet.has(module)) { + existingEntries.set(module, true); + if (runtimeCondition !== true) { + throw new Error( + `Cannot runtime-conditional concatenate a module (${module.identifier()} in ${this.rootModule.identifier()}, ${runtimeConditionToString( + runtimeCondition + )}). This should not happen.` ); - if (availableModulesSets.some(s => s === undefined)) continue; // No info about this chunk group - const availableModules = - availableModulesSets.length === 1 - ? availableModulesSets[0] - : intersect(availableModulesSets); - const numberOfModules = chunkGraph.getNumberOfChunkModules(chunk); - const toRemove = new Set(); - if (numberOfModules < availableModules.size) { - for (const m of chunkGraph.getChunkModulesIterable(chunk)) { - if (availableModules.has(m)) { - toRemove.add(m); - } - } - } else { - for (const m of availableModules) { - if (chunkGraph.isModuleInChunk(m, chunk)) { - toRemove.add(m); - } - } - } - for (const module of toRemove) { - chunkGraph.disconnectChunkAndModule(chunk, module); + } + const imports = getConcatenatedImports(module); + for (const { connection, runtimeCondition } of imports) + enterModule(connection, runtimeCondition); + list.push({ + type: "concatenated", + module: connection.module, + runtimeCondition + }); + } else { + if (existingEntry !== undefined) { + const reducedRuntimeCondition = subtractRuntimeCondition( + runtimeCondition, + existingEntry, + runtime + ); + if (reducedRuntimeCondition === false) return; + runtimeCondition = reducedRuntimeCondition; + existingEntries.set( + connection.module, + mergeRuntimeConditionNonFalse( + existingEntry, + runtimeCondition, + runtime + ) + ); + } else { + existingEntries.set(connection.module, runtimeCondition); + } + if (list.length > 0) { + const lastItem = list[list.length - 1]; + if ( + lastItem.type === "external" && + lastItem.module === connection.module + ) { + lastItem.runtimeCondition = mergeRuntimeCondition( + lastItem.runtimeCondition, + runtimeCondition, + runtime + ); + return; } } - }; - compilation.hooks.optimizeChunks.tap( - { - name: "RemoveParentModulesPlugin", - stage: STAGE_BASIC - }, - handler - ); - }); - } -} -module.exports = RemoveParentModulesPlugin; - - -/***/ }), - -/***/ 23821: -/***/ (function(module) { - -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ - + list.push({ + type: "external", + get module() { + // We need to use a getter here, because the module in the dependency + // could be replaced by some other process (i. e. also replaced with a + // concatenated module) + return connection.module; + }, + runtimeCondition + }); + } + }; + existingEntries.set(rootModule, true); + const imports = getConcatenatedImports(rootModule); + for (const { connection, runtimeCondition } of imports) + enterModule(connection, runtimeCondition); + list.push({ + type: "concatenated", + module: rootModule, + runtimeCondition: true + }); -/** @typedef {import("../Compiler")} Compiler */ + return list; + } -class RuntimeChunkPlugin { - constructor(options) { - this.options = { - name: entrypoint => `runtime~${entrypoint.name}`, - ...options - }; + /** + * @param {Module} rootModule the root module of the concatenation + * @param {Set} modules all modules in the concatenation (including the root module) + * @param {Object=} associatedObjectForCache object for caching + * @param {string | HashConstructor=} hashFunction hash function to use + * @returns {string} the identifier + */ + static _createIdentifier( + rootModule, + modules, + associatedObjectForCache, + hashFunction = "md4" + ) { + const cachedMakePathsRelative = makePathsRelative.bindContextCache( + rootModule.context, + associatedObjectForCache + ); + let identifiers = []; + for (const module of modules) { + identifiers.push(cachedMakePathsRelative(module.identifier())); + } + identifiers.sort(); + const hash = createHash(hashFunction); + hash.update(identifiers.join(" ")); + return rootModule.identifier() + "|" + hash.digest("hex"); } /** - * Apply the plugin - * @param {Compiler} compiler the compiler instance - * @returns {void} + * @param {LazySet} fileDependencies set where file dependencies are added to + * @param {LazySet} contextDependencies set where context dependencies are added to + * @param {LazySet} missingDependencies set where missing dependencies are added to + * @param {LazySet} buildDependencies set where build dependencies are added to */ - apply(compiler) { - compiler.hooks.thisCompilation.tap("RuntimeChunkPlugin", compilation => { - compilation.hooks.addEntry.tap( - "RuntimeChunkPlugin", - (_, { name: entryName }) => { - if (entryName === undefined) return; - const data = compilation.entries.get(entryName); - if (data.options.runtime === undefined && !data.options.dependOn) { - // Determine runtime chunk name - let name = this.options.name; - if (typeof name === "function") { - name = name({ name: entryName }); - } - data.options.runtime = name; - } - } + addCacheDependencies( + fileDependencies, + contextDependencies, + missingDependencies, + buildDependencies + ) { + for (const module of this._modules) { + module.addCacheDependencies( + fileDependencies, + contextDependencies, + missingDependencies, + buildDependencies ); - }); + } } -} - -module.exports = RuntimeChunkPlugin; - - -/***/ }), - -/***/ 47844: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ + /** + * @param {CodeGenerationContext} context context for code generation + * @returns {CodeGenerationResult} result + */ + codeGeneration({ + dependencyTemplates, + runtimeTemplate, + moduleGraph, + chunkGraph, + runtime: generationRuntime + }) { + /** @type {Set} */ + const runtimeRequirements = new Set(); + const runtime = intersectRuntime(generationRuntime, this._runtime); + const requestShortener = runtimeTemplate.requestShortener; + // Meta info for each module + const [modulesWithInfo, moduleToInfoMap] = this._getModulesWithInfo( + moduleGraph, + runtime + ); -const glob2regexp = __webpack_require__(22797); -const { STAGE_DEFAULT } = __webpack_require__(68145); -const HarmonyExportImportedSpecifierDependency = __webpack_require__(77952); -const HarmonyImportSpecifierDependency = __webpack_require__(61994); -const formatLocation = __webpack_require__(57261); + // Set with modules that need a generated namespace object + /** @type {Set} */ + const neededNamespaceObjects = new Set(); -/** @typedef {import("../Compiler")} Compiler */ -/** @typedef {import("../Dependency")} Dependency */ -/** @typedef {import("../Module")} Module */ -/** @typedef {import("../javascript/JavascriptParser")} JavascriptParser */ + // Generate source code and analyse scopes + // Prepare a ReplaceSource for the final source + for (const info of moduleToInfoMap.values()) { + this._analyseModule( + moduleToInfoMap, + info, + dependencyTemplates, + runtimeTemplate, + moduleGraph, + chunkGraph, + runtime + ); + } -/** - * @typedef {Object} ExportInModule - * @property {Module} module the module - * @property {string} exportName the name of the export - * @property {boolean} checked if the export is conditional - */ + // List of all used names to avoid conflicts + const allUsedNames = new Set(RESERVED_NAMES); -/** - * @typedef {Object} ReexportInfo - * @property {Map} static - * @property {Map>} dynamic - */ + // List of additional names in scope for module references + /** @type {Map, alreadyCheckedScopes: Set }>} */ + const usedNamesInScopeInfo = new Map(); + /** + * @param {string} module module identifier + * @param {string} id export id + * @returns {{ usedNames: Set, alreadyCheckedScopes: Set }} info + */ + const getUsedNamesInScopeInfo = (module, id) => { + const key = `${module}-${id}`; + let info = usedNamesInScopeInfo.get(key); + if (info === undefined) { + info = { + usedNames: new Set(), + alreadyCheckedScopes: new Set() + }; + usedNamesInScopeInfo.set(key, info); + } + return info; + }; -/** @type {WeakMap>} */ -const globToRegexpCache = new WeakMap(); + // Set of already checked scopes + const ignoredScopes = new Set(); -/** - * @param {string} glob the pattern - * @param {Map} cache the glob to RegExp cache - * @returns {RegExp} a regular expression - */ -const globToRegexp = (glob, cache) => { - const cacheEntry = cache.get(glob); - if (cacheEntry !== undefined) return cacheEntry; - if (!glob.includes("/")) { - glob = `**/${glob}`; - } - const baseRegexp = glob2regexp(glob, { globstar: true, extended: true }); - const regexpSource = baseRegexp.source; - const regexp = new RegExp("^(\\./)?" + regexpSource.slice(1)); - cache.set(glob, regexp); - return regexp; -}; + // get all global names + for (const info of modulesWithInfo) { + if (info.type === "concatenated") { + // ignore symbols from moduleScope + if (info.moduleScope) { + ignoredScopes.add(info.moduleScope); + } -class SideEffectsFlagPlugin { - /** - * @param {boolean} analyseSource analyse source code for side effects - */ - constructor(analyseSource = true) { - this._analyseSource = analyseSource; - } - /** - * Apply the plugin - * @param {Compiler} compiler the compiler instance - * @returns {void} - */ - apply(compiler) { - let cache = globToRegexpCache.get(compiler.root); - if (cache === undefined) { - cache = new Map(); - globToRegexpCache.set(compiler.root, cache); - } - compiler.hooks.compilation.tap( - "SideEffectsFlagPlugin", - (compilation, { normalModuleFactory }) => { - const moduleGraph = compilation.moduleGraph; - normalModuleFactory.hooks.module.tap( - "SideEffectsFlagPlugin", - (module, data) => { - const resolveData = data.resourceResolveData; + // The super class expression in class scopes behaves weird + // We get ranges of all super class expressions to make + // renaming to work correctly + const superClassCache = new WeakMap(); + const getSuperClassExpressions = scope => { + const cacheEntry = superClassCache.get(scope); + if (cacheEntry !== undefined) return cacheEntry; + const superClassExpressions = []; + for (const childScope of scope.childScopes) { + if (childScope.type !== "class") continue; + const block = childScope.block; if ( - resolveData && - resolveData.descriptionFileData && - resolveData.relativePath + (block.type === "ClassDeclaration" || + block.type === "ClassExpression") && + block.superClass ) { - const sideEffects = resolveData.descriptionFileData.sideEffects; - if (sideEffects !== undefined) { - if (module.factoryMeta === undefined) { - module.factoryMeta = {}; - } - const hasSideEffects = - SideEffectsFlagPlugin.moduleHasSideEffects( - resolveData.relativePath, - sideEffects, - cache - ); - module.factoryMeta.sideEffectFree = !hasSideEffects; - } - } - - return module; - } - ); - normalModuleFactory.hooks.module.tap( - "SideEffectsFlagPlugin", - (module, data) => { - if (typeof data.settings.sideEffects === "boolean") { - if (module.factoryMeta === undefined) { - module.factoryMeta = {}; - } - module.factoryMeta.sideEffectFree = !data.settings.sideEffects; + superClassExpressions.push({ + range: block.superClass.range, + variables: childScope.variables + }); } - return module; } - ); - if (this._analyseSource) { - /** - * @param {JavascriptParser} parser the parser - * @returns {void} - */ - const parserHandler = parser => { - let sideEffectsStatement; - parser.hooks.program.tap("SideEffectsFlagPlugin", () => { - sideEffectsStatement = undefined; - }); - parser.hooks.statement.tap( - { name: "SideEffectsFlagPlugin", stage: -100 }, - statement => { - if (sideEffectsStatement) return; - if (parser.scope.topLevelScope !== true) return; - switch (statement.type) { - case "ExpressionStatement": - if ( - !parser.isPure(statement.expression, statement.range[0]) - ) { - sideEffectsStatement = statement; - } - break; - case "IfStatement": - case "WhileStatement": - case "DoWhileStatement": - if (!parser.isPure(statement.test, statement.range[0])) { - sideEffectsStatement = statement; - } - // statement hook will be called for child statements too - break; - case "ForStatement": - if ( - !parser.isPure(statement.init, statement.range[0]) || - !parser.isPure( - statement.test, - statement.init - ? statement.init.range[1] - : statement.range[0] - ) || - !parser.isPure( - statement.update, - statement.test - ? statement.test.range[1] - : statement.init - ? statement.init.range[1] - : statement.range[0] - ) - ) { - sideEffectsStatement = statement; - } - // statement hook will be called for child statements too - break; - case "SwitchStatement": - if ( - !parser.isPure(statement.discriminant, statement.range[0]) - ) { - sideEffectsStatement = statement; - } - // statement hook will be called for child statements too - break; - case "VariableDeclaration": - case "ClassDeclaration": - case "FunctionDeclaration": - if (!parser.isPure(statement, statement.range[0])) { - sideEffectsStatement = statement; - } - break; - case "ExportNamedDeclaration": - case "ExportDefaultDeclaration": - if ( - !parser.isPure(statement.declaration, statement.range[0]) - ) { - sideEffectsStatement = statement; - } - break; - case "LabeledStatement": - case "BlockStatement": - // statement hook will be called for child statements too - break; - case "EmptyStatement": - break; - case "ExportAllDeclaration": - case "ImportDeclaration": - // imports will be handled by the dependencies - break; - default: - sideEffectsStatement = statement; - break; + superClassCache.set(scope, superClassExpressions); + return superClassExpressions; + }; + + // add global symbols + if (info.globalScope) { + for (const reference of info.globalScope.through) { + const name = reference.identifier.name; + if (ConcatenationScope.isModuleReference(name)) { + const match = ConcatenationScope.matchModuleReference(name); + if (!match) continue; + const referencedInfo = modulesWithInfo[match.index]; + if (referencedInfo.type === "reference") + throw new Error("Module reference can't point to a reference"); + const binding = getFinalBinding( + moduleGraph, + referencedInfo, + match.ids, + moduleToInfoMap, + runtime, + requestShortener, + runtimeTemplate, + neededNamespaceObjects, + false, + info.module.buildMeta.strictHarmonyModule, + true + ); + if (!binding.ids) continue; + const { usedNames, alreadyCheckedScopes } = + getUsedNamesInScopeInfo( + binding.info.module.identifier(), + "name" in binding ? binding.name : "" + ); + for (const expr of getSuperClassExpressions(reference.from)) { + if ( + expr.range[0] <= reference.identifier.range[0] && + expr.range[1] >= reference.identifier.range[1] + ) { + for (const variable of expr.variables) { + usedNames.add(variable.name); + } } } - ); - parser.hooks.finish.tap("SideEffectsFlagPlugin", () => { - if (sideEffectsStatement === undefined) { - parser.state.module.buildMeta.sideEffectFree = true; - } else { - const { loc, type } = sideEffectsStatement; - moduleGraph - .getOptimizationBailout(parser.state.module) - .push( - () => - `Statement (${type}) with side effects in source code at ${formatLocation( - loc - )}` - ); - } - }); - }; - for (const key of [ - "javascript/auto", - "javascript/esm", - "javascript/dynamic" - ]) { - normalModuleFactory.hooks.parser - .for(key) - .tap("SideEffectsFlagPlugin", parserHandler); + addScopeSymbols( + reference.from, + usedNames, + alreadyCheckedScopes, + ignoredScopes + ); + } else { + allUsedNames.add(name); + } } } - compilation.hooks.optimizeDependencies.tap( - { - name: "SideEffectsFlagPlugin", - stage: STAGE_DEFAULT - }, - modules => { - const logger = compilation.getLogger( - "webpack.SideEffectsFlagPlugin" - ); + } + } - logger.time("update dependencies"); - for (const module of modules) { - if (module.getSideEffectsConnectionState(moduleGraph) === false) { - const exportsInfo = moduleGraph.getExportsInfo(module); - for (const connection of moduleGraph.getIncomingConnections( - module - )) { - const dep = connection.dependency; - let isReexport; + // generate names for symbols + for (const info of moduleToInfoMap.values()) { + const { usedNames: namespaceObjectUsedNames } = getUsedNamesInScopeInfo( + info.module.identifier(), + "" + ); + switch (info.type) { + case "concatenated": { + for (const variable of info.moduleScope.variables) { + const name = variable.name; + const { usedNames, alreadyCheckedScopes } = getUsedNamesInScopeInfo( + info.module.identifier(), + name + ); + if (allUsedNames.has(name) || usedNames.has(name)) { + const references = getAllReferences(variable); + for (const ref of references) { + addScopeSymbols( + ref.from, + usedNames, + alreadyCheckedScopes, + ignoredScopes + ); + } + const newName = this.findNewName( + name, + allUsedNames, + usedNames, + info.module.readableIdentifier(requestShortener) + ); + allUsedNames.add(newName); + info.internalNames.set(name, newName); + const source = info.source; + const allIdentifiers = new Set( + references.map(r => r.identifier).concat(variable.identifiers) + ); + for (const identifier of allIdentifiers) { + const r = identifier.range; + const path = getPathInAst(info.ast, identifier); + if (path && path.length > 1) { + const maybeProperty = + path[1].type === "AssignmentPattern" && + path[1].left === path[0] + ? path[2] + : path[1]; if ( - (isReexport = - dep instanceof - HarmonyExportImportedSpecifierDependency) || - (dep instanceof HarmonyImportSpecifierDependency && - !dep.namespaceObjectAsContext) + maybeProperty.type === "Property" && + maybeProperty.shorthand ) { - // TODO improve for export * - if (isReexport && dep.name) { - const exportInfo = moduleGraph.getExportInfo( - connection.originModule, - dep.name - ); - exportInfo.moveTarget( - moduleGraph, - ({ module }) => - module.getSideEffectsConnectionState(moduleGraph) === - false, - ({ module: newModule, export: exportName }) => { - moduleGraph.updateModule(dep, newModule); - moduleGraph.addExplanation( - dep, - "(skipped side-effect-free modules)" - ); - const ids = dep.getIds(moduleGraph); - dep.setIds( - moduleGraph, - exportName - ? [...exportName, ...ids.slice(1)] - : ids.slice(1) - ); - return moduleGraph.getConnection(dep); - } - ); - continue; - } - // TODO improve for nested imports - const ids = dep.getIds(moduleGraph); - if (ids.length > 0) { - const exportInfo = exportsInfo.getExportInfo(ids[0]); - const target = exportInfo.getTarget( - moduleGraph, - ({ module }) => - module.getSideEffectsConnectionState(moduleGraph) === - false - ); - if (!target) continue; - - moduleGraph.updateModule(dep, target.module); - moduleGraph.addExplanation( - dep, - "(skipped side-effect-free modules)" - ); - dep.setIds( - moduleGraph, - target.export - ? [...target.export, ...ids.slice(1)] - : ids.slice(1) - ); - } + source.insert(r[1], `: ${newName}`); + continue; } } + source.replace(r[0], r[1] - 1, newName); } + } else { + allUsedNames.add(name); + info.internalNames.set(name, name); } - logger.timeEnd("update dependencies"); } + let namespaceObjectName; + if (info.namespaceExportSymbol) { + namespaceObjectName = info.internalNames.get( + info.namespaceExportSymbol + ); + } else { + namespaceObjectName = this.findNewName( + "namespaceObject", + allUsedNames, + namespaceObjectUsedNames, + info.module.readableIdentifier(requestShortener) + ); + allUsedNames.add(namespaceObjectName); + } + info.namespaceObjectName = namespaceObjectName; + break; + } + case "external": { + const externalName = this.findNewName( + "", + allUsedNames, + namespaceObjectUsedNames, + info.module.readableIdentifier(requestShortener) + ); + allUsedNames.add(externalName); + info.name = externalName; + break; + } + } + if (info.module.buildMeta.exportsType !== "namespace") { + const externalNameInterop = this.findNewName( + "namespaceObject", + allUsedNames, + namespaceObjectUsedNames, + info.module.readableIdentifier(requestShortener) ); + allUsedNames.add(externalNameInterop); + info.interopNamespaceObjectName = externalNameInterop; } - ); - } - - static moduleHasSideEffects(moduleName, flagValue, cache) { - switch (typeof flagValue) { - case "undefined": - return true; - case "boolean": - return flagValue; - case "string": - return globToRegexp(flagValue, cache).test(moduleName); - case "object": - return flagValue.some(glob => - SideEffectsFlagPlugin.moduleHasSideEffects(moduleName, glob, cache) + if ( + info.module.buildMeta.exportsType === "default" && + info.module.buildMeta.defaultObject !== "redirect" + ) { + const externalNameInterop = this.findNewName( + "namespaceObject2", + allUsedNames, + namespaceObjectUsedNames, + info.module.readableIdentifier(requestShortener) + ); + allUsedNames.add(externalNameInterop); + info.interopNamespaceObject2Name = externalNameInterop; + } + if ( + info.module.buildMeta.exportsType === "dynamic" || + !info.module.buildMeta.exportsType + ) { + const externalNameInterop = this.findNewName( + "default", + allUsedNames, + namespaceObjectUsedNames, + info.module.readableIdentifier(requestShortener) ); + allUsedNames.add(externalNameInterop); + info.interopDefaultAccessName = externalNameInterop; + } } - } -} -module.exports = SideEffectsFlagPlugin; - - -/***/ }), - -/***/ 57073: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ - - - -const Chunk = __webpack_require__(65574); -const { STAGE_ADVANCED } = __webpack_require__(68145); -const WebpackError = __webpack_require__(68422); -const { requestToId } = __webpack_require__(72922); -const { isSubset } = __webpack_require__(34715); -const SortableSet = __webpack_require__(67563); -const { - compareModulesByIdentifier, - compareIterables -} = __webpack_require__(26296); -const createHash = __webpack_require__(24123); -const deterministicGrouping = __webpack_require__(37906); -const { makePathsRelative } = __webpack_require__(96236); -const memoize = __webpack_require__(84297); -const MinMaxSizeWarning = __webpack_require__(46681); - -/** @typedef {import("../../declarations/WebpackOptions").OptimizationSplitChunksCacheGroup} OptimizationSplitChunksCacheGroup */ -/** @typedef {import("../../declarations/WebpackOptions").OptimizationSplitChunksGetCacheGroups} OptimizationSplitChunksGetCacheGroups */ -/** @typedef {import("../../declarations/WebpackOptions").OptimizationSplitChunksOptions} OptimizationSplitChunksOptions */ -/** @typedef {import("../../declarations/WebpackOptions").OptimizationSplitChunksSizes} OptimizationSplitChunksSizes */ -/** @typedef {import("../../declarations/WebpackOptions").Output} OutputOptions */ -/** @typedef {import("../ChunkGraph")} ChunkGraph */ -/** @typedef {import("../ChunkGroup")} ChunkGroup */ -/** @typedef {import("../Compilation").AssetInfo} AssetInfo */ -/** @typedef {import("../Compilation").PathData} PathData */ -/** @typedef {import("../Compiler")} Compiler */ -/** @typedef {import("../Module")} Module */ -/** @typedef {import("../ModuleGraph")} ModuleGraph */ -/** @typedef {import("../util/deterministicGrouping").GroupedItems} DeterministicGroupingGroupedItemsForModule */ -/** @typedef {import("../util/deterministicGrouping").Options} DeterministicGroupingOptionsForModule */ - -/** @typedef {Record} SplitChunksSizes */ - -/** - * @callback ChunkFilterFunction - * @param {Chunk} chunk - * @returns {boolean} - */ - -/** - * @callback CombineSizeFunction - * @param {number} a - * @param {number} b - * @returns {number} - */ - -/** - * @typedef {Object} CacheGroupSource - * @property {string=} key - * @property {number=} priority - * @property {GetName=} getName - * @property {ChunkFilterFunction=} chunksFilter - * @property {boolean=} enforce - * @property {SplitChunksSizes} minSize - * @property {SplitChunksSizes} minSizeReduction - * @property {SplitChunksSizes} minRemainingSize - * @property {SplitChunksSizes} enforceSizeThreshold - * @property {SplitChunksSizes} maxAsyncSize - * @property {SplitChunksSizes} maxInitialSize - * @property {number=} minChunks - * @property {number=} maxAsyncRequests - * @property {number=} maxInitialRequests - * @property {(string | function(PathData, AssetInfo=): string)=} filename - * @property {string=} idHint - * @property {string} automaticNameDelimiter - * @property {boolean=} reuseExistingChunk - * @property {boolean=} usedExports - */ - -/** - * @typedef {Object} CacheGroup - * @property {string} key - * @property {number=} priority - * @property {GetName=} getName - * @property {ChunkFilterFunction=} chunksFilter - * @property {SplitChunksSizes} minSize - * @property {SplitChunksSizes} minSizeReduction - * @property {SplitChunksSizes} minRemainingSize - * @property {SplitChunksSizes} enforceSizeThreshold - * @property {SplitChunksSizes} maxAsyncSize - * @property {SplitChunksSizes} maxInitialSize - * @property {number=} minChunks - * @property {number=} maxAsyncRequests - * @property {number=} maxInitialRequests - * @property {(string | function(PathData, AssetInfo=): string)=} filename - * @property {string=} idHint - * @property {string} automaticNameDelimiter - * @property {boolean} reuseExistingChunk - * @property {boolean} usedExports - * @property {boolean} _validateSize - * @property {boolean} _validateRemainingSize - * @property {SplitChunksSizes} _minSizeForMaxSize - * @property {boolean} _conditionalEnforce - */ - -/** - * @typedef {Object} FallbackCacheGroup - * @property {ChunkFilterFunction} chunksFilter - * @property {SplitChunksSizes} minSize - * @property {SplitChunksSizes} maxAsyncSize - * @property {SplitChunksSizes} maxInitialSize - * @property {string} automaticNameDelimiter - */ - -/** - * @typedef {Object} CacheGroupsContext - * @property {ModuleGraph} moduleGraph - * @property {ChunkGraph} chunkGraph - */ - -/** - * @callback GetCacheGroups - * @param {Module} module - * @param {CacheGroupsContext} context - * @returns {CacheGroupSource[]} - */ - -/** - * @callback GetName - * @param {Module=} module - * @param {Chunk[]=} chunks - * @param {string=} key - * @returns {string=} - */ - -/** - * @typedef {Object} SplitChunksOptions - * @property {ChunkFilterFunction} chunksFilter - * @property {string[]} defaultSizeTypes - * @property {SplitChunksSizes} minSize - * @property {SplitChunksSizes} minSizeReduction - * @property {SplitChunksSizes} minRemainingSize - * @property {SplitChunksSizes} enforceSizeThreshold - * @property {SplitChunksSizes} maxInitialSize - * @property {SplitChunksSizes} maxAsyncSize - * @property {number} minChunks - * @property {number} maxAsyncRequests - * @property {number} maxInitialRequests - * @property {boolean} hidePathInfo - * @property {string | function(PathData, AssetInfo=): string} filename - * @property {string} automaticNameDelimiter - * @property {GetCacheGroups} getCacheGroups - * @property {GetName} getName - * @property {boolean} usedExports - * @property {FallbackCacheGroup} fallbackCacheGroup - */ - -/** - * @typedef {Object} ChunksInfoItem - * @property {SortableSet} modules - * @property {CacheGroup} cacheGroup - * @property {number} cacheGroupIndex - * @property {string} name - * @property {Record} sizes - * @property {Set} chunks - * @property {Set} reuseableChunks - * @property {Set} chunksKeys - */ - -const defaultGetName = /** @type {GetName} */ (() => {}); - -const deterministicGroupingForModules = - /** @type {function(DeterministicGroupingOptionsForModule): DeterministicGroupingGroupedItemsForModule[]} */ ( - deterministicGrouping - ); -/** @type {WeakMap} */ -const getKeyCache = new WeakMap(); - -/** - * @param {string} name a filename to hash - * @param {OutputOptions} outputOptions hash function used - * @returns {string} hashed filename - */ -const hashFilename = (name, outputOptions) => { - const digest = /** @type {string} */ ( - createHash(outputOptions.hashFunction) - .update(name) - .digest(outputOptions.hashDigest) - ); - return digest.slice(0, 8); -}; - -/** - * @param {Chunk} chunk the chunk - * @returns {number} the number of requests - */ -const getRequests = chunk => { - let requests = 0; - for (const chunkGroup of chunk.groupsIterable) { - requests = Math.max(requests, chunkGroup.chunks.length); - } - return requests; -}; - -const mapObject = (obj, fn) => { - const newObj = Object.create(null); - for (const key of Object.keys(obj)) { - newObj[key] = fn(obj[key], key); - } - return newObj; -}; - -/** - * @template T - * @param {Set} a set - * @param {Set} b other set - * @returns {boolean} true if at least one item of a is in b - */ -const isOverlap = (a, b) => { - for (const item of a) { - if (b.has(item)) return true; - } - return false; -}; + // Find and replace references to modules + for (const info of moduleToInfoMap.values()) { + if (info.type === "concatenated") { + for (const reference of info.globalScope.through) { + const name = reference.identifier.name; + const match = ConcatenationScope.matchModuleReference(name); + if (match) { + const referencedInfo = modulesWithInfo[match.index]; + if (referencedInfo.type === "reference") + throw new Error("Module reference can't point to a reference"); + const finalName = getFinalName( + moduleGraph, + referencedInfo, + match.ids, + moduleToInfoMap, + runtime, + requestShortener, + runtimeTemplate, + neededNamespaceObjects, + match.call, + !match.directImport, + info.module.buildMeta.strictHarmonyModule, + match.asiSafe + ); + const r = reference.identifier.range; + const source = info.source; + // range is extended by 2 chars to cover the appended "._" + source.replace(r[0], r[1] + 1, finalName); + } + } + } + } -const compareModuleIterables = compareIterables(compareModulesByIdentifier); + // Map with all root exposed used exports + /** @type {Map} */ + const exportsMap = new Map(); -/** - * @param {ChunksInfoItem} a item - * @param {ChunksInfoItem} b item - * @returns {number} compare result - */ -const compareEntries = (a, b) => { - // 1. by priority - const diffPriority = a.cacheGroup.priority - b.cacheGroup.priority; - if (diffPriority) return diffPriority; - // 2. by number of chunks - const diffCount = a.chunks.size - b.chunks.size; - if (diffCount) return diffCount; - // 3. by size reduction - const aSizeReduce = totalSize(a.sizes) * (a.chunks.size - 1); - const bSizeReduce = totalSize(b.sizes) * (b.chunks.size - 1); - const diffSizeReduce = aSizeReduce - bSizeReduce; - if (diffSizeReduce) return diffSizeReduce; - // 4. by cache group index - const indexDiff = b.cacheGroupIndex - a.cacheGroupIndex; - if (indexDiff) return indexDiff; - // 5. by number of modules (to be able to compare by identifier) - const modulesA = a.modules; - const modulesB = b.modules; - const diff = modulesA.size - modulesB.size; - if (diff) return diff; - // 6. by module identifiers - modulesA.sort(); - modulesB.sort(); - return compareModuleIterables(modulesA, modulesB); -}; + // Set with all root exposed unused exports + /** @type {Set} */ + const unusedExports = new Set(); -const INITIAL_CHUNK_FILTER = chunk => chunk.canBeInitial(); -const ASYNC_CHUNK_FILTER = chunk => !chunk.canBeInitial(); -const ALL_CHUNK_FILTER = chunk => true; + const rootInfo = /** @type {ConcatenatedModuleInfo} */ ( + moduleToInfoMap.get(this.rootModule) + ); + const strictHarmonyModule = rootInfo.module.buildMeta.strictHarmonyModule; + const exportsInfo = moduleGraph.getExportsInfo(rootInfo.module); + for (const exportInfo of exportsInfo.orderedExports) { + const name = exportInfo.name; + if (exportInfo.provided === false) continue; + const used = exportInfo.getUsedName(undefined, runtime); + if (!used) { + unusedExports.add(name); + continue; + } + exportsMap.set(used, requestShortener => { + try { + const finalName = getFinalName( + moduleGraph, + rootInfo, + [name], + moduleToInfoMap, + runtime, + requestShortener, + runtimeTemplate, + neededNamespaceObjects, + false, + false, + strictHarmonyModule, + true + ); + return `/* ${ + exportInfo.isReexport() ? "reexport" : "binding" + } */ ${finalName}`; + } catch (e) { + e.message += `\nwhile generating the root export '${name}' (used name: '${used}')`; + throw e; + } + }); + } -/** - * @param {OptimizationSplitChunksSizes} value the sizes - * @param {string[]} defaultSizeTypes the default size types - * @returns {SplitChunksSizes} normalized representation - */ -const normalizeSizes = (value, defaultSizeTypes) => { - if (typeof value === "number") { - /** @type {Record} */ - const o = {}; - for (const sizeType of defaultSizeTypes) o[sizeType] = value; - return o; - } else if (typeof value === "object" && value !== null) { - return { ...value }; - } else { - return {}; - } -}; + const result = new ConcatSource(); -/** - * @param {...SplitChunksSizes} sizes the sizes - * @returns {SplitChunksSizes} the merged sizes - */ -const mergeSizes = (...sizes) => { - /** @type {SplitChunksSizes} */ - let merged = {}; - for (let i = sizes.length - 1; i >= 0; i--) { - merged = Object.assign(merged, sizes[i]); - } - return merged; -}; + // add harmony compatibility flag (must be first because of possible circular dependencies) + if ( + moduleGraph.getExportsInfo(this).otherExportsInfo.getUsed(runtime) !== + UsageState.Unused + ) { + result.add(`// ESM COMPAT FLAG\n`); + result.add( + runtimeTemplate.defineEsModuleFlagStatement({ + exportsArgument: this.exportsArgument, + runtimeRequirements + }) + ); + } -/** - * @param {SplitChunksSizes} sizes the sizes - * @returns {boolean} true, if there are sizes > 0 - */ -const hasNonZeroSizes = sizes => { - for (const key of Object.keys(sizes)) { - if (sizes[key] > 0) return true; - } - return false; -}; + // define exports + if (exportsMap.size > 0) { + runtimeRequirements.add(RuntimeGlobals.exports); + runtimeRequirements.add(RuntimeGlobals.definePropertyGetters); + const definitions = []; + for (const [key, value] of exportsMap) { + definitions.push( + `\n ${JSON.stringify(key)}: ${runtimeTemplate.returningFunction( + value(requestShortener) + )}` + ); + } + result.add(`\n// EXPORTS\n`); + result.add( + `${RuntimeGlobals.definePropertyGetters}(${ + this.exportsArgument + }, {${definitions.join(",")}\n});\n` + ); + } -/** - * @param {SplitChunksSizes} a first sizes - * @param {SplitChunksSizes} b second sizes - * @param {CombineSizeFunction} combine a function to combine sizes - * @returns {SplitChunksSizes} the combine sizes - */ -const combineSizes = (a, b, combine) => { - const aKeys = new Set(Object.keys(a)); - const bKeys = new Set(Object.keys(b)); - /** @type {SplitChunksSizes} */ - const result = {}; - for (const key of aKeys) { - if (bKeys.has(key)) { - result[key] = combine(a[key], b[key]); - } else { - result[key] = a[key]; + // list unused exports + if (unusedExports.size > 0) { + result.add( + `\n// UNUSED EXPORTS: ${joinIterableWithComma(unusedExports)}\n` + ); } - } - for (const key of bKeys) { - if (!aKeys.has(key)) { - result[key] = b[key]; + + // generate namespace objects + const namespaceObjectSources = new Map(); + for (const info of neededNamespaceObjects) { + if (info.namespaceExportSymbol) continue; + const nsObj = []; + const exportsInfo = moduleGraph.getExportsInfo(info.module); + for (const exportInfo of exportsInfo.orderedExports) { + if (exportInfo.provided === false) continue; + const usedName = exportInfo.getUsedName(undefined, runtime); + if (usedName) { + const finalName = getFinalName( + moduleGraph, + info, + [exportInfo.name], + moduleToInfoMap, + runtime, + requestShortener, + runtimeTemplate, + neededNamespaceObjects, + false, + undefined, + info.module.buildMeta.strictHarmonyModule, + true + ); + nsObj.push( + `\n ${JSON.stringify( + usedName + )}: ${runtimeTemplate.returningFunction(finalName)}` + ); + } + } + const name = info.namespaceObjectName; + const defineGetters = + nsObj.length > 0 + ? `${RuntimeGlobals.definePropertyGetters}(${name}, {${nsObj.join( + "," + )}\n});\n` + : ""; + if (nsObj.length > 0) + runtimeRequirements.add(RuntimeGlobals.definePropertyGetters); + namespaceObjectSources.set( + info, + ` +// NAMESPACE OBJECT: ${info.module.readableIdentifier(requestShortener)} +var ${name} = {}; +${RuntimeGlobals.makeNamespaceObject}(${name}); +${defineGetters}` + ); + runtimeRequirements.add(RuntimeGlobals.makeNamespaceObject); } - } - return result; -}; -/** - * @param {SplitChunksSizes} sizes the sizes - * @param {SplitChunksSizes} minSize the min sizes - * @returns {boolean} true if there are sizes and all existing sizes are at least `minSize` - */ -const checkMinSize = (sizes, minSize) => { - for (const key of Object.keys(minSize)) { - const size = sizes[key]; - if (size === undefined || size === 0) continue; - if (size < minSize[key]) return false; - } - return true; -}; + // define required namespace objects (must be before evaluation modules) + for (const info of modulesWithInfo) { + if (info.type === "concatenated") { + const source = namespaceObjectSources.get(info); + if (!source) continue; + result.add(source); + } + } -/** - * @param {SplitChunksSizes} sizes the sizes - * @param {SplitChunksSizes} minSizeReduction the min sizes - * @param {number} chunkCount number of chunks - * @returns {boolean} true if there are sizes and all existing sizes are at least `minSizeReduction` - */ -const checkMinSizeReduction = (sizes, minSizeReduction, chunkCount) => { - for (const key of Object.keys(minSizeReduction)) { - const size = sizes[key]; - if (size === undefined || size === 0) continue; - if (size * chunkCount < minSizeReduction[key]) return false; - } - return true; -}; + const chunkInitFragments = []; -/** - * @param {SplitChunksSizes} sizes the sizes - * @param {SplitChunksSizes} minSize the min sizes - * @returns {undefined | string[]} list of size types that are below min size - */ -const getViolatingMinSizes = (sizes, minSize) => { - let list; - for (const key of Object.keys(minSize)) { - const size = sizes[key]; - if (size === undefined || size === 0) continue; - if (size < minSize[key]) { - if (list === undefined) list = [key]; - else list.push(key); + // evaluate modules in order + for (const rawInfo of modulesWithInfo) { + let name; + let isConditional = false; + const info = rawInfo.type === "reference" ? rawInfo.target : rawInfo; + switch (info.type) { + case "concatenated": { + result.add( + `\n;// CONCATENATED MODULE: ${info.module.readableIdentifier( + requestShortener + )}\n` + ); + result.add(info.source); + if (info.chunkInitFragments) { + for (const f of info.chunkInitFragments) chunkInitFragments.push(f); + } + if (info.runtimeRequirements) { + for (const r of info.runtimeRequirements) { + runtimeRequirements.add(r); + } + } + name = info.namespaceObjectName; + break; + } + case "external": { + result.add( + `\n// EXTERNAL MODULE: ${info.module.readableIdentifier( + requestShortener + )}\n` + ); + runtimeRequirements.add(RuntimeGlobals.require); + const { runtimeCondition } = + /** @type {ExternalModuleInfo | ReferenceToModuleInfo} */ (rawInfo); + const condition = runtimeTemplate.runtimeConditionExpression({ + chunkGraph, + runtimeCondition, + runtime, + runtimeRequirements + }); + if (condition !== "true") { + isConditional = true; + result.add(`if (${condition}) {\n`); + } + result.add( + `var ${info.name} = __webpack_require__(${JSON.stringify( + chunkGraph.getModuleId(info.module) + )});` + ); + name = info.name; + break; + } + default: + // @ts-expect-error never is expected here + throw new Error(`Unsupported concatenation entry type ${info.type}`); + } + if (info.interopNamespaceObjectUsed) { + runtimeRequirements.add(RuntimeGlobals.createFakeNamespaceObject); + result.add( + `\nvar ${info.interopNamespaceObjectName} = /*#__PURE__*/${RuntimeGlobals.createFakeNamespaceObject}(${name}, 2);` + ); + } + if (info.interopNamespaceObject2Used) { + runtimeRequirements.add(RuntimeGlobals.createFakeNamespaceObject); + result.add( + `\nvar ${info.interopNamespaceObject2Name} = /*#__PURE__*/${RuntimeGlobals.createFakeNamespaceObject}(${name});` + ); + } + if (info.interopDefaultAccessUsed) { + runtimeRequirements.add(RuntimeGlobals.compatGetDefaultExport); + result.add( + `\nvar ${info.interopDefaultAccessName} = /*#__PURE__*/${RuntimeGlobals.compatGetDefaultExport}(${name});` + ); + } + if (isConditional) { + result.add("\n}"); + } } - } - return list; -}; -/** - * @param {SplitChunksSizes} sizes the sizes - * @returns {number} the total size - */ -const totalSize = sizes => { - let size = 0; - for (const key of Object.keys(sizes)) { - size += sizes[key]; - } - return size; -}; + const data = new Map(); + if (chunkInitFragments.length > 0) + data.set("chunkInitFragments", chunkInitFragments); -/** - * @param {false|string|Function} name the chunk name - * @returns {GetName} a function to get the name of the chunk - */ -const normalizeName = name => { - if (typeof name === "string") { - return () => name; - } - if (typeof name === "function") { - return /** @type {GetName} */ (name); - } -}; + /** @type {CodeGenerationResult} */ + const resultEntry = { + sources: new Map([["javascript", new CachedSource(result)]]), + data, + runtimeRequirements + }; -/** - * @param {OptimizationSplitChunksCacheGroup["chunks"]} chunks the chunk filter option - * @returns {ChunkFilterFunction} the chunk filter function - */ -const normalizeChunksFilter = chunks => { - if (chunks === "initial") { - return INITIAL_CHUNK_FILTER; - } - if (chunks === "async") { - return ASYNC_CHUNK_FILTER; - } - if (chunks === "all") { - return ALL_CHUNK_FILTER; - } - if (typeof chunks === "function") { - return chunks; + return resultEntry; } -}; -/** - * @param {GetCacheGroups | Record} cacheGroups the cache group options - * @param {string[]} defaultSizeTypes the default size types - * @returns {GetCacheGroups} a function to get the cache groups - */ -const normalizeCacheGroups = (cacheGroups, defaultSizeTypes) => { - if (typeof cacheGroups === "function") { - return cacheGroups; - } - if (typeof cacheGroups === "object" && cacheGroups !== null) { - /** @type {(function(Module, CacheGroupsContext, CacheGroupSource[]): void)[]} */ - const handlers = []; - for (const key of Object.keys(cacheGroups)) { - const option = cacheGroups[key]; - if (option === false) { - continue; - } - if (typeof option === "string" || option instanceof RegExp) { - const source = createCacheGroupSource({}, key, defaultSizeTypes); - handlers.push((module, context, results) => { - if (checkTest(option, module, context)) { - results.push(source); - } - }); - } else if (typeof option === "function") { - const cache = new WeakMap(); - handlers.push((module, context, results) => { - const result = option(module); - if (result) { - const groups = Array.isArray(result) ? result : [result]; - for (const group of groups) { - const cachedSource = cache.get(group); - if (cachedSource !== undefined) { - results.push(cachedSource); - } else { - const source = createCacheGroupSource( - group, - key, - defaultSizeTypes - ); - cache.set(group, source); - results.push(source); - } - } - } + /** + * @param {Map} modulesMap modulesMap + * @param {ModuleInfo} info info + * @param {DependencyTemplates} dependencyTemplates dependencyTemplates + * @param {RuntimeTemplate} runtimeTemplate runtimeTemplate + * @param {ModuleGraph} moduleGraph moduleGraph + * @param {ChunkGraph} chunkGraph chunkGraph + * @param {RuntimeSpec} runtime runtime + */ + _analyseModule( + modulesMap, + info, + dependencyTemplates, + runtimeTemplate, + moduleGraph, + chunkGraph, + runtime + ) { + if (info.type === "concatenated") { + const m = info.module; + try { + // Create a concatenation scope to track and capture information + const concatenationScope = new ConcatenationScope(modulesMap, info); + + // TODO cache codeGeneration results + const codeGenResult = m.codeGeneration({ + dependencyTemplates, + runtimeTemplate, + moduleGraph, + chunkGraph, + runtime, + concatenationScope }); - } else { - const source = createCacheGroupSource(option, key, defaultSizeTypes); - handlers.push((module, context, results) => { + const source = codeGenResult.sources.get("javascript"); + const data = codeGenResult.data; + const chunkInitFragments = data && data.get("chunkInitFragments"); + const code = source.source().toString(); + let ast; + try { + ast = JavascriptParser._parse(code, { + sourceType: "module" + }); + } catch (err) { if ( - checkTest(option.test, module, context) && - checkModuleType(option.type, module) && - checkModuleLayer(option.layer, module) + err.loc && + typeof err.loc === "object" && + typeof err.loc.line === "number" ) { - results.push(source); + const lineNumber = err.loc.line; + const lines = code.split("\n"); + err.message += + "\n| " + + lines + .slice(Math.max(0, lineNumber - 3), lineNumber + 2) + .join("\n| "); } + throw err; + } + const scopeManager = eslintScope.analyze(ast, { + ecmaVersion: 6, + sourceType: "module", + optimistic: true, + ignoreEval: true, + impliedStrict: true }); + const globalScope = scopeManager.acquire(ast); + const moduleScope = globalScope.childScopes[0]; + const resultSource = new ReplaceSource(source); + info.runtimeRequirements = codeGenResult.runtimeRequirements; + info.ast = ast; + info.internalSource = source; + info.source = resultSource; + info.chunkInitFragments = chunkInitFragments; + info.globalScope = globalScope; + info.moduleScope = moduleScope; + } catch (err) { + err.message += `\nwhile analysing module ${m.identifier()} for concatenation`; + throw err; } } - /** - * @param {Module} module the current module - * @param {CacheGroupsContext} context the current context - * @returns {CacheGroupSource[]} the matching cache groups - */ - const fn = (module, context) => { - /** @type {CacheGroupSource[]} */ - let results = []; - for (const fn of handlers) { - fn(module, context, results); - } - return results; - }; - return fn; - } - return () => null; -}; - -/** - * @param {undefined|boolean|string|RegExp|Function} test test option - * @param {Module} module the module - * @param {CacheGroupsContext} context context object - * @returns {boolean} true, if the module should be selected - */ -const checkTest = (test, module, context) => { - if (test === undefined) return true; - if (typeof test === "function") { - return test(module, context); } - if (typeof test === "boolean") return test; - if (typeof test === "string") { - const name = module.nameForCondition(); - return name && name.startsWith(test); - } - if (test instanceof RegExp) { - const name = module.nameForCondition(); - return name && test.test(name); - } - return false; -}; - -/** - * @param {undefined|string|RegExp|Function} test type option - * @param {Module} module the module - * @returns {boolean} true, if the module should be selected - */ -const checkModuleType = (test, module) => { - if (test === undefined) return true; - if (typeof test === "function") { - return test(module.type); - } - if (typeof test === "string") { - const type = module.type; - return test === type; - } - if (test instanceof RegExp) { - const type = module.type; - return test.test(type); - } - return false; -}; - -/** - * @param {undefined|string|RegExp|Function} test type option - * @param {Module} module the module - * @returns {boolean} true, if the module should be selected - */ -const checkModuleLayer = (test, module) => { - if (test === undefined) return true; - if (typeof test === "function") { - return test(module.layer); - } - if (typeof test === "string") { - const layer = module.layer; - return test === "" ? !layer : layer && layer.startsWith(test); - } - if (test instanceof RegExp) { - const layer = module.layer; - return test.test(layer); - } - return false; -}; - -/** - * @param {OptimizationSplitChunksCacheGroup} options the group options - * @param {string} key key of cache group - * @param {string[]} defaultSizeTypes the default size types - * @returns {CacheGroupSource} the normalized cached group - */ -const createCacheGroupSource = (options, key, defaultSizeTypes) => { - const minSize = normalizeSizes(options.minSize, defaultSizeTypes); - const minSizeReduction = normalizeSizes( - options.minSizeReduction, - defaultSizeTypes - ); - const maxSize = normalizeSizes(options.maxSize, defaultSizeTypes); - return { - key, - priority: options.priority, - getName: normalizeName(options.name), - chunksFilter: normalizeChunksFilter(options.chunks), - enforce: options.enforce, - minSize, - minSizeReduction, - minRemainingSize: mergeSizes( - normalizeSizes(options.minRemainingSize, defaultSizeTypes), - minSize - ), - enforceSizeThreshold: normalizeSizes( - options.enforceSizeThreshold, - defaultSizeTypes - ), - maxAsyncSize: mergeSizes( - normalizeSizes(options.maxAsyncSize, defaultSizeTypes), - maxSize - ), - maxInitialSize: mergeSizes( - normalizeSizes(options.maxInitialSize, defaultSizeTypes), - maxSize - ), - minChunks: options.minChunks, - maxAsyncRequests: options.maxAsyncRequests, - maxInitialRequests: options.maxInitialRequests, - filename: options.filename, - idHint: options.idHint, - automaticNameDelimiter: options.automaticNameDelimiter, - reuseExistingChunk: options.reuseExistingChunk, - usedExports: options.usedExports - }; -}; -module.exports = class SplitChunksPlugin { /** - * @param {OptimizationSplitChunksOptions=} options plugin options + * @param {ModuleGraph} moduleGraph the module graph + * @param {RuntimeSpec} runtime the runtime + * @returns {[ModuleInfoOrReference[], Map]} module info items */ - constructor(options = {}) { - const defaultSizeTypes = options.defaultSizeTypes || [ - "javascript", - "unknown" - ]; - const fallbackCacheGroup = options.fallbackCacheGroup || {}; - const minSize = normalizeSizes(options.minSize, defaultSizeTypes); - const minSizeReduction = normalizeSizes( - options.minSizeReduction, - defaultSizeTypes + _getModulesWithInfo(moduleGraph, runtime) { + const orderedConcatenationList = this._createConcatenationList( + this.rootModule, + this._modules, + runtime, + moduleGraph ); - const maxSize = normalizeSizes(options.maxSize, defaultSizeTypes); - - /** @type {SplitChunksOptions} */ - this.options = { - chunksFilter: normalizeChunksFilter(options.chunks || "all"), - defaultSizeTypes, - minSize, - minSizeReduction, - minRemainingSize: mergeSizes( - normalizeSizes(options.minRemainingSize, defaultSizeTypes), - minSize - ), - enforceSizeThreshold: normalizeSizes( - options.enforceSizeThreshold, - defaultSizeTypes - ), - maxAsyncSize: mergeSizes( - normalizeSizes(options.maxAsyncSize, defaultSizeTypes), - maxSize - ), - maxInitialSize: mergeSizes( - normalizeSizes(options.maxInitialSize, defaultSizeTypes), - maxSize - ), - minChunks: options.minChunks || 1, - maxAsyncRequests: options.maxAsyncRequests || 1, - maxInitialRequests: options.maxInitialRequests || 1, - hidePathInfo: options.hidePathInfo || false, - filename: options.filename || undefined, - getCacheGroups: normalizeCacheGroups( - options.cacheGroups, - defaultSizeTypes - ), - getName: options.name ? normalizeName(options.name) : defaultGetName, - automaticNameDelimiter: options.automaticNameDelimiter, - usedExports: options.usedExports, - fallbackCacheGroup: { - chunksFilter: normalizeChunksFilter( - fallbackCacheGroup.chunks || options.chunks || "all" - ), - minSize: mergeSizes( - normalizeSizes(fallbackCacheGroup.minSize, defaultSizeTypes), - minSize - ), - maxAsyncSize: mergeSizes( - normalizeSizes(fallbackCacheGroup.maxAsyncSize, defaultSizeTypes), - normalizeSizes(fallbackCacheGroup.maxSize, defaultSizeTypes), - normalizeSizes(options.maxAsyncSize, defaultSizeTypes), - normalizeSizes(options.maxSize, defaultSizeTypes) - ), - maxInitialSize: mergeSizes( - normalizeSizes(fallbackCacheGroup.maxInitialSize, defaultSizeTypes), - normalizeSizes(fallbackCacheGroup.maxSize, defaultSizeTypes), - normalizeSizes(options.maxInitialSize, defaultSizeTypes), - normalizeSizes(options.maxSize, defaultSizeTypes) - ), - automaticNameDelimiter: - fallbackCacheGroup.automaticNameDelimiter || - options.automaticNameDelimiter || - "~" + /** @type {Map} */ + const map = new Map(); + const list = orderedConcatenationList.map((info, index) => { + let item = map.get(info.module); + if (item === undefined) { + switch (info.type) { + case "concatenated": + item = { + type: "concatenated", + module: info.module, + index, + ast: undefined, + internalSource: undefined, + runtimeRequirements: undefined, + source: undefined, + globalScope: undefined, + moduleScope: undefined, + internalNames: new Map(), + exportMap: undefined, + rawExportMap: undefined, + namespaceExportSymbol: undefined, + namespaceObjectName: undefined, + interopNamespaceObjectUsed: false, + interopNamespaceObjectName: undefined, + interopNamespaceObject2Used: false, + interopNamespaceObject2Name: undefined, + interopDefaultAccessUsed: false, + interopDefaultAccessName: undefined + }; + break; + case "external": + item = { + type: "external", + module: info.module, + runtimeCondition: info.runtimeCondition, + index, + name: undefined, + interopNamespaceObjectUsed: false, + interopNamespaceObjectName: undefined, + interopNamespaceObject2Used: false, + interopNamespaceObject2Name: undefined, + interopDefaultAccessUsed: false, + interopDefaultAccessName: undefined + }; + break; + default: + throw new Error( + `Unsupported concatenation entry type ${info.type}` + ); + } + map.set(item.module, item); + return item; + } else { + /** @type {ReferenceToModuleInfo} */ + const ref = { + type: "reference", + runtimeCondition: info.runtimeCondition, + target: item + }; + return ref; } - }; - - /** @type {WeakMap} */ - this._cacheGroupCache = new WeakMap(); + }); + return [list, map]; } - /** - * @param {CacheGroupSource} cacheGroupSource source - * @returns {CacheGroup} the cache group (cached) - */ - _getCacheGroup(cacheGroupSource) { - const cacheEntry = this._cacheGroupCache.get(cacheGroupSource); - if (cacheEntry !== undefined) return cacheEntry; - const minSize = mergeSizes( - cacheGroupSource.minSize, - cacheGroupSource.enforce ? undefined : this.options.minSize - ); - const minSizeReduction = mergeSizes( - cacheGroupSource.minSizeReduction, - cacheGroupSource.enforce ? undefined : this.options.minSizeReduction - ); - const minRemainingSize = mergeSizes( - cacheGroupSource.minRemainingSize, - cacheGroupSource.enforce ? undefined : this.options.minRemainingSize - ); - const enforceSizeThreshold = mergeSizes( - cacheGroupSource.enforceSizeThreshold, - cacheGroupSource.enforce ? undefined : this.options.enforceSizeThreshold + findNewName(oldName, usedNamed1, usedNamed2, extraInfo) { + let name = oldName; + + if (name === ConcatenationScope.DEFAULT_EXPORT) { + name = ""; + } + if (name === ConcatenationScope.NAMESPACE_OBJECT_EXPORT) { + name = "namespaceObject"; + } + + // Remove uncool stuff + extraInfo = extraInfo.replace( + /\.+\/|(\/index)?\.([a-zA-Z0-9]{1,4})($|\s|\?)|\s*\+\s*\d+\s*modules/g, + "" ); - const cacheGroup = { - key: cacheGroupSource.key, - priority: cacheGroupSource.priority || 0, - chunksFilter: cacheGroupSource.chunksFilter || this.options.chunksFilter, - minSize, - minSizeReduction, - minRemainingSize, - enforceSizeThreshold, - maxAsyncSize: mergeSizes( - cacheGroupSource.maxAsyncSize, - cacheGroupSource.enforce ? undefined : this.options.maxAsyncSize - ), - maxInitialSize: mergeSizes( - cacheGroupSource.maxInitialSize, - cacheGroupSource.enforce ? undefined : this.options.maxInitialSize - ), - minChunks: - cacheGroupSource.minChunks !== undefined - ? cacheGroupSource.minChunks - : cacheGroupSource.enforce - ? 1 - : this.options.minChunks, - maxAsyncRequests: - cacheGroupSource.maxAsyncRequests !== undefined - ? cacheGroupSource.maxAsyncRequests - : cacheGroupSource.enforce - ? Infinity - : this.options.maxAsyncRequests, - maxInitialRequests: - cacheGroupSource.maxInitialRequests !== undefined - ? cacheGroupSource.maxInitialRequests - : cacheGroupSource.enforce - ? Infinity - : this.options.maxInitialRequests, - getName: - cacheGroupSource.getName !== undefined - ? cacheGroupSource.getName - : this.options.getName, - usedExports: - cacheGroupSource.usedExports !== undefined - ? cacheGroupSource.usedExports - : this.options.usedExports, - filename: - cacheGroupSource.filename !== undefined - ? cacheGroupSource.filename - : this.options.filename, - automaticNameDelimiter: - cacheGroupSource.automaticNameDelimiter !== undefined - ? cacheGroupSource.automaticNameDelimiter - : this.options.automaticNameDelimiter, - idHint: - cacheGroupSource.idHint !== undefined - ? cacheGroupSource.idHint - : cacheGroupSource.key, - reuseExistingChunk: cacheGroupSource.reuseExistingChunk || false, - _validateSize: hasNonZeroSizes(minSize), - _validateRemainingSize: hasNonZeroSizes(minRemainingSize), - _minSizeForMaxSize: mergeSizes( - cacheGroupSource.minSize, - this.options.minSize - ), - _conditionalEnforce: hasNonZeroSizes(enforceSizeThreshold) - }; - this._cacheGroupCache.set(cacheGroupSource, cacheGroup); - return cacheGroup; + + const splittedInfo = extraInfo.split("/"); + while (splittedInfo.length) { + name = splittedInfo.pop() + (name ? "_" + name : ""); + const nameIdent = Template.toIdentifier(name); + if ( + !usedNamed1.has(nameIdent) && + (!usedNamed2 || !usedNamed2.has(nameIdent)) + ) + return nameIdent; + } + + let i = 0; + let nameWithNumber = Template.toIdentifier(`${name}_${i}`); + while ( + usedNamed1.has(nameWithNumber) || + (usedNamed2 && usedNamed2.has(nameWithNumber)) + ) { + i++; + nameWithNumber = Template.toIdentifier(`${name}_${i}`); + } + return nameWithNumber; } /** - * Apply the plugin - * @param {Compiler} compiler the compiler instance + * @param {Hash} hash the hash used to track dependencies + * @param {UpdateHashContext} context context * @returns {void} */ - apply(compiler) { - const cachedMakePathsRelative = makePathsRelative.bindContextCache( - compiler.context, - compiler.root - ); - compiler.hooks.thisCompilation.tap("SplitChunksPlugin", compilation => { - const logger = compilation.getLogger("webpack.SplitChunksPlugin"); - let alreadyOptimized = false; - compilation.hooks.unseal.tap("SplitChunksPlugin", () => { - alreadyOptimized = false; - }); - compilation.hooks.optimizeChunks.tap( - { - name: "SplitChunksPlugin", - stage: STAGE_ADVANCED - }, - chunks => { - if (alreadyOptimized) return; - alreadyOptimized = true; - logger.time("prepare"); - const chunkGraph = compilation.chunkGraph; - const moduleGraph = compilation.moduleGraph; - // Give each selected chunk an index (to create strings from chunks) - /** @type {Map} */ - const chunkIndexMap = new Map(); - const ZERO = BigInt("0"); - const ONE = BigInt("1"); - const START = ONE << BigInt("31"); - let index = START; - for (const chunk of chunks) { - chunkIndexMap.set( - chunk, - index | BigInt((Math.random() * 0x7fffffff) | 0) - ); - index = index << ONE; - } - /** - * @param {Iterable} chunks list of chunks - * @returns {bigint | Chunk} key of the chunks - */ - const getKey = chunks => { - const iterator = chunks[Symbol.iterator](); - let result = iterator.next(); - if (result.done) return ZERO; - const first = result.value; - result = iterator.next(); - if (result.done) return first; - let key = - chunkIndexMap.get(first) | chunkIndexMap.get(result.value); - while (!(result = iterator.next()).done) { - const raw = chunkIndexMap.get(result.value); - key = key ^ raw; - } - return key; - }; - const keyToString = key => { - if (typeof key === "bigint") return key.toString(16); - return chunkIndexMap.get(key).toString(16); - }; + updateHash(hash, context) { + const { chunkGraph, runtime } = context; + for (const info of this._createConcatenationList( + this.rootModule, + this._modules, + intersectRuntime(runtime, this._runtime), + chunkGraph.moduleGraph + )) { + switch (info.type) { + case "concatenated": + info.module.updateHash(hash, context); + break; + case "external": + hash.update(`${chunkGraph.getModuleId(info.module)}`); + // TODO runtimeCondition + break; + } + } + super.updateHash(hash, context); + } - const getChunkSetsInGraph = memoize(() => { - /** @type {Map>} */ - const chunkSetsInGraph = new Map(); - /** @type {Set} */ - const singleChunkSets = new Set(); - for (const module of compilation.modules) { - const chunks = chunkGraph.getModuleChunksIterable(module); - const chunksKey = getKey(chunks); - if (typeof chunksKey === "bigint") { - if (!chunkSetsInGraph.has(chunksKey)) { - chunkSetsInGraph.set(chunksKey, new Set(chunks)); - } - } else { - singleChunkSets.add(chunksKey); - } - } - return { chunkSetsInGraph, singleChunkSets }; - }); + static deserialize(context) { + const obj = new ConcatenatedModule({ + identifier: undefined, + rootModule: undefined, + modules: undefined, + runtime: undefined + }); + obj.deserialize(context); + return obj; + } +} - /** - * @param {Module} module the module - * @returns {Iterable} groups of chunks with equal exports - */ - const groupChunksByExports = module => { - const exportsInfo = moduleGraph.getExportsInfo(module); - const groupedByUsedExports = new Map(); - for (const chunk of chunkGraph.getModuleChunksIterable(module)) { - const key = exportsInfo.getUsageKey(chunk.runtime); - const list = groupedByUsedExports.get(key); - if (list !== undefined) { - list.push(chunk); - } else { - groupedByUsedExports.set(key, [chunk]); - } - } - return groupedByUsedExports.values(); - }; +makeSerializable(ConcatenatedModule, "webpack/lib/optimize/ConcatenatedModule"); - /** @type {Map>} */ - const groupedByExportsMap = new Map(); +module.exports = ConcatenatedModule; - const getExportsChunkSetsInGraph = memoize(() => { - /** @type {Map>} */ - const chunkSetsInGraph = new Map(); - /** @type {Set} */ - const singleChunkSets = new Set(); - for (const module of compilation.modules) { - const groupedChunks = Array.from(groupChunksByExports(module)); - groupedByExportsMap.set(module, groupedChunks); - for (const chunks of groupedChunks) { - if (chunks.length === 1) { - singleChunkSets.add(chunks[0]); - } else { - const chunksKey = /** @type {bigint} */ (getKey(chunks)); - if (!chunkSetsInGraph.has(chunksKey)) { - chunkSetsInGraph.set(chunksKey, new Set(chunks)); - } - } - } - } - return { chunkSetsInGraph, singleChunkSets }; - }); - // group these set of chunks by count - // to allow to check less sets via isSubset - // (only smaller sets can be subset) - const groupChunkSetsByCount = chunkSets => { - /** @type {Map>>} */ - const chunkSetsByCount = new Map(); - for (const chunksSet of chunkSets) { - const count = chunksSet.size; - let array = chunkSetsByCount.get(count); - if (array === undefined) { - array = []; - chunkSetsByCount.set(count, array); - } - array.push(chunksSet); - } - return chunkSetsByCount; - }; - const getChunkSetsByCount = memoize(() => - groupChunkSetsByCount( - getChunkSetsInGraph().chunkSetsInGraph.values() - ) - ); - const getExportsChunkSetsByCount = memoize(() => - groupChunkSetsByCount( - getExportsChunkSetsInGraph().chunkSetsInGraph.values() - ) - ); +/***/ }), - // Create a list of possible combinations - const createGetCombinations = ( - chunkSets, - singleChunkSets, - chunkSetsByCount - ) => { - /** @type {Map | Chunk)[]>} */ - const combinationsCache = new Map(); +/***/ 91120: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - return key => { - const cacheEntry = combinationsCache.get(key); - if (cacheEntry !== undefined) return cacheEntry; - if (key instanceof Chunk) { - const result = [key]; - combinationsCache.set(key, result); - return result; - } - const chunksSet = chunkSets.get(key); - /** @type {(Set | Chunk)[]} */ - const array = [chunksSet]; - for (const [count, setArray] of chunkSetsByCount) { - // "equal" is not needed because they would have been merge in the first step - if (count < chunksSet.size) { - for (const set of setArray) { - if (isSubset(chunksSet, set)) { - array.push(set); - } - } - } - } - for (const chunk of singleChunkSets) { - if (chunksSet.has(chunk)) { - array.push(chunk); - } - } - combinationsCache.set(key, array); - return array; - }; - }; +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ - const getCombinationsFactory = memoize(() => { - const { chunkSetsInGraph, singleChunkSets } = getChunkSetsInGraph(); - return createGetCombinations( - chunkSetsInGraph, - singleChunkSets, - getChunkSetsByCount() - ); - }); - const getCombinations = key => getCombinationsFactory()(key); - const getExportsCombinationsFactory = memoize(() => { - const { chunkSetsInGraph, singleChunkSets } = - getExportsChunkSetsInGraph(); - return createGetCombinations( - chunkSetsInGraph, - singleChunkSets, - getExportsChunkSetsByCount() - ); - }); - const getExportsCombinations = key => - getExportsCombinationsFactory()(key); - /** - * @typedef {Object} SelectedChunksResult - * @property {Chunk[]} chunks the list of chunks - * @property {bigint | Chunk} key a key of the list - */ +const { STAGE_BASIC } = __webpack_require__(68145); - /** @type {WeakMap | Chunk, WeakMap>} */ - const selectedChunksCacheByChunksSet = new WeakMap(); +/** @typedef {import("../Chunk")} Chunk */ +/** @typedef {import("../ChunkGroup")} ChunkGroup */ +/** @typedef {import("../Compiler")} Compiler */ - /** - * get list and key by applying the filter function to the list - * It is cached for performance reasons - * @param {Set | Chunk} chunks list of chunks - * @param {ChunkFilterFunction} chunkFilter filter function for chunks - * @returns {SelectedChunksResult} list and key - */ - const getSelectedChunks = (chunks, chunkFilter) => { - let entry = selectedChunksCacheByChunksSet.get(chunks); - if (entry === undefined) { - entry = new WeakMap(); - selectedChunksCacheByChunksSet.set(chunks, entry); - } - /** @type {SelectedChunksResult} */ - let entry2 = entry.get(chunkFilter); - if (entry2 === undefined) { - /** @type {Chunk[]} */ - const selectedChunks = []; - if (chunks instanceof Chunk) { - if (chunkFilter(chunks)) selectedChunks.push(chunks); - } else { - for (const chunk of chunks) { - if (chunkFilter(chunk)) selectedChunks.push(chunk); +class EnsureChunkConditionsPlugin { + /** + * Apply the plugin + * @param {Compiler} compiler the compiler instance + * @returns {void} + */ + apply(compiler) { + compiler.hooks.compilation.tap( + "EnsureChunkConditionsPlugin", + compilation => { + const handler = chunks => { + const chunkGraph = compilation.chunkGraph; + // These sets are hoisted here to save memory + // They are cleared at the end of every loop + /** @type {Set} */ + const sourceChunks = new Set(); + /** @type {Set} */ + const chunkGroups = new Set(); + for (const module of compilation.modules) { + if (!module.hasChunkCondition()) continue; + for (const chunk of chunkGraph.getModuleChunksIterable(module)) { + if (!module.chunkCondition(chunk, compilation)) { + sourceChunks.add(chunk); + for (const group of chunk.groupsIterable) { + chunkGroups.add(group); } } - entry2 = { - chunks: selectedChunks, - key: getKey(selectedChunks) - }; - entry.set(chunkFilter, entry2); } - return entry2; - }; - - /** @type {Map} */ - const alreadyValidatedParents = new Map(); - /** @type {Set} */ - const alreadyReportedErrors = new Set(); - - // Map a list of chunks to a list of modules - // For the key the chunk "index" is used, the value is a SortableSet of modules - /** @type {Map} */ - const chunksInfoMap = new Map(); - - /** - * @param {CacheGroup} cacheGroup the current cache group - * @param {number} cacheGroupIndex the index of the cache group of ordering - * @param {Chunk[]} selectedChunks chunks selected for this module - * @param {bigint | Chunk} selectedChunksKey a key of selectedChunks - * @param {Module} module the current module - * @returns {void} - */ - const addModuleToChunksInfoMap = ( - cacheGroup, - cacheGroupIndex, - selectedChunks, - selectedChunksKey, - module - ) => { - // Break if minimum number of chunks is not reached - if (selectedChunks.length < cacheGroup.minChunks) return; - // Determine name for split chunk - const name = cacheGroup.getName( - module, - selectedChunks, - cacheGroup.key - ); - // Check if the name is ok - const existingChunk = compilation.namedChunks.get(name); - if (existingChunk) { - const parentValidationKey = `${name}|${ - typeof selectedChunksKey === "bigint" - ? selectedChunksKey - : selectedChunksKey.debugId - }`; - const valid = alreadyValidatedParents.get(parentValidationKey); - if (valid === false) return; - if (valid === undefined) { - // Module can only be moved into the existing chunk if the existing chunk - // is a parent of all selected chunks - let isInAllParents = true; - /** @type {Set} */ - const queue = new Set(); - for (const chunk of selectedChunks) { - for (const group of chunk.groupsIterable) { - queue.add(group); - } - } - for (const group of queue) { - if (existingChunk.isInGroup(group)) continue; - let hasParent = false; - for (const parent of group.parentsIterable) { - hasParent = true; - queue.add(parent); - } - if (!hasParent) { - isInAllParents = false; - } - } - const valid = isInAllParents; - alreadyValidatedParents.set(parentValidationKey, valid); - if (!valid) { - if (!alreadyReportedErrors.has(name)) { - alreadyReportedErrors.add(name); - compilation.errors.push( - new WebpackError( - "SplitChunksPlugin\n" + - `Cache group "${cacheGroup.key}" conflicts with existing chunk.\n` + - `Both have the same name "${name}" and existing chunk is not a parent of the selected modules.\n` + - "Use a different name for the cache group or make sure that the existing chunk is a parent (e. g. via dependOn).\n" + - 'HINT: You can omit "name" to automatically create a name.\n' + - "BREAKING CHANGE: webpack < 5 used to allow to use an entrypoint as splitChunk. " + - "This is no longer allowed when the entrypoint is not a parent of the selected modules.\n" + - "Remove this entrypoint and add modules to cache group's 'test' instead. " + - "If you need modules to be evaluated on startup, add them to the existing entrypoints (make them arrays). " + - "See migration guide of more info." - ) - ); - } - return; + if (sourceChunks.size === 0) continue; + /** @type {Set} */ + const targetChunks = new Set(); + chunkGroupLoop: for (const chunkGroup of chunkGroups) { + // Can module be placed in a chunk of this group? + for (const chunk of chunkGroup.chunks) { + if (module.chunkCondition(chunk, compilation)) { + targetChunks.add(chunk); + continue chunkGroupLoop; } } - } - // Create key for maps - // When it has a name we use the name as key - // Otherwise we create the key from chunks and cache group key - // This automatically merges equal names - const key = - cacheGroup.key + - (name - ? ` name:${name}` - : ` chunks:${keyToString(selectedChunksKey)}`); - // Add module to maps - let info = chunksInfoMap.get(key); - if (info === undefined) { - chunksInfoMap.set( - key, - (info = { - modules: new SortableSet( - undefined, - compareModulesByIdentifier - ), - cacheGroup, - cacheGroupIndex, - name, - sizes: {}, - chunks: new Set(), - reuseableChunks: new Set(), - chunksKeys: new Set() - }) - ); - } - const oldSize = info.modules.size; - info.modules.add(module); - if (info.modules.size !== oldSize) { - for (const type of module.getSourceTypes()) { - info.sizes[type] = (info.sizes[type] || 0) + module.size(type); + // We reached the entrypoint: fail + if (chunkGroup.isInitial()) { + throw new Error( + "Cannot fullfil chunk condition of " + module.identifier() + ); } - } - const oldChunksKeysSize = info.chunksKeys.size; - info.chunksKeys.add(selectedChunksKey); - if (oldChunksKeysSize !== info.chunksKeys.size) { - for (const chunk of selectedChunks) { - info.chunks.add(chunk); + // Try placing in all parents + for (const group of chunkGroup.parentsIterable) { + chunkGroups.add(group); } } - }; + for (const sourceChunk of sourceChunks) { + chunkGraph.disconnectChunkAndModule(sourceChunk, module); + } + for (const targetChunk of targetChunks) { + chunkGraph.connectChunkAndModule(targetChunk, module); + } + sourceChunks.clear(); + chunkGroups.clear(); + } + }; + compilation.hooks.optimizeChunks.tap( + { + name: "EnsureChunkConditionsPlugin", + stage: STAGE_BASIC + }, + handler + ); + } + ); + } +} +module.exports = EnsureChunkConditionsPlugin; - const context = { - moduleGraph, - chunkGraph - }; - logger.timeEnd("prepare"); +/***/ }), - logger.time("modules"); +/***/ 48424: +/***/ (function(module) { - // Walk through all modules +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ + + + +/** @typedef {import("../Chunk")} Chunk */ +/** @typedef {import("../Compiler")} Compiler */ +/** @typedef {import("../Module")} Module */ + +class FlagIncludedChunksPlugin { + /** + * Apply the plugin + * @param {Compiler} compiler the compiler instance + * @returns {void} + */ + apply(compiler) { + compiler.hooks.compilation.tap("FlagIncludedChunksPlugin", compilation => { + compilation.hooks.optimizeChunkIds.tap( + "FlagIncludedChunksPlugin", + chunks => { + const chunkGraph = compilation.chunkGraph; + + // prepare two bit integers for each module + // 2^31 is the max number represented as SMI in v8 + // we want the bits distributed this way: + // the bit 2^31 is pretty rar and only one module should get it + // so it has a probability of 1 / modulesCount + // the first bit (2^0) is the easiest and every module could get it + // if it doesn't get a better bit + // from bit 2^n to 2^(n+1) there is a probability of p + // so 1 / modulesCount == p^31 + // <=> p = sqrt31(1 / modulesCount) + // so we use a modulo of 1 / sqrt31(1 / modulesCount) + /** @type {WeakMap} */ + const moduleBits = new WeakMap(); + const modulesCount = compilation.modules.size; + + // precalculate the modulo values for each bit + const modulo = 1 / Math.pow(1 / modulesCount, 1 / 31); + const modulos = Array.from( + { length: 31 }, + (x, i) => Math.pow(modulo, i) | 0 + ); + + // iterate all modules to generate bit values + let i = 0; for (const module of compilation.modules) { - // Get cache group - let cacheGroups = this.options.getCacheGroups(module, context); - if (!Array.isArray(cacheGroups) || cacheGroups.length === 0) { - continue; + let bit = 30; + while (i % modulos[bit] !== 0) { + bit--; } + moduleBits.set(module, 1 << bit); + i++; + } - // Prepare some values (usedExports = false) - const getCombs = memoize(() => { - const chunks = chunkGraph.getModuleChunksIterable(module); - const chunksKey = getKey(chunks); - return getCombinations(chunksKey); - }); + // iterate all chunks to generate bitmaps + /** @type {WeakMap} */ + const chunkModulesHash = new WeakMap(); + for (const chunk of chunks) { + let hash = 0; + for (const module of chunkGraph.getChunkModulesIterable(chunk)) { + hash |= moduleBits.get(module); + } + chunkModulesHash.set(chunk, hash); + } + + for (const chunkA of chunks) { + const chunkAHash = chunkModulesHash.get(chunkA); + const chunkAModulesCount = + chunkGraph.getNumberOfChunkModules(chunkA); + if (chunkAModulesCount === 0) continue; + let bestModule = undefined; + for (const module of chunkGraph.getChunkModulesIterable(chunkA)) { + if ( + bestModule === undefined || + chunkGraph.getNumberOfModuleChunks(bestModule) > + chunkGraph.getNumberOfModuleChunks(module) + ) + bestModule = module; + } + loopB: for (const chunkB of chunkGraph.getModuleChunksIterable( + bestModule + )) { + // as we iterate the same iterables twice + // skip if we find ourselves + if (chunkA === chunkB) continue; + + const chunkBModulesCount = + chunkGraph.getNumberOfChunkModules(chunkB); - // Prepare some values (usedExports = true) - const getCombsByUsedExports = memoize(() => { - // fill the groupedByExportsMap - getExportsChunkSetsInGraph(); - /** @type {Set | Chunk>} */ - const set = new Set(); - const groupedByUsedExports = groupedByExportsMap.get(module); - for (const chunks of groupedByUsedExports) { - const chunksKey = getKey(chunks); - for (const comb of getExportsCombinations(chunksKey)) - set.add(comb); - } - return set; - }); + // ids for empty chunks are not included + if (chunkBModulesCount === 0) continue; - let cacheGroupIndex = 0; - for (const cacheGroupSource of cacheGroups) { - const cacheGroup = this._getCacheGroup(cacheGroupSource); + // instead of swapping A and B just bail + // as we loop twice the current A will be B and B then A + if (chunkAModulesCount > chunkBModulesCount) continue; - const combs = cacheGroup.usedExports - ? getCombsByUsedExports() - : getCombs(); - // For all combination of chunk selection - for (const chunkCombination of combs) { - // Break if minimum number of chunks is not reached - const count = - chunkCombination instanceof Chunk ? 1 : chunkCombination.size; - if (count < cacheGroup.minChunks) continue; - // Select chunks by configuration - const { chunks: selectedChunks, key: selectedChunksKey } = - getSelectedChunks(chunkCombination, cacheGroup.chunksFilter); + // is chunkA in chunkB? - addModuleToChunksInfoMap( - cacheGroup, - cacheGroupIndex, - selectedChunks, - selectedChunksKey, - module - ); + // we do a cheap check for the hash value + const chunkBHash = chunkModulesHash.get(chunkB); + if ((chunkBHash & chunkAHash) !== chunkAHash) continue; + + // compare all modules + for (const m of chunkGraph.getChunkModulesIterable(chunkA)) { + if (!chunkGraph.isModuleInChunk(m, chunkB)) continue loopB; } - cacheGroupIndex++; + chunkB.ids.push(chunkA.id); } } + } + ); + }); + } +} +module.exports = FlagIncludedChunksPlugin; - logger.timeEnd("modules"); - logger.time("queue"); +/***/ }), - /** - * @param {ChunksInfoItem} info entry - * @param {string[]} sourceTypes source types to be removed - */ - const removeModulesWithSourceType = (info, sourceTypes) => { - for (const module of info.modules) { - const types = module.getSourceTypes(); - if (sourceTypes.some(type => types.has(type))) { - info.modules.delete(module); - for (const type of types) { - info.sizes[type] -= module.size(type); - } - } - } - }; +/***/ 92886: +/***/ (function(__unused_webpack_module, exports, __webpack_require__) { - /** - * @param {ChunksInfoItem} info entry - * @returns {boolean} true, if entry become empty - */ - const removeMinSizeViolatingModules = info => { - if (!info.cacheGroup._validateSize) return false; - const violatingSizes = getViolatingMinSizes( - info.sizes, - info.cacheGroup.minSize - ); - if (violatingSizes === undefined) return false; - removeModulesWithSourceType(info, violatingSizes); - return info.modules.size === 0; - }; +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Sergey Melyukov @smelukov +*/ - // Filter items were size < minSize - for (const [key, info] of chunksInfoMap) { - if (removeMinSizeViolatingModules(info)) { - chunksInfoMap.delete(key); - } else if ( - !checkMinSizeReduction( - info.sizes, - info.cacheGroup.minSizeReduction, - info.chunks.size - ) - ) { - chunksInfoMap.delete(key); - } - } - /** - * @typedef {Object} MaxSizeQueueItem - * @property {SplitChunksSizes} minSize - * @property {SplitChunksSizes} maxAsyncSize - * @property {SplitChunksSizes} maxInitialSize - * @property {string} automaticNameDelimiter - * @property {string[]} keys - */ - /** @type {Map} */ - const maxSizeQueueMap = new Map(); +const { UsageState } = __webpack_require__(4295); - while (chunksInfoMap.size > 0) { - // Find best matching entry - let bestEntryKey; - let bestEntry; - for (const pair of chunksInfoMap) { - const key = pair[0]; - const info = pair[1]; - if ( - bestEntry === undefined || - compareEntries(bestEntry, info) < 0 - ) { - bestEntry = info; - bestEntryKey = key; - } - } +/** @typedef {import("estree").Node} AnyNode */ +/** @typedef {import("../Dependency")} Dependency */ +/** @typedef {import("../ModuleGraph")} ModuleGraph */ +/** @typedef {import("../ModuleGraphConnection")} ModuleGraphConnection */ +/** @typedef {import("../ModuleGraphConnection").ConnectionState} ConnectionState */ +/** @typedef {import("../Parser").ParserState} ParserState */ +/** @typedef {import("../javascript/JavascriptParser")} JavascriptParser */ +/** @typedef {import("../util/runtime").RuntimeSpec} RuntimeSpec */ - const item = bestEntry; - chunksInfoMap.delete(bestEntryKey); +/** @typedef {Map | true>} InnerGraph */ +/** @typedef {function(boolean | Set | undefined): void} UsageCallback */ - let chunkName = item.name; - // Variable for the new chunk (lazy created) - /** @type {Chunk} */ - let newChunk; - // When no chunk name, check if we can reuse a chunk instead of creating a new one - let isExistingChunk = false; - let isReusedWithAllModules = false; - if (chunkName) { - const chunkByName = compilation.namedChunks.get(chunkName); - if (chunkByName !== undefined) { - newChunk = chunkByName; - const oldSize = item.chunks.size; - item.chunks.delete(newChunk); - isExistingChunk = item.chunks.size !== oldSize; - } - } else if (item.cacheGroup.reuseExistingChunk) { - outer: for (const chunk of item.chunks) { - if ( - chunkGraph.getNumberOfChunkModules(chunk) !== - item.modules.size - ) { - continue; - } - if ( - item.chunks.size > 1 && - chunkGraph.getNumberOfEntryModules(chunk) > 0 - ) { - continue; - } - for (const module of item.modules) { - if (!chunkGraph.isModuleInChunk(module, chunk)) { - continue outer; - } - } - if (!newChunk || !newChunk.name) { - newChunk = chunk; - } else if ( - chunk.name && - chunk.name.length < newChunk.name.length - ) { - newChunk = chunk; - } else if ( - chunk.name && - chunk.name.length === newChunk.name.length && - chunk.name < newChunk.name - ) { - newChunk = chunk; - } - } - if (newChunk) { - item.chunks.delete(newChunk); - chunkName = undefined; - isExistingChunk = true; - isReusedWithAllModules = true; - } - } +/** + * @typedef {Object} StateObject + * @property {InnerGraph} innerGraph + * @property {TopLevelSymbol=} currentTopLevelSymbol + * @property {Map>} usageCallbackMap + */ - const enforced = - item.cacheGroup._conditionalEnforce && - checkMinSize(item.sizes, item.cacheGroup.enforceSizeThreshold); +/** @typedef {false|StateObject} State */ - const usedChunks = new Set(item.chunks); +/** @type {WeakMap} */ +const parserStateMap = new WeakMap(); +const topLevelSymbolTag = Symbol("top level symbol"); - // Check if maxRequests condition can be fulfilled - if ( - !enforced && - (Number.isFinite(item.cacheGroup.maxInitialRequests) || - Number.isFinite(item.cacheGroup.maxAsyncRequests)) - ) { - for (const chunk of usedChunks) { - // respect max requests - const maxRequests = chunk.isOnlyInitial() - ? item.cacheGroup.maxInitialRequests - : chunk.canBeInitial() - ? Math.min( - item.cacheGroup.maxInitialRequests, - item.cacheGroup.maxAsyncRequests - ) - : item.cacheGroup.maxAsyncRequests; - if ( - isFinite(maxRequests) && - getRequests(chunk) >= maxRequests - ) { - usedChunks.delete(chunk); - } - } - } +/** + * @param {ParserState} parserState parser state + * @returns {State} state + */ +function getState(parserState) { + return parserStateMap.get(parserState); +} - outer: for (const chunk of usedChunks) { - for (const module of item.modules) { - if (chunkGraph.isModuleInChunk(module, chunk)) continue outer; - } - usedChunks.delete(chunk); - } +/** + * @param {ParserState} parserState parser state + * @returns {void} + */ +exports.bailout = parserState => { + parserStateMap.set(parserState, false); +}; - // Were some (invalid) chunks removed from usedChunks? - // => readd all modules to the queue, as things could have been changed - if (usedChunks.size < item.chunks.size) { - if (isExistingChunk) usedChunks.add(newChunk); - if (usedChunks.size >= item.cacheGroup.minChunks) { - const chunksArr = Array.from(usedChunks); - for (const module of item.modules) { - addModuleToChunksInfoMap( - item.cacheGroup, - item.cacheGroupIndex, - chunksArr, - getKey(usedChunks), - module - ); - } - } - continue; - } +/** + * @param {ParserState} parserState parser state + * @returns {void} + */ +exports.enable = parserState => { + const state = parserStateMap.get(parserState); + if (state === false) { + return; + } + parserStateMap.set(parserState, { + innerGraph: new Map(), + currentTopLevelSymbol: undefined, + usageCallbackMap: new Map() + }); +}; - // Validate minRemainingSize constraint when a single chunk is left over - if ( - !enforced && - item.cacheGroup._validateRemainingSize && - usedChunks.size === 1 - ) { - const [chunk] = usedChunks; - let chunkSizes = Object.create(null); - for (const module of chunkGraph.getChunkModulesIterable(chunk)) { - if (!item.modules.has(module)) { - for (const type of module.getSourceTypes()) { - chunkSizes[type] = - (chunkSizes[type] || 0) + module.size(type); - } - } - } - const violatingSizes = getViolatingMinSizes( - chunkSizes, - item.cacheGroup.minRemainingSize - ); - if (violatingSizes !== undefined) { - const oldModulesSize = item.modules.size; - removeModulesWithSourceType(item, violatingSizes); - if ( - item.modules.size > 0 && - item.modules.size !== oldModulesSize - ) { - // queue this item again to be processed again - // without violating modules - chunksInfoMap.set(bestEntryKey, item); - } - continue; - } - } +/** + * @param {ParserState} parserState parser state + * @returns {boolean} true, when enabled + */ +exports.isEnabled = parserState => { + const state = parserStateMap.get(parserState); + return !!state; +}; - // Create the new chunk if not reusing one - if (newChunk === undefined) { - newChunk = compilation.addChunk(chunkName); - } - // Walk through all chunks - for (const chunk of usedChunks) { - // Add graph connections for splitted chunk - chunk.split(newChunk); - } +/** + * @param {ParserState} state parser state + * @param {TopLevelSymbol | null} symbol the symbol, or null for all symbols + * @param {string | TopLevelSymbol | true} usage usage data + * @returns {void} + */ +exports.addUsage = (state, symbol, usage) => { + const innerGraphState = getState(state); - // Add a note to the chunk - newChunk.chunkReason = - (newChunk.chunkReason ? newChunk.chunkReason + ", " : "") + - (isReusedWithAllModules - ? "reused as split chunk" - : "split chunk"); - if (item.cacheGroup.key) { - newChunk.chunkReason += ` (cache group: ${item.cacheGroup.key})`; - } - if (chunkName) { - newChunk.chunkReason += ` (name: ${chunkName})`; - } - if (item.cacheGroup.filename) { - newChunk.filenameTemplate = item.cacheGroup.filename; - } - if (item.cacheGroup.idHint) { - newChunk.idNameHints.add(item.cacheGroup.idHint); - } - if (!isReusedWithAllModules) { - // Add all modules to the new chunk - for (const module of item.modules) { - if (!module.chunkCondition(newChunk, compilation)) continue; - // Add module to new chunk - chunkGraph.connectChunkAndModule(newChunk, module); - // Remove module from used chunks - for (const chunk of usedChunks) { - chunkGraph.disconnectChunkAndModule(chunk, module); - } - } - } else { - // Remove all modules from used chunks - for (const module of item.modules) { - for (const chunk of usedChunks) { - chunkGraph.disconnectChunkAndModule(chunk, module); - } - } - } + if (innerGraphState) { + const { innerGraph } = innerGraphState; + const info = innerGraph.get(symbol); + if (usage === true) { + innerGraph.set(symbol, true); + } else if (info === undefined) { + innerGraph.set(symbol, new Set([usage])); + } else if (info !== true) { + info.add(usage); + } + } +}; - if ( - Object.keys(item.cacheGroup.maxAsyncSize).length > 0 || - Object.keys(item.cacheGroup.maxInitialSize).length > 0 - ) { - const oldMaxSizeSettings = maxSizeQueueMap.get(newChunk); - maxSizeQueueMap.set(newChunk, { - minSize: oldMaxSizeSettings - ? combineSizes( - oldMaxSizeSettings.minSize, - item.cacheGroup._minSizeForMaxSize, - Math.max - ) - : item.cacheGroup.minSize, - maxAsyncSize: oldMaxSizeSettings - ? combineSizes( - oldMaxSizeSettings.maxAsyncSize, - item.cacheGroup.maxAsyncSize, - Math.min - ) - : item.cacheGroup.maxAsyncSize, - maxInitialSize: oldMaxSizeSettings - ? combineSizes( - oldMaxSizeSettings.maxInitialSize, - item.cacheGroup.maxInitialSize, - Math.min - ) - : item.cacheGroup.maxInitialSize, - automaticNameDelimiter: item.cacheGroup.automaticNameDelimiter, - keys: oldMaxSizeSettings - ? oldMaxSizeSettings.keys.concat(item.cacheGroup.key) - : [item.cacheGroup.key] - }); - } +/** + * @param {JavascriptParser} parser the parser + * @param {string} name name of variable + * @param {string | TopLevelSymbol | true} usage usage data + * @returns {void} + */ +exports.addVariableUsage = (parser, name, usage) => { + const symbol = + /** @type {TopLevelSymbol} */ ( + parser.getTagData(name, topLevelSymbolTag) + ) || exports.tagTopLevelSymbol(parser, name); + if (symbol) { + exports.addUsage(parser.state, symbol, usage); + } +}; - // remove all modules from other entries and update size - for (const [key, info] of chunksInfoMap) { - if (isOverlap(info.chunks, usedChunks)) { - // update modules and total size - // may remove it from the map when < minSize - let updated = false; - for (const module of item.modules) { - if (info.modules.has(module)) { - // remove module - info.modules.delete(module); - // update size - for (const key of module.getSourceTypes()) { - info.sizes[key] -= module.size(key); - } - updated = true; - } - } - if (updated) { - if (info.modules.size === 0) { - chunksInfoMap.delete(key); - continue; - } - if ( - removeMinSizeViolatingModules(info) || - !checkMinSizeReduction( - info.sizes, - info.cacheGroup.minSizeReduction, - info.chunks.size - ) - ) { - chunksInfoMap.delete(key); - continue; - } +/** + * @param {ParserState} state parser state + * @returns {void} + */ +exports.inferDependencyUsage = state => { + const innerGraphState = getState(state); + + if (!innerGraphState) { + return; + } + + const { innerGraph, usageCallbackMap } = innerGraphState; + const processed = new Map(); + // flatten graph to terminal nodes (string, undefined or true) + const nonTerminal = new Set(innerGraph.keys()); + while (nonTerminal.size > 0) { + for (const key of nonTerminal) { + /** @type {Set | true} */ + let newSet = new Set(); + let isTerminal = true; + const value = innerGraph.get(key); + let alreadyProcessed = processed.get(key); + if (alreadyProcessed === undefined) { + alreadyProcessed = new Set(); + processed.set(key, alreadyProcessed); + } + if (value !== true && value !== undefined) { + for (const item of value) { + alreadyProcessed.add(item); + } + for (const item of value) { + if (typeof item === "string") { + newSet.add(item); + } else { + const itemValue = innerGraph.get(item); + if (itemValue === true) { + newSet = true; + break; + } + if (itemValue !== undefined) { + for (const i of itemValue) { + if (i === key) continue; + if (alreadyProcessed.has(i)) continue; + newSet.add(i); + if (typeof i !== "string") { + isTerminal = false; } } } } + } + if (newSet === true) { + innerGraph.set(key, true); + } else if (newSet.size === 0) { + innerGraph.set(key, undefined); + } else { + innerGraph.set(key, newSet); + } + } + if (isTerminal) { + nonTerminal.delete(key); - logger.timeEnd("queue"); - - logger.time("maxSize"); - - /** @type {Set} */ - const incorrectMinMaxSizeSet = new Set(); - - const { outputOptions } = compilation; - - // Make sure that maxSize is fulfilled - const { fallbackCacheGroup } = this.options; - for (const chunk of Array.from(compilation.chunks)) { - const chunkConfig = maxSizeQueueMap.get(chunk); - const { - minSize, - maxAsyncSize, - maxInitialSize, - automaticNameDelimiter - } = chunkConfig || fallbackCacheGroup; - if (!chunkConfig && !fallbackCacheGroup.chunksFilter(chunk)) - continue; - /** @type {SplitChunksSizes} */ - let maxSize; - if (chunk.isOnlyInitial()) { - maxSize = maxInitialSize; - } else if (chunk.canBeInitial()) { - maxSize = combineSizes(maxAsyncSize, maxInitialSize, Math.min); - } else { - maxSize = maxAsyncSize; - } - if (Object.keys(maxSize).length === 0) { - continue; - } - for (const key of Object.keys(maxSize)) { - const maxSizeValue = maxSize[key]; - const minSizeValue = minSize[key]; - if ( - typeof minSizeValue === "number" && - minSizeValue > maxSizeValue - ) { - const keys = chunkConfig && chunkConfig.keys; - const warningKey = `${ - keys && keys.join() - } ${minSizeValue} ${maxSizeValue}`; - if (!incorrectMinMaxSizeSet.has(warningKey)) { - incorrectMinMaxSizeSet.add(warningKey); - compilation.warnings.push( - new MinMaxSizeWarning(keys, minSizeValue, maxSizeValue) - ); - } - } - } - const results = deterministicGroupingForModules({ - minSize, - maxSize: mapObject(maxSize, (value, key) => { - const minSizeValue = minSize[key]; - return typeof minSizeValue === "number" - ? Math.max(value, minSizeValue) - : value; - }), - items: chunkGraph.getChunkModulesIterable(chunk), - getKey(module) { - const cache = getKeyCache.get(module); - if (cache !== undefined) return cache; - const ident = cachedMakePathsRelative(module.identifier()); - const nameForCondition = - module.nameForCondition && module.nameForCondition(); - const name = nameForCondition - ? cachedMakePathsRelative(nameForCondition) - : ident.replace(/^.*!|\?[^?!]*$/g, ""); - const fullKey = - name + - automaticNameDelimiter + - hashFilename(ident, outputOptions); - const key = requestToId(fullKey); - getKeyCache.set(module, key); - return key; - }, - getSize(module) { - const size = Object.create(null); - for (const key of module.getSourceTypes()) { - size[key] = module.size(key); - } - return size; - } - }); - if (results.length <= 1) { - continue; - } - for (let i = 0; i < results.length; i++) { - const group = results[i]; - const key = this.options.hidePathInfo - ? hashFilename(group.key, outputOptions) - : group.key; - let name = chunk.name - ? chunk.name + automaticNameDelimiter + key - : null; - if (name && name.length > 100) { - name = - name.slice(0, 100) + - automaticNameDelimiter + - hashFilename(name, outputOptions); - } - if (i !== results.length - 1) { - const newPart = compilation.addChunk(name); - chunk.split(newPart); - newPart.chunkReason = chunk.chunkReason; - // Add all modules to the new chunk - for (const module of group.items) { - if (!module.chunkCondition(newPart, compilation)) { - continue; + // For the global key, merge with all other keys + if (key === null) { + const globalValue = innerGraph.get(null); + if (globalValue) { + for (const [key, value] of innerGraph) { + if (key !== null && value !== true) { + if (globalValue === true) { + innerGraph.set(key, true); + } else { + const newSet = new Set(value); + for (const item of globalValue) { + newSet.add(item); } - // Add module to new chunk - chunkGraph.connectChunkAndModule(newPart, module); - // Remove module from used chunks - chunkGraph.disconnectChunkAndModule(chunk, module); + innerGraph.set(key, newSet); } - } else { - // change the chunk to be a part - chunk.name = name; } } } - logger.timeEnd("maxSize"); } - ); - }); + } + } + } + + /** @type {Map>} */ + for (const [symbol, callbacks] of usageCallbackMap) { + const usage = /** @type {true | Set | undefined} */ ( + innerGraph.get(symbol) + ); + for (const callback of callbacks) { + callback(usage === undefined ? false : usage); + } } }; +/** + * @param {ParserState} state parser state + * @param {UsageCallback} onUsageCallback on usage callback + */ +exports.onUsage = (state, onUsageCallback) => { + const innerGraphState = getState(state); -/***/ }), + if (innerGraphState) { + const { usageCallbackMap, currentTopLevelSymbol } = innerGraphState; + if (currentTopLevelSymbol) { + let callbacks = usageCallbackMap.get(currentTopLevelSymbol); -/***/ 60139: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + if (callbacks === undefined) { + callbacks = new Set(); + usageCallbackMap.set(currentTopLevelSymbol, callbacks); + } -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Sean Larkin @thelarkinn -*/ + callbacks.add(onUsageCallback); + } else { + onUsageCallback(true); + } + } else { + onUsageCallback(undefined); + } +}; +/** + * @param {ParserState} state parser state + * @param {TopLevelSymbol} symbol the symbol + */ +exports.setTopLevelSymbol = (state, symbol) => { + const innerGraphState = getState(state); + if (innerGraphState) { + innerGraphState.currentTopLevelSymbol = symbol; + } +}; -const { formatSize } = __webpack_require__(15979); -const WebpackError = __webpack_require__(68422); +/** + * @param {ParserState} state parser state + * @returns {TopLevelSymbol|void} usage data + */ +exports.getTopLevelSymbol = state => { + const innerGraphState = getState(state); -/** @typedef {import("./SizeLimitsPlugin").AssetDetails} AssetDetails */ + if (innerGraphState) { + return innerGraphState.currentTopLevelSymbol; + } +}; -module.exports = class AssetsOverSizeLimitWarning extends WebpackError { - /** - * @param {AssetDetails[]} assetsOverSizeLimit the assets - * @param {number} assetLimit the size limit - */ - constructor(assetsOverSizeLimit, assetLimit) { - const assetLists = assetsOverSizeLimit - .map(asset => `\n ${asset.name} (${formatSize(asset.size)})`) - .join(""); +/** + * @param {JavascriptParser} parser parser + * @param {string} name name of variable + * @returns {TopLevelSymbol} symbol + */ +exports.tagTopLevelSymbol = (parser, name) => { + const innerGraphState = getState(parser.state); + if (!innerGraphState) return; - super(`asset size limit: The following asset(s) exceed the recommended size limit (${formatSize( - assetLimit - )}). -This can impact web performance. -Assets: ${assetLists}`); + parser.defineVariable(name); - this.name = "AssetsOverSizeLimitWarning"; - this.assets = assetsOverSizeLimit; + const existingTag = /** @type {TopLevelSymbol} */ ( + parser.getTagData(name, topLevelSymbolTag) + ); + if (existingTag) { + return existingTag; + } + + const fn = new TopLevelSymbol(name); + parser.tagVariable(name, topLevelSymbolTag, fn); + return fn; +}; + +/** + * @param {Dependency} dependency the dependency + * @param {Set | boolean} usedByExports usedByExports info + * @param {ModuleGraph} moduleGraph moduleGraph + * @param {RuntimeSpec} runtime runtime + * @returns {boolean} false, when unused. Otherwise true + */ +exports.isDependencyUsedByExports = ( + dependency, + usedByExports, + moduleGraph, + runtime +) => { + if (usedByExports === false) return false; + if (usedByExports !== true && usedByExports !== undefined) { + const selfModule = moduleGraph.getParentModule(dependency); + const exportsInfo = moduleGraph.getExportsInfo(selfModule); + let used = false; + for (const exportName of usedByExports) { + if (exportsInfo.getUsed(exportName, runtime) !== UsageState.Unused) + used = true; + } + if (!used) return false; + } + return true; +}; + +/** + * @param {Dependency} dependency the dependency + * @param {Set | boolean} usedByExports usedByExports info + * @param {ModuleGraph} moduleGraph moduleGraph + * @returns {null | false | function(ModuleGraphConnection, RuntimeSpec): ConnectionState} function to determine if the connection is active + */ +exports.getDependencyUsedByExportsCondition = ( + dependency, + usedByExports, + moduleGraph +) => { + if (usedByExports === false) return false; + if (usedByExports !== true && usedByExports !== undefined) { + const selfModule = moduleGraph.getParentModule(dependency); + const exportsInfo = moduleGraph.getExportsInfo(selfModule); + return (connections, runtime) => { + for (const exportName of usedByExports) { + if (exportsInfo.getUsed(exportName, runtime) !== UsageState.Unused) + return true; + } + return false; + }; } + return null; }; +class TopLevelSymbol { + /** + * @param {string} name name of the variable + */ + constructor(name) { + this.name = name; + } +} + +exports.TopLevelSymbol = TopLevelSymbol; +exports.topLevelSymbolTag = topLevelSymbolTag; + /***/ }), -/***/ 87216: +/***/ 57997: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; /* MIT License http://www.opensource.org/licenses/mit-license.php - Author Sean Larkin @thelarkinn + Author Tobias Koppers @sokra */ -const { formatSize } = __webpack_require__(15979); -const WebpackError = __webpack_require__(68422); +const PureExpressionDependency = __webpack_require__(24746); +const InnerGraph = __webpack_require__(92886); -/** @typedef {import("./SizeLimitsPlugin").EntrypointDetails} EntrypointDetails */ +/** @typedef {import("estree").ClassDeclaration} ClassDeclarationNode */ +/** @typedef {import("estree").ClassExpression} ClassExpressionNode */ +/** @typedef {import("estree").Node} Node */ +/** @typedef {import("estree").VariableDeclarator} VariableDeclaratorNode */ +/** @typedef {import("../Compiler")} Compiler */ +/** @typedef {import("../Dependency")} Dependency */ +/** @typedef {import("../dependencies/HarmonyImportSpecifierDependency")} HarmonyImportSpecifierDependency */ +/** @typedef {import("../javascript/JavascriptParser")} JavascriptParser */ +/** @typedef {import("./InnerGraph").InnerGraph} InnerGraph */ +/** @typedef {import("./InnerGraph").TopLevelSymbol} TopLevelSymbol */ + +const { topLevelSymbolTag } = InnerGraph; + +class InnerGraphPlugin { + /** + * Apply the plugin + * @param {Compiler} compiler the compiler instance + * @returns {void} + */ + apply(compiler) { + compiler.hooks.compilation.tap( + "InnerGraphPlugin", + (compilation, { normalModuleFactory }) => { + const logger = compilation.getLogger("webpack.InnerGraphPlugin"); + + compilation.dependencyTemplates.set( + PureExpressionDependency, + new PureExpressionDependency.Template() + ); + + /** + * @param {JavascriptParser} parser the parser + * @param {Object} parserOptions options + * @returns {void} + */ + const handler = (parser, parserOptions) => { + const onUsageSuper = sup => { + InnerGraph.onUsage(parser.state, usedByExports => { + switch (usedByExports) { + case undefined: + case true: + return; + default: { + const dep = new PureExpressionDependency(sup.range); + dep.loc = sup.loc; + dep.usedByExports = usedByExports; + parser.state.module.addDependency(dep); + break; + } + } + }); + }; + + parser.hooks.program.tap("InnerGraphPlugin", () => { + InnerGraph.enable(parser.state); + }); + + parser.hooks.finish.tap("InnerGraphPlugin", () => { + if (!InnerGraph.isEnabled(parser.state)) return; + + logger.time("infer dependency usage"); + InnerGraph.inferDependencyUsage(parser.state); + logger.timeAggregate("infer dependency usage"); + }); + + // During prewalking the following datastructures are filled with + // nodes that have a TopLevelSymbol assigned and + // variables are tagged with the assigned TopLevelSymbol + + // We differ 3 types of nodes: + // 1. full statements (export default, function declaration) + // 2. classes (class declaration, class expression) + // 3. variable declarators (const x = ...) + + /** @type {WeakMap} */ + const statementWithTopLevelSymbol = new WeakMap(); + /** @type {WeakMap} */ + const statementPurePart = new WeakMap(); + + /** @type {WeakMap} */ + const classWithTopLevelSymbol = new WeakMap(); + + /** @type {WeakMap} */ + const declWithTopLevelSymbol = new WeakMap(); + /** @type {WeakSet} */ + const pureDeclarators = new WeakSet(); + + // The following hooks are used during prewalking: + + parser.hooks.preStatement.tap("InnerGraphPlugin", statement => { + if (!InnerGraph.isEnabled(parser.state)) return; + + if (parser.scope.topLevelScope === true) { + if (statement.type === "FunctionDeclaration") { + const name = statement.id ? statement.id.name : "*default*"; + const fn = InnerGraph.tagTopLevelSymbol(parser, name); + statementWithTopLevelSymbol.set(statement, fn); + return true; + } + } + }); + + parser.hooks.blockPreStatement.tap("InnerGraphPlugin", statement => { + if (!InnerGraph.isEnabled(parser.state)) return; + + if (parser.scope.topLevelScope === true) { + if (statement.type === "ClassDeclaration") { + const name = statement.id ? statement.id.name : "*default*"; + const fn = InnerGraph.tagTopLevelSymbol(parser, name); + classWithTopLevelSymbol.set(statement, fn); + return true; + } + if (statement.type === "ExportDefaultDeclaration") { + const name = "*default*"; + const fn = InnerGraph.tagTopLevelSymbol(parser, name); + const decl = statement.declaration; + if ( + decl.type === "ClassExpression" || + decl.type === "ClassDeclaration" + ) { + classWithTopLevelSymbol.set(decl, fn); + } else if (parser.isPure(decl, statement.range[0])) { + statementWithTopLevelSymbol.set(statement, fn); + if ( + !decl.type.endsWith("FunctionExpression") && + !decl.type.endsWith("Declaration") && + decl.type !== "Literal" + ) { + statementPurePart.set(statement, decl); + } + } + } + } + }); + + parser.hooks.preDeclarator.tap( + "InnerGraphPlugin", + (decl, statement) => { + if (!InnerGraph.isEnabled(parser.state)) return; + if ( + parser.scope.topLevelScope === true && + decl.init && + decl.id.type === "Identifier" + ) { + const name = decl.id.name; + if (decl.init.type === "ClassExpression") { + const fn = InnerGraph.tagTopLevelSymbol(parser, name); + classWithTopLevelSymbol.set(decl.init, fn); + } else if (parser.isPure(decl.init, decl.id.range[1])) { + const fn = InnerGraph.tagTopLevelSymbol(parser, name); + declWithTopLevelSymbol.set(decl, fn); + if ( + !decl.init.type.endsWith("FunctionExpression") && + decl.init.type !== "Literal" + ) { + pureDeclarators.add(decl); + } + return true; + } + } + } + ); + + // During real walking we set the TopLevelSymbol state to the assigned + // TopLevelSymbol by using the fill datastructures. + + // In addition to tracking TopLevelSymbols, we sometimes need to + // add a PureExpressionDependency. This is needed to skip execution + // of pure expressions, even when they are not dropped due to + // minimizing. Otherwise symbols used there might not exist anymore + // as they are removed as unused by this optimization + + // When we find a reference to a TopLevelSymbol, we register a + // TopLevelSymbol dependency from TopLevelSymbol in state to the + // referenced TopLevelSymbol. This way we get a graph of all + // TopLevelSymbols. -module.exports = class EntrypointsOverSizeLimitWarning extends WebpackError { - /** - * @param {EntrypointDetails[]} entrypoints the entrypoints - * @param {number} entrypointLimit the size limit - */ - constructor(entrypoints, entrypointLimit) { - const entrypointList = entrypoints - .map( - entrypoint => - `\n ${entrypoint.name} (${formatSize( - entrypoint.size - )})\n${entrypoint.files.map(asset => ` ${asset}`).join("\n")}` - ) - .join(""); - super(`entrypoint size limit: The following entrypoint(s) combined asset size exceeds the recommended limit (${formatSize( - entrypointLimit - )}). This can impact web performance. -Entrypoints:${entrypointList}\n`); + // The following hooks are called during walking: - this.name = "EntrypointsOverSizeLimitWarning"; - this.entrypoints = entrypoints; - } -}; + parser.hooks.statement.tap("InnerGraphPlugin", statement => { + if (!InnerGraph.isEnabled(parser.state)) return; + if (parser.scope.topLevelScope === true) { + InnerGraph.setTopLevelSymbol(parser.state, undefined); + const fn = statementWithTopLevelSymbol.get(statement); + if (fn) { + InnerGraph.setTopLevelSymbol(parser.state, fn); + const purePart = statementPurePart.get(statement); + if (purePart) { + InnerGraph.onUsage(parser.state, usedByExports => { + switch (usedByExports) { + case undefined: + case true: + return; + default: { + const dep = new PureExpressionDependency( + purePart.range + ); + dep.loc = statement.loc; + dep.usedByExports = usedByExports; + parser.state.module.addDependency(dep); + break; + } + } + }); + } + } + } + }); -/***/ }), + parser.hooks.classExtendsExpression.tap( + "InnerGraphPlugin", + (expr, statement) => { + if (!InnerGraph.isEnabled(parser.state)) return; + if (parser.scope.topLevelScope === true) { + const fn = classWithTopLevelSymbol.get(statement); + if ( + fn && + parser.isPure( + expr, + statement.id ? statement.id.range[1] : statement.range[0] + ) + ) { + InnerGraph.setTopLevelSymbol(parser.state, fn); + onUsageSuper(expr); + } + } + } + ); -/***/ 80882: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + parser.hooks.classBodyElement.tap( + "InnerGraphPlugin", + (element, classDefinition) => { + if (!InnerGraph.isEnabled(parser.state)) return; + if (parser.scope.topLevelScope === true) { + const fn = classWithTopLevelSymbol.get(classDefinition); + if (fn) { + InnerGraph.setTopLevelSymbol(parser.state, undefined); + } + } + } + ); -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Sean Larkin @thelarkinn -*/ + parser.hooks.classBodyValue.tap( + "InnerGraphPlugin", + (expression, element, classDefinition) => { + if (!InnerGraph.isEnabled(parser.state)) return; + if (parser.scope.topLevelScope === true) { + const fn = classWithTopLevelSymbol.get(classDefinition); + if (fn) { + if ( + !element.static || + parser.isPure( + expression, + element.key ? element.key.range[1] : element.range[0] + ) + ) { + InnerGraph.setTopLevelSymbol(parser.state, fn); + if (element.type !== "MethodDefinition" && element.static) { + InnerGraph.onUsage(parser.state, usedByExports => { + switch (usedByExports) { + case undefined: + case true: + return; + default: { + const dep = new PureExpressionDependency( + expression.range + ); + dep.loc = expression.loc; + dep.usedByExports = usedByExports; + parser.state.module.addDependency(dep); + break; + } + } + }); + } + } else { + InnerGraph.setTopLevelSymbol(parser.state, undefined); + } + } + } + } + ); + parser.hooks.declarator.tap("InnerGraphPlugin", (decl, statement) => { + if (!InnerGraph.isEnabled(parser.state)) return; + const fn = declWithTopLevelSymbol.get(decl); + if (fn) { + InnerGraph.setTopLevelSymbol(parser.state, fn); + if (pureDeclarators.has(decl)) { + if (decl.init.type === "ClassExpression") { + if (decl.init.superClass) { + onUsageSuper(decl.init.superClass); + } + } else { + InnerGraph.onUsage(parser.state, usedByExports => { + switch (usedByExports) { + case undefined: + case true: + return; + default: { + const dep = new PureExpressionDependency( + decl.init.range + ); + dep.loc = decl.loc; + dep.usedByExports = usedByExports; + parser.state.module.addDependency(dep); + break; + } + } + }); + } + } + parser.walkExpression(decl.init); + InnerGraph.setTopLevelSymbol(parser.state, undefined); + return true; + } + }); -const WebpackError = __webpack_require__(68422); + parser.hooks.expression + .for(topLevelSymbolTag) + .tap("InnerGraphPlugin", () => { + const topLevelSymbol = /** @type {TopLevelSymbol} */ ( + parser.currentTagData + ); + const currentTopLevelSymbol = InnerGraph.getTopLevelSymbol( + parser.state + ); + InnerGraph.addUsage( + parser.state, + topLevelSymbol, + currentTopLevelSymbol || true + ); + }); + parser.hooks.assign + .for(topLevelSymbolTag) + .tap("InnerGraphPlugin", expr => { + if (!InnerGraph.isEnabled(parser.state)) return; + if (expr.operator === "=") return true; + }); + }; + normalModuleFactory.hooks.parser + .for("javascript/auto") + .tap("InnerGraphPlugin", handler); + normalModuleFactory.hooks.parser + .for("javascript/esm") + .tap("InnerGraphPlugin", handler); -module.exports = class NoAsyncChunksWarning extends WebpackError { - constructor() { - super( - "webpack performance recommendations: \n" + - "You can limit the size of your bundles by using import() or require.ensure to lazy load some parts of your application.\n" + - "For more info visit https://webpack.js.org/guides/code-splitting/" + compilation.hooks.finishModules.tap("InnerGraphPlugin", () => { + logger.timeAggregateEnd("infer dependency usage"); + }); + } ); - - this.name = "NoAsyncChunksWarning"; } -}; +} + +module.exports = InnerGraphPlugin; /***/ }), -/***/ 64025: +/***/ 22119: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; /* MIT License http://www.opensource.org/licenses/mit-license.php - Author Sean Larkin @thelarkinn + Author Tobias Koppers @sokra */ -const { find } = __webpack_require__(34715); -const AssetsOverSizeLimitWarning = __webpack_require__(60139); -const EntrypointsOverSizeLimitWarning = __webpack_require__(87216); -const NoAsyncChunksWarning = __webpack_require__(80882); +const { STAGE_ADVANCED } = __webpack_require__(68145); +const LazyBucketSortedSet = __webpack_require__(79300); +const { compareChunks } = __webpack_require__(26296); +const createSchemaValidation = __webpack_require__(77695); -/** @typedef {import("webpack-sources").Source} Source */ -/** @typedef {import("../../declarations/WebpackOptions").PerformanceOptions} PerformanceOptions */ -/** @typedef {import("../ChunkGroup")} ChunkGroup */ +/** @typedef {import("../../declarations/plugins/optimize/LimitChunkCountPlugin").LimitChunkCountPluginOptions} LimitChunkCountPluginOptions */ +/** @typedef {import("../Chunk")} Chunk */ /** @typedef {import("../Compiler")} Compiler */ -/** @typedef {import("../Entrypoint")} Entrypoint */ -/** @typedef {import("../WebpackError")} WebpackError */ -/** - * @typedef {Object} AssetDetails - * @property {string} name - * @property {number} size - */ +const validate = createSchemaValidation( + __webpack_require__(70831), + () => __webpack_require__(58898), + { + name: "Limit Chunk Count Plugin", + baseDataPath: "options" + } +); /** - * @typedef {Object} EntrypointDetails - * @property {string} name - * @property {number} size - * @property {string[]} files + * @typedef {Object} ChunkCombination + * @property {boolean} deleted this is set to true when combination was removed + * @property {number} sizeDiff + * @property {number} integratedSize + * @property {Chunk} a + * @property {Chunk} b + * @property {number} aIdx + * @property {number} bIdx + * @property {number} aSize + * @property {number} bSize */ -const isOverSizeLimitSet = new WeakSet(); - -const excludeSourceMap = (name, source, info) => !info.development; - -module.exports = class SizeLimitsPlugin { - /** - * @param {PerformanceOptions} options the plugin options - */ - constructor(options) { - this.hints = options.hints; - this.maxAssetSize = options.maxAssetSize; - this.maxEntrypointSize = options.maxEntrypointSize; - this.assetFilter = options.assetFilter; +const addToSetMap = (map, key, value) => { + const set = map.get(key); + if (set === undefined) { + map.set(key, new Set([value])); + } else { + set.add(value); } +}; +class LimitChunkCountPlugin { /** - * @param {ChunkGroup | Source} thing the resource to test - * @returns {boolean} true if over the limit + * @param {LimitChunkCountPluginOptions=} options options object */ - static isOverSizeLimit(thing) { - return isOverSizeLimitSet.has(thing); + constructor(options) { + validate(options); + this.options = options; } /** - * Apply the plugin - * @param {Compiler} compiler the compiler instance + * @param {Compiler} compiler the webpack compiler * @returns {void} */ apply(compiler) { - const entrypointSizeLimit = this.maxEntrypointSize; - const assetSizeLimit = this.maxAssetSize; - const hints = this.hints; - const assetFilter = this.assetFilter || excludeSourceMap; + const options = this.options; + compiler.hooks.compilation.tap("LimitChunkCountPlugin", compilation => { + compilation.hooks.optimizeChunks.tap( + { + name: "LimitChunkCountPlugin", + stage: STAGE_ADVANCED + }, + chunks => { + const chunkGraph = compilation.chunkGraph; + const maxChunks = options.maxChunks; + if (!maxChunks) return; + if (maxChunks < 1) return; + if (compilation.chunks.size <= maxChunks) return; - compiler.hooks.afterEmit.tap("SizeLimitsPlugin", compilation => { - /** @type {WebpackError[]} */ - const warnings = []; + let remainingChunksToMerge = compilation.chunks.size - maxChunks; - /** - * @param {Entrypoint} entrypoint an entrypoint - * @returns {number} the size of the entrypoint - */ - const getEntrypointSize = entrypoint => { - let size = 0; - for (const file of entrypoint.getFiles()) { - const asset = compilation.getAsset(file); - if ( - asset && - assetFilter(asset.name, asset.source, asset.info) && - asset.source - ) { - size += asset.info.size || asset.source.size(); - } - } - return size; - }; + // order chunks in a deterministic way + const compareChunksWithGraph = compareChunks(chunkGraph); + const orderedChunks = Array.from(chunks).sort(compareChunksWithGraph); - /** @type {AssetDetails[]} */ - const assetsOverSizeLimit = []; - for (const { name, source, info } of compilation.getAssets()) { - if (!assetFilter(name, source, info) || !source) { - continue; - } + // create a lazy sorted data structure to keep all combinations + // this is large. Size = chunks * (chunks - 1) / 2 + // It uses a multi layer bucket sort plus normal sort in the last layer + // It's also lazy so only accessed buckets are sorted + const combinations = new LazyBucketSortedSet( + // Layer 1: ordered by largest size benefit + c => c.sizeDiff, + (a, b) => b - a, + // Layer 2: ordered by smallest combined size + c => c.integratedSize, + (a, b) => a - b, + // Layer 3: ordered by position difference in orderedChunk (-> to be deterministic) + c => c.bIdx - c.aIdx, + (a, b) => a - b, + // Layer 4: ordered by position in orderedChunk (-> to be deterministic) + (a, b) => a.bIdx - b.bIdx + ); - const size = info.size || source.size(); - if (size > assetSizeLimit) { - assetsOverSizeLimit.push({ - name, - size - }); - isOverSizeLimitSet.add(source); - } - } + // we keep a mapping from chunk to all combinations + // but this mapping is not kept up-to-date with deletions + // so `deleted` flag need to be considered when iterating this + /** @type {Map>} */ + const combinationsByChunk = new Map(); - const fileFilter = name => { - const asset = compilation.getAsset(name); - return asset && assetFilter(asset.name, asset.source, asset.info); - }; + orderedChunks.forEach((b, bIdx) => { + // create combination pairs with size and integrated size + for (let aIdx = 0; aIdx < bIdx; aIdx++) { + const a = orderedChunks[aIdx]; + // filter pairs that can not be integrated! + if (!chunkGraph.canChunksBeIntegrated(a, b)) continue; - /** @type {EntrypointDetails[]} */ - const entrypointsOverLimit = []; - for (const [name, entry] of compilation.entrypoints) { - const size = getEntrypointSize(entry); + const integratedSize = chunkGraph.getIntegratedChunksSize( + a, + b, + options + ); - if (size > entrypointSizeLimit) { - entrypointsOverLimit.push({ - name: name, - size: size, - files: entry.getFiles().filter(fileFilter) + const aSize = chunkGraph.getChunkSize(a, options); + const bSize = chunkGraph.getChunkSize(b, options); + const c = { + deleted: false, + sizeDiff: aSize + bSize - integratedSize, + integratedSize, + a, + b, + aIdx, + bIdx, + aSize, + bSize + }; + combinations.add(c); + addToSetMap(combinationsByChunk, a, c); + addToSetMap(combinationsByChunk, b, c); + } + return combinations; }); - isOverSizeLimitSet.add(entry); - } - } - if (hints) { - // 1. Individual Chunk: Size < 250kb - // 2. Collective Initial Chunks [entrypoint] (Each Set?): Size < 250kb - // 3. No Async Chunks - // if !1, then 2, if !2 return - if (assetsOverSizeLimit.length > 0) { - warnings.push( - new AssetsOverSizeLimitWarning(assetsOverSizeLimit, assetSizeLimit) - ); - } - if (entrypointsOverLimit.length > 0) { - warnings.push( - new EntrypointsOverSizeLimitWarning( - entrypointsOverLimit, - entrypointSizeLimit - ) - ); - } + // list of modified chunks during this run + // combinations affected by this change are skipped to allow + // further optimizations + /** @type {Set} */ + const modifiedChunks = new Set(); - if (warnings.length > 0) { - const someAsyncChunk = find( - compilation.chunks, - chunk => !chunk.canBeInitial() - ); + let changed = false; + // eslint-disable-next-line no-constant-condition + loop: while (true) { + const combination = combinations.popFirst(); + if (combination === undefined) break; - if (!someAsyncChunk) { - warnings.push(new NoAsyncChunksWarning()); - } + combination.deleted = true; + const { a, b, integratedSize } = combination; + + // skip over pair when + // one of the already merged chunks is a parent of one of the chunks + if (modifiedChunks.size > 0) { + const queue = new Set(a.groupsIterable); + for (const group of b.groupsIterable) { + queue.add(group); + } + for (const group of queue) { + for (const mChunk of modifiedChunks) { + if (mChunk !== a && mChunk !== b && mChunk.isInGroup(group)) { + // This is a potential pair which needs recalculation + // We can't do that now, but it merge before following pairs + // so we leave space for it, and consider chunks as modified + // just for the worse case + remainingChunksToMerge--; + if (remainingChunksToMerge <= 0) break loop; + modifiedChunks.add(a); + modifiedChunks.add(b); + continue loop; + } + } + for (const parent of group.parentsIterable) { + queue.add(parent); + } + } + } + + // merge the chunks + if (chunkGraph.canChunksBeIntegrated(a, b)) { + chunkGraph.integrateChunks(a, b); + compilation.chunks.delete(b); + + // flag chunk a as modified as further optimization are possible for all children here + modifiedChunks.add(a); + + changed = true; + remainingChunksToMerge--; + if (remainingChunksToMerge <= 0) break; + + // Update all affected combinations + // delete all combination with the removed chunk + // we will use combinations with the kept chunk instead + for (const combination of combinationsByChunk.get(a)) { + if (combination.deleted) continue; + combination.deleted = true; + combinations.delete(combination); + } + + // Update combinations with the kept chunk with new sizes + for (const combination of combinationsByChunk.get(b)) { + if (combination.deleted) continue; + if (combination.a === b) { + if (!chunkGraph.canChunksBeIntegrated(a, combination.b)) { + combination.deleted = true; + combinations.delete(combination); + continue; + } + // Update size + const newIntegratedSize = chunkGraph.getIntegratedChunksSize( + a, + combination.b, + options + ); + const finishUpdate = combinations.startUpdate(combination); + combination.a = a; + combination.integratedSize = newIntegratedSize; + combination.aSize = integratedSize; + combination.sizeDiff = + combination.bSize + integratedSize - newIntegratedSize; + finishUpdate(); + } else if (combination.b === b) { + if (!chunkGraph.canChunksBeIntegrated(combination.a, a)) { + combination.deleted = true; + combinations.delete(combination); + continue; + } + // Update size + const newIntegratedSize = chunkGraph.getIntegratedChunksSize( + combination.a, + a, + options + ); - if (hints === "error") { - compilation.errors.push(...warnings); - } else { - compilation.warnings.push(...warnings); + const finishUpdate = combinations.startUpdate(combination); + combination.b = a; + combination.integratedSize = newIntegratedSize; + combination.bSize = integratedSize; + combination.sizeDiff = + integratedSize + combination.aSize - newIntegratedSize; + finishUpdate(); + } + } + combinationsByChunk.set(a, combinationsByChunk.get(b)); + combinationsByChunk.delete(b); + } } + if (changed) return true; } - } + ); }); } -}; +} +module.exports = LimitChunkCountPlugin; /***/ }), -/***/ 18315: +/***/ 7281: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; /* MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra */ -const RuntimeModule = __webpack_require__(61439); -const Template = __webpack_require__(92066); +const { UsageState } = __webpack_require__(4295); +const { + numberToIdentifier, + NUMBER_OF_IDENTIFIER_START_CHARS, + NUMBER_OF_IDENTIFIER_CONTINUATION_CHARS +} = __webpack_require__(92066); +const { assignDeterministicIds } = __webpack_require__(72922); +const { compareSelect, compareStringsNumeric } = __webpack_require__(26296); -/** @typedef {import("../RuntimeTemplate")} RuntimeTemplate */ +/** @typedef {import("../Compiler")} Compiler */ +/** @typedef {import("../ExportsInfo")} ExportsInfo */ +/** @typedef {import("../ExportsInfo").ExportInfo} ExportInfo */ -class ChunkPrefetchFunctionRuntimeModule extends RuntimeModule { +/** + * @param {ExportsInfo} exportsInfo exports info + * @returns {boolean} mangle is possible + */ +const canMangle = exportsInfo => { + if (exportsInfo.otherExportsInfo.getUsed(undefined) !== UsageState.Unused) + return false; + let hasSomethingToMangle = false; + for (const exportInfo of exportsInfo.exports) { + if (exportInfo.canMangle === true) { + hasSomethingToMangle = true; + } + } + return hasSomethingToMangle; +}; + +// Sort by name +const comparator = compareSelect(e => e.name, compareStringsNumeric); +/** + * @param {boolean} deterministic use deterministic names + * @param {ExportsInfo} exportsInfo exports info + * @param {boolean} isNamespace is namespace object + * @returns {void} + */ +const mangleExportsInfo = (deterministic, exportsInfo, isNamespace) => { + if (!canMangle(exportsInfo)) return; + const usedNames = new Set(); + /** @type {ExportInfo[]} */ + const mangleableExports = []; + + // Avoid to renamed exports that are not provided when + // 1. it's not a namespace export: non-provided exports can be found in prototype chain + // 2. there are other provided exports and deterministic mode is chosen: + // non-provided exports would break the determinism + let avoidMangleNonProvided = !isNamespace; + if (!avoidMangleNonProvided && deterministic) { + for (const exportInfo of exportsInfo.ownedExports) { + if (exportInfo.provided !== false) { + avoidMangleNonProvided = true; + break; + } + } + } + for (const exportInfo of exportsInfo.ownedExports) { + const name = exportInfo.name; + if (!exportInfo.hasUsedName()) { + if ( + // Can the export be mangled? + exportInfo.canMangle !== true || + // Never rename 1 char exports + (name.length === 1 && /^[a-zA-Z0-9_$]/.test(name)) || + // Don't rename 2 char exports in deterministic mode + (deterministic && + name.length === 2 && + /^[a-zA-Z_$][a-zA-Z0-9_$]|^[1-9][0-9]/.test(name)) || + // Don't rename exports that are not provided + (avoidMangleNonProvided && exportInfo.provided !== true) + ) { + exportInfo.setUsedName(name); + usedNames.add(name); + } else { + mangleableExports.push(exportInfo); + } + } + if (exportInfo.exportsInfoOwned) { + const used = exportInfo.getUsed(undefined); + if ( + used === UsageState.OnlyPropertiesUsed || + used === UsageState.Unused + ) { + mangleExportsInfo(deterministic, exportInfo.exportsInfo, false); + } + } + } + if (deterministic) { + assignDeterministicIds( + mangleableExports, + e => e.name, + comparator, + (e, id) => { + const name = numberToIdentifier(id); + const size = usedNames.size; + usedNames.add(name); + if (size === usedNames.size) return false; + e.setUsedName(name); + return true; + }, + [ + NUMBER_OF_IDENTIFIER_START_CHARS, + NUMBER_OF_IDENTIFIER_START_CHARS * + NUMBER_OF_IDENTIFIER_CONTINUATION_CHARS + ], + NUMBER_OF_IDENTIFIER_CONTINUATION_CHARS, + usedNames.size + ); + } else { + const usedExports = []; + const unusedExports = []; + for (const exportInfo of mangleableExports) { + if (exportInfo.getUsed(undefined) === UsageState.Unused) { + unusedExports.push(exportInfo); + } else { + usedExports.push(exportInfo); + } + } + usedExports.sort(comparator); + unusedExports.sort(comparator); + let i = 0; + for (const list of [usedExports, unusedExports]) { + for (const exportInfo of list) { + let name; + do { + name = numberToIdentifier(i++); + } while (usedNames.has(name)); + exportInfo.setUsedName(name); + } + } + } +}; + +class MangleExportsPlugin { /** - * @param {string} childType TODO - * @param {string} runtimeFunction TODO - * @param {string} runtimeHandlers TODO + * @param {boolean} deterministic use deterministic names */ - constructor(childType, runtimeFunction, runtimeHandlers) { - super(`chunk ${childType} function`); - this.childType = childType; - this.runtimeFunction = runtimeFunction; - this.runtimeHandlers = runtimeHandlers; + constructor(deterministic) { + this._deterministic = deterministic; } - /** - * @returns {string} runtime code + * Apply the plugin + * @param {Compiler} compiler the compiler instance + * @returns {void} */ - generate() { - const { runtimeFunction, runtimeHandlers } = this; - const { runtimeTemplate } = this.compilation; - return Template.asString([ - `${runtimeHandlers} = {};`, - `${runtimeFunction} = ${runtimeTemplate.basicFunction("chunkId", [ - // map is shorter than forEach - `Object.keys(${runtimeHandlers}).map(${runtimeTemplate.basicFunction( - "key", - `${runtimeHandlers}[key](chunkId);` - )});` - ])}` - ]); + apply(compiler) { + const { _deterministic: deterministic } = this; + compiler.hooks.compilation.tap("MangleExportsPlugin", compilation => { + const moduleGraph = compilation.moduleGraph; + compilation.hooks.optimizeCodeGeneration.tap( + "MangleExportsPlugin", + modules => { + if (compilation.moduleMemCaches) { + throw new Error( + "optimization.mangleExports can't be used with cacheUnaffected as export mangling is a global effect" + ); + } + for (const module of modules) { + const isNamespace = + module.buildMeta && module.buildMeta.exportsType === "namespace"; + const exportsInfo = moduleGraph.getExportsInfo(module); + mangleExportsInfo(deterministic, exportsInfo, isNamespace); + } + } + ); + }); } } -module.exports = ChunkPrefetchFunctionRuntimeModule; +module.exports = MangleExportsPlugin; /***/ }), -/***/ 17839: +/***/ 54450: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; @@ -108823,315 +106441,241 @@ module.exports = ChunkPrefetchFunctionRuntimeModule; -const RuntimeGlobals = __webpack_require__(49404); -const ChunkPrefetchFunctionRuntimeModule = __webpack_require__(18315); -const ChunkPrefetchStartupRuntimeModule = __webpack_require__(79985); -const ChunkPrefetchTriggerRuntimeModule = __webpack_require__(32123); -const ChunkPreloadTriggerRuntimeModule = __webpack_require__(58929); +const { STAGE_BASIC } = __webpack_require__(68145); +const { runtimeEqual } = __webpack_require__(19655); /** @typedef {import("../Compiler")} Compiler */ -class ChunkPrefetchPreloadPlugin { +class MergeDuplicateChunksPlugin { /** * @param {Compiler} compiler the compiler * @returns {void} */ apply(compiler) { compiler.hooks.compilation.tap( - "ChunkPrefetchPreloadPlugin", + "MergeDuplicateChunksPlugin", compilation => { - compilation.hooks.additionalChunkRuntimeRequirements.tap( - "ChunkPrefetchPreloadPlugin", - (chunk, set, { chunkGraph }) => { - if (chunkGraph.getNumberOfEntryModules(chunk) === 0) return; - const startupChildChunks = chunk.getChildrenOfTypeInOrder( - chunkGraph, - "prefetchOrder" - ); - if (startupChildChunks) { - set.add(RuntimeGlobals.prefetchChunk); - set.add(RuntimeGlobals.onChunksLoaded); - compilation.addRuntimeModule( - chunk, - new ChunkPrefetchStartupRuntimeModule(startupChildChunks) - ); - } - } - ); - compilation.hooks.additionalTreeRuntimeRequirements.tap( - "ChunkPrefetchPreloadPlugin", - (chunk, set, { chunkGraph }) => { - const chunkMap = chunk.getChildIdsByOrdersMap(chunkGraph, false); + compilation.hooks.optimizeChunks.tap( + { + name: "MergeDuplicateChunksPlugin", + stage: STAGE_BASIC + }, + chunks => { + const { chunkGraph, moduleGraph } = compilation; - if (chunkMap.prefetch) { - set.add(RuntimeGlobals.prefetchChunk); - compilation.addRuntimeModule( - chunk, - new ChunkPrefetchTriggerRuntimeModule(chunkMap.prefetch) - ); - } - if (chunkMap.preload) { - set.add(RuntimeGlobals.preloadChunk); - compilation.addRuntimeModule( - chunk, - new ChunkPreloadTriggerRuntimeModule(chunkMap.preload) - ); + // remember already tested chunks for performance + const notDuplicates = new Set(); + + // for each chunk + for (const chunk of chunks) { + // track a Set of all chunk that could be duplicates + let possibleDuplicates; + for (const module of chunkGraph.getChunkModulesIterable(chunk)) { + if (possibleDuplicates === undefined) { + // when possibleDuplicates is not yet set, + // create a new Set from chunks of the current module + // including only chunks with the same number of modules + for (const dup of chunkGraph.getModuleChunksIterable( + module + )) { + if ( + dup !== chunk && + chunkGraph.getNumberOfChunkModules(chunk) === + chunkGraph.getNumberOfChunkModules(dup) && + !notDuplicates.has(dup) + ) { + // delay allocating the new Set until here, reduce memory pressure + if (possibleDuplicates === undefined) { + possibleDuplicates = new Set(); + } + possibleDuplicates.add(dup); + } + } + // when no chunk is possible we can break here + if (possibleDuplicates === undefined) break; + } else { + // validate existing possible duplicates + for (const dup of possibleDuplicates) { + // remove possible duplicate when module is not contained + if (!chunkGraph.isModuleInChunk(module, dup)) { + possibleDuplicates.delete(dup); + } + } + // when all chunks has been removed we can break here + if (possibleDuplicates.size === 0) break; + } + } + + // when we found duplicates + if ( + possibleDuplicates !== undefined && + possibleDuplicates.size > 0 + ) { + outer: for (const otherChunk of possibleDuplicates) { + if (otherChunk.hasRuntime() !== chunk.hasRuntime()) continue; + if (chunkGraph.getNumberOfEntryModules(chunk) > 0) continue; + if (chunkGraph.getNumberOfEntryModules(otherChunk) > 0) + continue; + if (!runtimeEqual(chunk.runtime, otherChunk.runtime)) { + for (const module of chunkGraph.getChunkModulesIterable( + chunk + )) { + const exportsInfo = moduleGraph.getExportsInfo(module); + if ( + !exportsInfo.isEquallyUsed( + chunk.runtime, + otherChunk.runtime + ) + ) { + continue outer; + } + } + } + // merge them + if (chunkGraph.canChunksBeIntegrated(chunk, otherChunk)) { + chunkGraph.integrateChunks(chunk, otherChunk); + compilation.chunks.delete(otherChunk); + } + } + } + + // don't check already processed chunks twice + notDuplicates.add(chunk); } } ); - compilation.hooks.runtimeRequirementInTree - .for(RuntimeGlobals.prefetchChunk) - .tap("ChunkPrefetchPreloadPlugin", (chunk, set) => { - compilation.addRuntimeModule( - chunk, - new ChunkPrefetchFunctionRuntimeModule( - "prefetch", - RuntimeGlobals.prefetchChunk, - RuntimeGlobals.prefetchChunkHandlers - ) - ); - set.add(RuntimeGlobals.prefetchChunkHandlers); - }); - compilation.hooks.runtimeRequirementInTree - .for(RuntimeGlobals.preloadChunk) - .tap("ChunkPrefetchPreloadPlugin", (chunk, set) => { - compilation.addRuntimeModule( - chunk, - new ChunkPrefetchFunctionRuntimeModule( - "preload", - RuntimeGlobals.preloadChunk, - RuntimeGlobals.preloadChunkHandlers - ) - ); - set.add(RuntimeGlobals.preloadChunkHandlers); - }); } ); } } - -module.exports = ChunkPrefetchPreloadPlugin; - - -/***/ }), - -/***/ 79985: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php -*/ - - - -const RuntimeGlobals = __webpack_require__(49404); -const RuntimeModule = __webpack_require__(61439); -const Template = __webpack_require__(92066); - -/** @typedef {import("../Chunk")} Chunk */ -/** @typedef {import("../RuntimeTemplate")} RuntimeTemplate */ - -class ChunkPrefetchStartupRuntimeModule extends RuntimeModule { - /** - * @param {{ onChunks: Chunk[], chunks: Set }[]} startupChunks chunk ids to trigger when chunks are loaded - */ - constructor(startupChunks) { - super("startup prefetch", RuntimeModule.STAGE_TRIGGER); - this.startupChunks = startupChunks; - } - - /** - * @returns {string} runtime code - */ - generate() { - const { startupChunks, chunk } = this; - const { runtimeTemplate } = this.compilation; - return Template.asString( - startupChunks.map( - ({ onChunks, chunks }) => - `${RuntimeGlobals.onChunksLoaded}(0, ${JSON.stringify( - // This need to include itself to delay execution after this chunk has been fully loaded - onChunks.filter(c => c === chunk).map(c => c.id) - )}, ${runtimeTemplate.basicFunction( - "", - chunks.size < 3 - ? Array.from( - chunks, - c => - `${RuntimeGlobals.prefetchChunk}(${JSON.stringify(c.id)});` - ) - : `${JSON.stringify(Array.from(chunks, c => c.id))}.map(${ - RuntimeGlobals.prefetchChunk - });` - )}, 5);` - ) - ); - } -} - -module.exports = ChunkPrefetchStartupRuntimeModule; - - -/***/ }), - -/***/ 32123: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php -*/ - - - -const RuntimeGlobals = __webpack_require__(49404); -const RuntimeModule = __webpack_require__(61439); -const Template = __webpack_require__(92066); - -/** @typedef {import("../RuntimeTemplate")} RuntimeTemplate */ - -class ChunkPrefetchTriggerRuntimeModule extends RuntimeModule { - /** - * @param {Record} chunkMap map from chunk to - */ - constructor(chunkMap) { - super(`chunk prefetch trigger`, RuntimeModule.STAGE_TRIGGER); - this.chunkMap = chunkMap; - } - - /** - * @returns {string} runtime code - */ - generate() { - const { chunkMap } = this; - const { runtimeTemplate } = this.compilation; - const body = [ - "var chunks = chunkToChildrenMap[chunkId];", - `Array.isArray(chunks) && chunks.map(${RuntimeGlobals.prefetchChunk});` - ]; - return Template.asString([ - Template.asString([ - `var chunkToChildrenMap = ${JSON.stringify(chunkMap, null, "\t")};`, - `${ - RuntimeGlobals.ensureChunkHandlers - }.prefetch = ${runtimeTemplate.expressionFunction( - `Promise.all(promises).then(${runtimeTemplate.basicFunction( - "", - body - )})`, - "chunkId, promises" - )};` - ]) - ]); - } -} - -module.exports = ChunkPrefetchTriggerRuntimeModule; +module.exports = MergeDuplicateChunksPlugin; /***/ }), -/***/ 58929: +/***/ 85813: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; /* MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra */ -const RuntimeGlobals = __webpack_require__(49404); -const RuntimeModule = __webpack_require__(61439); -const Template = __webpack_require__(92066); +const { STAGE_ADVANCED } = __webpack_require__(68145); +const createSchemaValidation = __webpack_require__(77695); -/** @typedef {import("../RuntimeTemplate")} RuntimeTemplate */ +/** @typedef {import("../../declarations/plugins/optimize/MinChunkSizePlugin").MinChunkSizePluginOptions} MinChunkSizePluginOptions */ +/** @typedef {import("../Chunk")} Chunk */ +/** @typedef {import("../Compiler")} Compiler */ -class ChunkPreloadTriggerRuntimeModule extends RuntimeModule { - /** - * @param {Record} chunkMap map from chunk to chunks - */ - constructor(chunkMap) { - super(`chunk preload trigger`, RuntimeModule.STAGE_TRIGGER); - this.chunkMap = chunkMap; +const validate = createSchemaValidation( + __webpack_require__(60902), + () => __webpack_require__(66480), + { + name: "Min Chunk Size Plugin", + baseDataPath: "options" } +); +class MinChunkSizePlugin { /** - * @returns {string} runtime code + * @param {MinChunkSizePluginOptions} options options object */ - generate() { - const { chunkMap } = this; - const { runtimeTemplate } = this.compilation; - const body = [ - "var chunks = chunkToChildrenMap[chunkId];", - `Array.isArray(chunks) && chunks.map(${RuntimeGlobals.preloadChunk});` - ]; - return Template.asString([ - Template.asString([ - `var chunkToChildrenMap = ${JSON.stringify(chunkMap, null, "\t")};`, - `${ - RuntimeGlobals.ensureChunkHandlers - }.preload = ${runtimeTemplate.basicFunction("chunkId", body)};` - ]) - ]); - } -} - -module.exports = ChunkPreloadTriggerRuntimeModule; - - -/***/ }), - -/***/ 70119: -/***/ (function(module) { - -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ - - - -/** @typedef {import("./RuleSetCompiler")} RuleSetCompiler */ - -class BasicEffectRulePlugin { - constructor(ruleProperty, effectType) { - this.ruleProperty = ruleProperty; - this.effectType = effectType || ruleProperty; + constructor(options) { + validate(options); + this.options = options; } /** - * @param {RuleSetCompiler} ruleSetCompiler the rule set compiler + * Apply the plugin + * @param {Compiler} compiler the compiler instance * @returns {void} */ - apply(ruleSetCompiler) { - ruleSetCompiler.hooks.rule.tap( - "BasicEffectRulePlugin", - (path, rule, unhandledProperties, result, references) => { - if (unhandledProperties.has(this.ruleProperty)) { - unhandledProperties.delete(this.ruleProperty); + apply(compiler) { + const options = this.options; + const minChunkSize = options.minChunkSize; + compiler.hooks.compilation.tap("MinChunkSizePlugin", compilation => { + compilation.hooks.optimizeChunks.tap( + { + name: "MinChunkSizePlugin", + stage: STAGE_ADVANCED + }, + chunks => { + const chunkGraph = compilation.chunkGraph; + const equalOptions = { + chunkOverhead: 1, + entryChunkMultiplicator: 1 + }; - const value = rule[this.ruleProperty]; + const chunkSizesMap = new Map(); + /** @type {[Chunk, Chunk][]} */ + const combinations = []; + /** @type {Chunk[]} */ + const smallChunks = []; + const visitedChunks = []; + for (const a of chunks) { + // check if one of the chunks sizes is smaller than the minChunkSize + // and filter pairs that can NOT be integrated! + if (chunkGraph.getChunkSize(a, equalOptions) < minChunkSize) { + smallChunks.push(a); + for (const b of visitedChunks) { + if (chunkGraph.canChunksBeIntegrated(b, a)) + combinations.push([b, a]); + } + } else { + for (const b of smallChunks) { + if (chunkGraph.canChunksBeIntegrated(b, a)) + combinations.push([b, a]); + } + } + chunkSizesMap.set(a, chunkGraph.getChunkSize(a, options)); + visitedChunks.push(a); + } - result.effects.push({ - type: this.effectType, - value - }); + const sortedSizeFilteredExtendedPairCombinations = combinations + .map(pair => { + // extend combination pairs with size and integrated size + const a = chunkSizesMap.get(pair[0]); + const b = chunkSizesMap.get(pair[1]); + const ab = chunkGraph.getIntegratedChunksSize( + pair[0], + pair[1], + options + ); + /** @type {[number, number, Chunk, Chunk]} */ + const extendedPair = [a + b - ab, ab, pair[0], pair[1]]; + return extendedPair; + }) + .sort((a, b) => { + // sadly javascript does an in place sort here + // sort by size + const diff = b[0] - a[0]; + if (diff !== 0) return diff; + return a[1] - b[1]; + }); + + if (sortedSizeFilteredExtendedPairCombinations.length === 0) return; + + const pair = sortedSizeFilteredExtendedPairCombinations[0]; + + chunkGraph.integrateChunks(pair[2], pair[3]); + compilation.chunks.delete(pair[3]); + return true; } - } - ); + ); + }); } } - -module.exports = BasicEffectRulePlugin; +module.exports = MinChunkSizePlugin; /***/ }), -/***/ 99083: -/***/ (function(module) { +/***/ 46681: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; /* @@ -109141,52 +106685,35 @@ module.exports = BasicEffectRulePlugin; -/** @typedef {import("./RuleSetCompiler")} RuleSetCompiler */ -/** @typedef {import("./RuleSetCompiler").RuleCondition} RuleCondition */ - -class BasicMatcherRulePlugin { - constructor(ruleProperty, dataProperty, invert) { - this.ruleProperty = ruleProperty; - this.dataProperty = dataProperty || ruleProperty; - this.invert = invert || false; - } +const SizeFormatHelpers = __webpack_require__(15979); +const WebpackError = __webpack_require__(68422); - /** - * @param {RuleSetCompiler} ruleSetCompiler the rule set compiler - * @returns {void} - */ - apply(ruleSetCompiler) { - ruleSetCompiler.hooks.rule.tap( - "BasicMatcherRulePlugin", - (path, rule, unhandledProperties, result) => { - if (unhandledProperties.has(this.ruleProperty)) { - unhandledProperties.delete(this.ruleProperty); - const value = rule[this.ruleProperty]; - const condition = ruleSetCompiler.compileCondition( - `${path}.${this.ruleProperty}`, - value - ); - const fn = condition.fn; - result.conditions.push({ - property: this.dataProperty, - matchWhenEmpty: this.invert - ? !condition.matchWhenEmpty - : condition.matchWhenEmpty, - fn: this.invert ? v => !fn(v) : fn - }); - } - } +class MinMaxSizeWarning extends WebpackError { + constructor(keys, minSize, maxSize) { + let keysMessage = "Fallback cache group"; + if (keys) { + keysMessage = + keys.length > 1 + ? `Cache groups ${keys.sort().join(", ")}` + : `Cache group ${keys[0]}`; + } + super( + `SplitChunksPlugin\n` + + `${keysMessage}\n` + + `Configured minSize (${SizeFormatHelpers.formatSize(minSize)}) is ` + + `bigger than maxSize (${SizeFormatHelpers.formatSize(maxSize)}).\n` + + "This seem to be a invalid optimization.splitChunks configuration." ); } } -module.exports = BasicMatcherRulePlugin; +module.exports = MinMaxSizeWarning; /***/ }), -/***/ 61166: -/***/ (function(module) { +/***/ 29585: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; /* @@ -109196,2170 +106723,3892 @@ module.exports = BasicMatcherRulePlugin; -/** @typedef {import("./RuleSetCompiler")} RuleSetCompiler */ -/** @typedef {import("./RuleSetCompiler").RuleCondition} RuleCondition */ +const asyncLib = __webpack_require__(36386); +const ChunkGraph = __webpack_require__(97860); +const ModuleGraph = __webpack_require__(20258); +const { STAGE_DEFAULT } = __webpack_require__(68145); +const HarmonyImportDependency = __webpack_require__(19577); +const { compareModulesByIdentifier } = __webpack_require__(26296); +const { + intersectRuntime, + mergeRuntimeOwned, + filterRuntime, + runtimeToString, + mergeRuntime +} = __webpack_require__(19655); +const ConcatenatedModule = __webpack_require__(1881); -class ObjectMatcherRulePlugin { - constructor(ruleProperty, dataProperty) { - this.ruleProperty = ruleProperty; - this.dataProperty = dataProperty || ruleProperty; +/** @typedef {import("../Compilation")} Compilation */ +/** @typedef {import("../Compiler")} Compiler */ +/** @typedef {import("../Module")} Module */ +/** @typedef {import("../RequestShortener")} RequestShortener */ +/** @typedef {import("../util/runtime").RuntimeSpec} RuntimeSpec */ + +/** + * @typedef {Object} Statistics + * @property {number} cached + * @property {number} alreadyInConfig + * @property {number} invalidModule + * @property {number} incorrectChunks + * @property {number} incorrectDependency + * @property {number} incorrectModuleDependency + * @property {number} incorrectChunksOfImporter + * @property {number} incorrectRuntimeCondition + * @property {number} importerFailed + * @property {number} added + */ + +const formatBailoutReason = msg => { + return "ModuleConcatenation bailout: " + msg; +}; + +class ModuleConcatenationPlugin { + constructor(options) { + if (typeof options !== "object") options = {}; + this.options = options; } /** - * @param {RuleSetCompiler} ruleSetCompiler the rule set compiler + * Apply the plugin + * @param {Compiler} compiler the compiler instance * @returns {void} */ - apply(ruleSetCompiler) { - const { ruleProperty, dataProperty } = this; - ruleSetCompiler.hooks.rule.tap( - "ObjectMatcherRulePlugin", - (path, rule, unhandledProperties, result) => { - if (unhandledProperties.has(ruleProperty)) { - unhandledProperties.delete(ruleProperty); - const value = rule[ruleProperty]; - for (const property of Object.keys(value)) { - const nestedDataProperties = property.split("."); - const condition = ruleSetCompiler.compileCondition( - `${path}.${ruleProperty}.${property}`, - value[property] - ); - result.conditions.push({ - property: [dataProperty, ...nestedDataProperties], - matchWhenEmpty: condition.matchWhenEmpty, - fn: condition.fn - }); - } + apply(compiler) { + const { _backCompat: backCompat } = compiler; + compiler.hooks.compilation.tap("ModuleConcatenationPlugin", compilation => { + const moduleGraph = compilation.moduleGraph; + const bailoutReasonMap = new Map(); + + const setBailoutReason = (module, reason) => { + setInnerBailoutReason(module, reason); + moduleGraph + .getOptimizationBailout(module) + .push( + typeof reason === "function" + ? rs => formatBailoutReason(reason(rs)) + : formatBailoutReason(reason) + ); + }; + + const setInnerBailoutReason = (module, reason) => { + bailoutReasonMap.set(module, reason); + }; + + const getInnerBailoutReason = (module, requestShortener) => { + const reason = bailoutReasonMap.get(module); + if (typeof reason === "function") return reason(requestShortener); + return reason; + }; + + const formatBailoutWarning = (module, problem) => requestShortener => { + if (typeof problem === "function") { + return formatBailoutReason( + `Cannot concat with ${module.readableIdentifier( + requestShortener + )}: ${problem(requestShortener)}` + ); } - } - ); - } -} + const reason = getInnerBailoutReason(module, requestShortener); + const reasonWithPrefix = reason ? `: ${reason}` : ""; + if (module === problem) { + return formatBailoutReason( + `Cannot concat with ${module.readableIdentifier( + requestShortener + )}${reasonWithPrefix}` + ); + } else { + return formatBailoutReason( + `Cannot concat with ${module.readableIdentifier( + requestShortener + )} because of ${problem.readableIdentifier( + requestShortener + )}${reasonWithPrefix}` + ); + } + }; -module.exports = ObjectMatcherRulePlugin; + compilation.hooks.optimizeChunkModules.tapAsync( + { + name: "ModuleConcatenationPlugin", + stage: STAGE_DEFAULT + }, + (allChunks, modules, callback) => { + const logger = compilation.getLogger( + "webpack.ModuleConcatenationPlugin" + ); + const { chunkGraph, moduleGraph } = compilation; + const relevantModules = []; + const possibleInners = new Set(); + const context = { + chunkGraph, + moduleGraph + }; + logger.time("select relevant modules"); + for (const module of modules) { + let canBeRoot = true; + let canBeInner = true; + const bailoutReason = module.getConcatenationBailoutReason(context); + if (bailoutReason) { + setBailoutReason(module, bailoutReason); + continue; + } -/***/ }), + // Must not be an async module + if (moduleGraph.isAsync(module)) { + setBailoutReason(module, `Module is async`); + continue; + } -/***/ 23246: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + // Must be in strict mode + if (!module.buildInfo.strict) { + setBailoutReason(module, `Module is not in strict mode`); + continue; + } -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ + // Module must be in any chunk (we don't want to do useless work) + if (chunkGraph.getNumberOfModuleChunks(module) === 0) { + setBailoutReason(module, "Module is not in any chunk"); + continue; + } + // Exports must be known (and not dynamic) + const exportsInfo = moduleGraph.getExportsInfo(module); + const relevantExports = exportsInfo.getRelevantExports(undefined); + const unknownReexports = relevantExports.filter(exportInfo => { + return ( + exportInfo.isReexport() && !exportInfo.getTarget(moduleGraph) + ); + }); + if (unknownReexports.length > 0) { + setBailoutReason( + module, + `Reexports in this module do not have a static target (${Array.from( + unknownReexports, + exportInfo => + `${ + exportInfo.name || "other exports" + }: ${exportInfo.getUsedInfo()}` + ).join(", ")})` + ); + continue; + } + // Root modules must have a static list of exports + const unknownProvidedExports = relevantExports.filter( + exportInfo => { + return exportInfo.provided !== true; + } + ); + if (unknownProvidedExports.length > 0) { + setBailoutReason( + module, + `List of module exports is dynamic (${Array.from( + unknownProvidedExports, + exportInfo => + `${ + exportInfo.name || "other exports" + }: ${exportInfo.getProvidedInfo()} and ${exportInfo.getUsedInfo()}` + ).join(", ")})` + ); + canBeRoot = false; + } -const { SyncHook } = __webpack_require__(34718); + // Module must not be an entry point + if (chunkGraph.isEntryModule(module)) { + setInnerBailoutReason(module, "Module is an entry point"); + canBeInner = false; + } -/** - * @typedef {Object} RuleCondition - * @property {string | string[]} property - * @property {boolean} matchWhenEmpty - * @property {function(string): boolean} fn - */ + if (canBeRoot) relevantModules.push(module); + if (canBeInner) possibleInners.add(module); + } + logger.timeEnd("select relevant modules"); + logger.debug( + `${relevantModules.length} potential root modules, ${possibleInners.size} potential inner modules` + ); + // sort by depth + // modules with lower depth are more likely suited as roots + // this improves performance, because modules already selected as inner are skipped + logger.time("sort relevant modules"); + relevantModules.sort((a, b) => { + return moduleGraph.getDepth(a) - moduleGraph.getDepth(b); + }); + logger.timeEnd("sort relevant modules"); -/** - * @typedef {Object} Condition - * @property {boolean} matchWhenEmpty - * @property {function(string): boolean} fn - */ + /** @type {Statistics} */ + const stats = { + cached: 0, + alreadyInConfig: 0, + invalidModule: 0, + incorrectChunks: 0, + incorrectDependency: 0, + incorrectModuleDependency: 0, + incorrectChunksOfImporter: 0, + incorrectRuntimeCondition: 0, + importerFailed: 0, + added: 0 + }; + let statsCandidates = 0; + let statsSizeSum = 0; + let statsEmptyConfigurations = 0; -/** - * @typedef {Object} CompiledRule - * @property {RuleCondition[]} conditions - * @property {(Effect|function(object): Effect[])[]} effects - * @property {CompiledRule[]=} rules - * @property {CompiledRule[]=} oneOf - */ + logger.time("find modules to concatenate"); + const concatConfigurations = []; + const usedAsInner = new Set(); + for (const currentRoot of relevantModules) { + // when used by another configuration as inner: + // the other configuration is better and we can skip this one + // TODO reconsider that when it's only used in a different runtime + if (usedAsInner.has(currentRoot)) continue; + + let chunkRuntime = undefined; + for (const r of chunkGraph.getModuleRuntimes(currentRoot)) { + chunkRuntime = mergeRuntimeOwned(chunkRuntime, r); + } + const exportsInfo = moduleGraph.getExportsInfo(currentRoot); + const filteredRuntime = filterRuntime(chunkRuntime, r => + exportsInfo.isModuleUsed(r) + ); + const activeRuntime = + filteredRuntime === true + ? chunkRuntime + : filteredRuntime === false + ? undefined + : filteredRuntime; -/** - * @typedef {Object} Effect - * @property {string} type - * @property {any} value - */ + // create a configuration with the root + const currentConfiguration = new ConcatConfiguration( + currentRoot, + activeRuntime + ); -/** - * @typedef {Object} RuleSet - * @property {Map} references map of references in the rule set (may grow over time) - * @property {function(object): Effect[]} exec execute the rule set - */ + // cache failures to add modules + const failureCache = new Map(); -class RuleSetCompiler { - constructor(plugins) { - this.hooks = Object.freeze({ - /** @type {SyncHook<[string, object, Set, CompiledRule, Map]>} */ - rule: new SyncHook([ - "path", - "rule", - "unhandledProperties", - "compiledRule", - "references" - ]) - }); - if (plugins) { - for (const plugin of plugins) { - plugin.apply(this); - } - } - } + // potential optional import candidates + /** @type {Set} */ + const candidates = new Set(); - /** - * @param {object[]} ruleSet raw user provided rules - * @returns {RuleSet} compiled RuleSet - */ - compile(ruleSet) { - const refs = new Map(); - const rules = this.compileRules("ruleSet", ruleSet, refs); + // try to add all imports + for (const imp of this._getImports( + compilation, + currentRoot, + activeRuntime + )) { + candidates.add(imp); + } - /** - * @param {object} data data passed in - * @param {CompiledRule} rule the compiled rule - * @param {Effect[]} effects an array where effects are pushed to - * @returns {boolean} true, if the rule has matched - */ - const execRule = (data, rule, effects) => { - for (const condition of rule.conditions) { - const p = condition.property; - if (Array.isArray(p)) { - let current = data; - for (const subProperty of p) { - if ( - current && - typeof current === "object" && - Object.prototype.hasOwnProperty.call(current, subProperty) - ) { - current = current[subProperty]; + for (const imp of candidates) { + const impCandidates = new Set(); + const problem = this._tryToAdd( + compilation, + currentConfiguration, + imp, + chunkRuntime, + activeRuntime, + possibleInners, + impCandidates, + failureCache, + chunkGraph, + true, + stats + ); + if (problem) { + failureCache.set(imp, problem); + currentConfiguration.addWarning(imp, problem); + } else { + for (const c of impCandidates) { + candidates.add(c); + } + } + } + statsCandidates += candidates.size; + if (!currentConfiguration.isEmpty()) { + const modules = currentConfiguration.getModules(); + statsSizeSum += modules.size; + concatConfigurations.push(currentConfiguration); + for (const module of modules) { + if (module !== currentConfiguration.rootModule) { + usedAsInner.add(module); + } + } } else { - current = undefined; - break; + statsEmptyConfigurations++; + const optimizationBailouts = + moduleGraph.getOptimizationBailout(currentRoot); + for (const warning of currentConfiguration.getWarningsSorted()) { + optimizationBailouts.push( + formatBailoutWarning(warning[0], warning[1]) + ); + } } } - if (current !== undefined) { - if (!condition.fn(current)) return false; - continue; - } - } else if (p in data) { - const value = data[p]; - if (value !== undefined) { - if (!condition.fn(value)) return false; - continue; - } - } - if (!condition.matchWhenEmpty) { - return false; - } - } - for (const effect of rule.effects) { - if (typeof effect === "function") { - const returnedEffects = effect(data); - for (const effect of returnedEffects) { - effects.push(effect); - } - } else { - effects.push(effect); - } - } - if (rule.rules) { - for (const childRule of rule.rules) { - execRule(data, childRule, effects); - } - } - if (rule.oneOf) { - for (const childRule of rule.oneOf) { - if (execRule(data, childRule, effects)) { - break; - } - } - } - return true; - }; + logger.timeEnd("find modules to concatenate"); + logger.debug( + `${ + concatConfigurations.length + } successful concat configurations (avg size: ${ + statsSizeSum / concatConfigurations.length + }), ${statsEmptyConfigurations} bailed out completely` + ); + logger.debug( + `${statsCandidates} candidates were considered for adding (${stats.cached} cached failure, ${stats.alreadyInConfig} already in config, ${stats.invalidModule} invalid module, ${stats.incorrectChunks} incorrect chunks, ${stats.incorrectDependency} incorrect dependency, ${stats.incorrectChunksOfImporter} incorrect chunks of importer, ${stats.incorrectModuleDependency} incorrect module dependency, ${stats.incorrectRuntimeCondition} incorrect runtime condition, ${stats.importerFailed} importer failed, ${stats.added} added)` + ); + // HACK: Sort configurations by length and start with the longest one + // to get the biggest groups possible. Used modules are marked with usedModules + // TODO: Allow to reuse existing configuration while trying to add dependencies. + // This would improve performance. O(n^2) -> O(n) + logger.time(`sort concat configurations`); + concatConfigurations.sort((a, b) => { + return b.modules.size - a.modules.size; + }); + logger.timeEnd(`sort concat configurations`); + const usedModules = new Set(); - return { - references: refs, - exec: data => { - /** @type {Effect[]} */ - const effects = []; - for (const rule of rules) { - execRule(data, rule, effects); - } - return effects; - } - }; - } + logger.time("create concatenated modules"); + asyncLib.each( + concatConfigurations, + (concatConfiguration, callback) => { + const rootModule = concatConfiguration.rootModule; - /** - * @param {string} path current path - * @param {object[]} rules the raw rules provided by user - * @param {Map} refs references - * @returns {CompiledRule[]} rules - */ - compileRules(path, rules, refs) { - return rules.map((rule, i) => - this.compileRule(`${path}[${i}]`, rule, refs) - ); - } + // Avoid overlapping configurations + // TODO: remove this when todo above is fixed + if (usedModules.has(rootModule)) return callback(); + const modules = concatConfiguration.getModules(); + for (const m of modules) { + usedModules.add(m); + } - /** - * @param {string} path current path - * @param {object} rule the raw rule provided by user - * @param {Map} refs references - * @returns {CompiledRule} normalized and compiled rule for processing - */ - compileRule(path, rule, refs) { - const unhandledProperties = new Set( - Object.keys(rule).filter(key => rule[key] !== undefined) - ); + // Create a new ConcatenatedModule + let newModule = ConcatenatedModule.create( + rootModule, + modules, + concatConfiguration.runtime, + compiler.root, + compilation.outputOptions.hashFunction + ); - /** @type {CompiledRule} */ - const compiledRule = { - conditions: [], - effects: [], - rules: undefined, - oneOf: undefined - }; + const build = () => { + newModule.build( + compiler.options, + compilation, + null, + null, + err => { + if (err) { + if (!err.module) { + err.module = newModule; + } + return callback(err); + } + integrate(); + } + ); + }; - this.hooks.rule.call(path, rule, unhandledProperties, compiledRule, refs); + const integrate = () => { + if (backCompat) { + ChunkGraph.setChunkGraphForModule(newModule, chunkGraph); + ModuleGraph.setModuleGraphForModule(newModule, moduleGraph); + } - if (unhandledProperties.has("rules")) { - unhandledProperties.delete("rules"); - const rules = rule.rules; - if (!Array.isArray(rules)) - throw this.error(path, rules, "Rule.rules must be an array of rules"); - compiledRule.rules = this.compileRules(`${path}.rules`, rules, refs); - } + for (const warning of concatConfiguration.getWarningsSorted()) { + moduleGraph + .getOptimizationBailout(newModule) + .push(formatBailoutWarning(warning[0], warning[1])); + } + moduleGraph.cloneModuleAttributes(rootModule, newModule); + for (const m of modules) { + // add to builtModules when one of the included modules was built + if (compilation.builtModules.has(m)) { + compilation.builtModules.add(newModule); + } + if (m !== rootModule) { + // attach external references to the concatenated module too + moduleGraph.copyOutgoingModuleConnections( + m, + newModule, + c => { + return ( + c.originModule === m && + !( + c.dependency instanceof HarmonyImportDependency && + modules.has(c.module) + ) + ); + } + ); + // remove module from chunk + for (const chunk of chunkGraph.getModuleChunksIterable( + rootModule + )) { + chunkGraph.disconnectChunkAndModule(chunk, m); + } + } + } + compilation.modules.delete(rootModule); + ChunkGraph.clearChunkGraphForModule(rootModule); + ModuleGraph.clearModuleGraphForModule(rootModule); - if (unhandledProperties.has("oneOf")) { - unhandledProperties.delete("oneOf"); - const oneOf = rule.oneOf; - if (!Array.isArray(oneOf)) - throw this.error(path, oneOf, "Rule.oneOf must be an array of rules"); - compiledRule.oneOf = this.compileRules(`${path}.oneOf`, oneOf, refs); - } + // remove module from chunk + chunkGraph.replaceModule(rootModule, newModule); + // replace module references with the concatenated module + moduleGraph.moveModuleConnections(rootModule, newModule, c => { + const otherModule = + c.module === rootModule ? c.originModule : c.module; + const innerConnection = + c.dependency instanceof HarmonyImportDependency && + modules.has(otherModule); + return !innerConnection; + }); + // add concatenated module to the compilation + compilation.modules.add(newModule); - if (unhandledProperties.size > 0) { - throw this.error( - path, - rule, - `Properties ${Array.from(unhandledProperties).join(", ")} are unknown` - ); - } + callback(); + }; - return compiledRule; + build(); + }, + err => { + logger.timeEnd("create concatenated modules"); + process.nextTick(callback.bind(null, err)); + } + ); + } + ); + }); } /** - * @param {string} path current path - * @param {any} condition user provided condition value - * @returns {Condition} compiled condition + * @param {Compilation} compilation the compilation + * @param {Module} module the module to be added + * @param {RuntimeSpec} runtime the runtime scope + * @returns {Set} the imported modules */ - compileCondition(path, condition) { - if (condition === "") { - return { - matchWhenEmpty: true, - fn: str => str === "" - }; - } - if (!condition) { - throw this.error( - path, - condition, - "Expected condition but got falsy value" - ); - } - if (typeof condition === "string") { - return { - matchWhenEmpty: condition.length === 0, - fn: str => typeof str === "string" && str.startsWith(condition) - }; - } - if (typeof condition === "function") { - try { - return { - matchWhenEmpty: condition(""), - fn: condition - }; - } catch (err) { - throw this.error( - path, - condition, - "Evaluation of condition function threw error" - ); + _getImports(compilation, module, runtime) { + const moduleGraph = compilation.moduleGraph; + const set = new Set(); + for (const dep of module.dependencies) { + // Get reference info only for harmony Dependencies + if (!(dep instanceof HarmonyImportDependency)) continue; + + const connection = moduleGraph.getConnection(dep); + // Reference is valid and has a module + if ( + !connection || + !connection.module || + !connection.isTargetActive(runtime) + ) { + continue; } - } - if (condition instanceof RegExp) { - return { - matchWhenEmpty: condition.test(""), - fn: v => typeof v === "string" && condition.test(v) - }; - } - if (Array.isArray(condition)) { - const items = condition.map((c, i) => - this.compileCondition(`${path}[${i}]`, c) - ); - return this.combineConditionsOr(items); - } - if (typeof condition !== "object") { - throw this.error( - path, - condition, - `Unexpected ${typeof condition} when condition was expected` + const importedNames = compilation.getDependencyReferencedExports( + dep, + undefined ); - } - const conditions = []; - for (const key of Object.keys(condition)) { - const value = condition[key]; - switch (key) { - case "or": - if (value) { - if (!Array.isArray(value)) { - throw this.error( - `${path}.or`, - condition.and, - "Expected array of conditions" - ); - } - conditions.push(this.compileCondition(`${path}.or`, value)); - } - break; - case "and": - if (value) { - if (!Array.isArray(value)) { - throw this.error( - `${path}.and`, - condition.and, - "Expected array of conditions" - ); - } - let i = 0; - for (const item of value) { - conditions.push(this.compileCondition(`${path}.and[${i}]`, item)); - i++; - } - } - break; - case "not": - if (value) { - const matcher = this.compileCondition(`${path}.not`, value); - const fn = matcher.fn; - conditions.push({ - matchWhenEmpty: !matcher.matchWhenEmpty, - fn: v => !fn(v) - }); - } - break; - default: - throw this.error( - `${path}.${key}`, - condition[key], - `Unexpected property ${key} in condition` - ); + if ( + importedNames.every(i => + Array.isArray(i) ? i.length > 0 : i.name.length > 0 + ) || + Array.isArray(moduleGraph.getProvidedExports(module)) + ) { + set.add(connection.module); } } - if (conditions.length === 0) { - throw this.error( - path, - condition, - "Expected condition, but got empty thing" - ); + return set; + } + + /** + * @param {Compilation} compilation webpack compilation + * @param {ConcatConfiguration} config concat configuration (will be modified when added) + * @param {Module} module the module to be added + * @param {RuntimeSpec} runtime the runtime scope of the generated code + * @param {RuntimeSpec} activeRuntime the runtime scope of the root module + * @param {Set} possibleModules modules that are candidates + * @param {Set} candidates list of potential candidates (will be added to) + * @param {Map} failureCache cache for problematic modules to be more performant + * @param {ChunkGraph} chunkGraph the chunk graph + * @param {boolean} avoidMutateOnFailure avoid mutating the config when adding fails + * @param {Statistics} statistics gathering metrics + * @returns {Module | function(RequestShortener): string} the problematic module + */ + _tryToAdd( + compilation, + config, + module, + runtime, + activeRuntime, + possibleModules, + candidates, + failureCache, + chunkGraph, + avoidMutateOnFailure, + statistics + ) { + const cacheEntry = failureCache.get(module); + if (cacheEntry) { + statistics.cached++; + return cacheEntry; + } + + // Already added? + if (config.has(module)) { + statistics.alreadyInConfig++; + return null; } - return this.combineConditionsAnd(conditions); - } - /** - * @param {Condition[]} conditions some conditions - * @returns {Condition} merged condition - */ - combineConditionsOr(conditions) { - if (conditions.length === 0) { - return { - matchWhenEmpty: false, - fn: () => false - }; - } else if (conditions.length === 1) { - return conditions[0]; - } else { - return { - matchWhenEmpty: conditions.some(c => c.matchWhenEmpty), - fn: v => conditions.some(c => c.fn(v)) - }; + // Not possible to add? + if (!possibleModules.has(module)) { + statistics.invalidModule++; + failureCache.set(module, module); // cache failures for performance + return module; } - } - /** - * @param {Condition[]} conditions some conditions - * @returns {Condition} merged condition - */ - combineConditionsAnd(conditions) { - if (conditions.length === 0) { - return { - matchWhenEmpty: false, - fn: () => false - }; - } else if (conditions.length === 1) { - return conditions[0]; - } else { - return { - matchWhenEmpty: conditions.every(c => c.matchWhenEmpty), - fn: v => conditions.every(c => c.fn(v)) + // Module must be in the correct chunks + const missingChunks = Array.from( + chunkGraph.getModuleChunksIterable(config.rootModule) + ).filter(chunk => !chunkGraph.isModuleInChunk(module, chunk)); + if (missingChunks.length > 0) { + const problem = requestShortener => { + const missingChunksList = Array.from( + new Set(missingChunks.map(chunk => chunk.name || "unnamed chunk(s)")) + ).sort(); + const chunks = Array.from( + new Set( + Array.from(chunkGraph.getModuleChunksIterable(module)).map( + chunk => chunk.name || "unnamed chunk(s)" + ) + ) + ).sort(); + return `Module ${module.readableIdentifier( + requestShortener + )} is not in the same chunk(s) (expected in chunk(s) ${missingChunksList.join( + ", " + )}, module is in chunk(s) ${chunks.join(", ")})`; }; + statistics.incorrectChunks++; + failureCache.set(module, problem); // cache failures for performance + return problem; } - } - /** - * @param {string} path current path - * @param {any} value value at the error location - * @param {string} message message explaining the problem - * @returns {Error} an error object - */ - error(path, value, message) { - return new Error( - `Compiling RuleSet failed: ${message} (at ${path}: ${value})` - ); - } -} + const moduleGraph = compilation.moduleGraph; -module.exports = RuleSetCompiler; + const incomingConnections = + moduleGraph.getIncomingConnectionsByOriginModule(module); + const incomingConnectionsFromNonModules = + incomingConnections.get(null) || incomingConnections.get(undefined); + if (incomingConnectionsFromNonModules) { + const activeNonModulesConnections = + incomingConnectionsFromNonModules.filter(connection => { + // We are not interested in inactive connections + // or connections without dependency + return connection.isActive(runtime) || connection.dependency; + }); + if (activeNonModulesConnections.length > 0) { + const problem = requestShortener => { + const importingExplanations = new Set( + activeNonModulesConnections.map(c => c.explanation).filter(Boolean) + ); + const explanations = Array.from(importingExplanations).sort(); + return `Module ${module.readableIdentifier( + requestShortener + )} is referenced ${ + explanations.length > 0 + ? `by: ${explanations.join(", ")}` + : "in an unsupported way" + }`; + }; + statistics.incorrectDependency++; + failureCache.set(module, problem); // cache failures for performance + return problem; + } + } -/***/ }), + /** @type {Map} */ + const incomingConnectionsFromModules = new Map(); + for (const [originModule, connections] of incomingConnections) { + if (originModule) { + // Ignore connection from orphan modules + if (chunkGraph.getNumberOfModuleChunks(originModule) === 0) continue; -/***/ 42541: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + // We don't care for connections from other runtimes + let originRuntime = undefined; + for (const r of chunkGraph.getModuleRuntimes(originModule)) { + originRuntime = mergeRuntimeOwned(originRuntime, r); + } -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ + if (!intersectRuntime(runtime, originRuntime)) continue; + // We are not interested in inactive connections + const activeConnections = connections.filter(connection => + connection.isActive(runtime) + ); + if (activeConnections.length > 0) + incomingConnectionsFromModules.set(originModule, activeConnections); + } + } + const incomingModules = Array.from(incomingConnectionsFromModules.keys()); -const util = __webpack_require__(31669); + // Module must be in the same chunks like the referencing module + const otherChunkModules = incomingModules.filter(originModule => { + for (const chunk of chunkGraph.getModuleChunksIterable( + config.rootModule + )) { + if (!chunkGraph.isModuleInChunk(originModule, chunk)) { + return true; + } + } + return false; + }); + if (otherChunkModules.length > 0) { + const problem = requestShortener => { + const names = otherChunkModules + .map(m => m.readableIdentifier(requestShortener)) + .sort(); + return `Module ${module.readableIdentifier( + requestShortener + )} is referenced from different chunks by these modules: ${names.join( + ", " + )}`; + }; + statistics.incorrectChunksOfImporter++; + failureCache.set(module, problem); // cache failures for performance + return problem; + } -/** @typedef {import("./RuleSetCompiler")} RuleSetCompiler */ -/** @typedef {import("./RuleSetCompiler").Effect} Effect */ + /** @type {Map} */ + const nonHarmonyConnections = new Map(); + for (const [originModule, connections] of incomingConnectionsFromModules) { + const selected = connections.filter( + connection => + !connection.dependency || + !(connection.dependency instanceof HarmonyImportDependency) + ); + if (selected.length > 0) + nonHarmonyConnections.set(originModule, connections); + } + if (nonHarmonyConnections.size > 0) { + const problem = requestShortener => { + const names = Array.from(nonHarmonyConnections) + .map(([originModule, connections]) => { + return `${originModule.readableIdentifier( + requestShortener + )} (referenced with ${Array.from( + new Set( + connections + .map(c => c.dependency && c.dependency.type) + .filter(Boolean) + ) + ) + .sort() + .join(", ")})`; + }) + .sort(); + return `Module ${module.readableIdentifier( + requestShortener + )} is referenced from these modules with unsupported syntax: ${names.join( + ", " + )}`; + }; + statistics.incorrectModuleDependency++; + failureCache.set(module, problem); // cache failures for performance + return problem; + } -class UseEffectRulePlugin { - /** - * @param {RuleSetCompiler} ruleSetCompiler the rule set compiler - * @returns {void} - */ - apply(ruleSetCompiler) { - ruleSetCompiler.hooks.rule.tap( - "UseEffectRulePlugin", - (path, rule, unhandledProperties, result, references) => { - const conflictWith = (property, correctProperty) => { - if (unhandledProperties.has(property)) { - throw ruleSetCompiler.error( - `${path}.${property}`, - rule[property], - `A Rule must not have a '${property}' property when it has a '${correctProperty}' property` + if (runtime !== undefined && typeof runtime !== "string") { + // Module must be consistently referenced in the same runtimes + /** @type {{ originModule: Module, runtimeCondition: RuntimeSpec }[]} */ + const otherRuntimeConnections = []; + outer: for (const [ + originModule, + connections + ] of incomingConnectionsFromModules) { + /** @type {false | RuntimeSpec} */ + let currentRuntimeCondition = false; + for (const connection of connections) { + const runtimeCondition = filterRuntime(runtime, runtime => { + return connection.isTargetActive(runtime); + }); + if (runtimeCondition === false) continue; + if (runtimeCondition === true) continue outer; + if (currentRuntimeCondition !== false) { + currentRuntimeCondition = mergeRuntime( + currentRuntimeCondition, + runtimeCondition ); + } else { + currentRuntimeCondition = runtimeCondition; } + } + if (currentRuntimeCondition !== false) { + otherRuntimeConnections.push({ + originModule, + runtimeCondition: currentRuntimeCondition + }); + } + } + if (otherRuntimeConnections.length > 0) { + const problem = requestShortener => { + return `Module ${module.readableIdentifier( + requestShortener + )} is runtime-dependent referenced by these modules: ${Array.from( + otherRuntimeConnections, + ({ originModule, runtimeCondition }) => + `${originModule.readableIdentifier( + requestShortener + )} (expected runtime ${runtimeToString( + runtime + )}, module is only referenced in ${runtimeToString( + /** @type {RuntimeSpec} */ (runtimeCondition) + )})` + ).join(", ")}`; }; + statistics.incorrectRuntimeCondition++; + failureCache.set(module, problem); // cache failures for performance + return problem; + } + } - if (unhandledProperties.has("use")) { - unhandledProperties.delete("use"); - unhandledProperties.delete("enforce"); - - conflictWith("loader", "use"); - conflictWith("options", "use"); + let backup; + if (avoidMutateOnFailure) { + backup = config.snapshot(); + } - const use = rule.use; - const enforce = rule.enforce; + // Add the module + config.add(module); - const type = enforce ? `use-${enforce}` : "use"; + incomingModules.sort(compareModulesByIdentifier); - /** - * - * @param {string} path options path - * @param {string} defaultIdent default ident when none is provided - * @param {object} item user provided use value - * @returns {Effect|function(any): Effect[]} effect - */ - const useToEffect = (path, defaultIdent, item) => { - if (typeof item === "function") { - return data => useToEffectsWithoutIdent(path, item(data)); - } else { - return useToEffectRaw(path, defaultIdent, item); - } - }; + // Every module which depends on the added module must be in the configuration too. + for (const originModule of incomingModules) { + const problem = this._tryToAdd( + compilation, + config, + originModule, + runtime, + activeRuntime, + possibleModules, + candidates, + failureCache, + chunkGraph, + false, + statistics + ); + if (problem) { + if (backup !== undefined) config.rollback(backup); + statistics.importerFailed++; + failureCache.set(module, problem); // cache failures for performance + return problem; + } + } - /** - * - * @param {string} path options path - * @param {string} defaultIdent default ident when none is provided - * @param {object} item user provided use value - * @returns {Effect} effect - */ - const useToEffectRaw = (path, defaultIdent, item) => { - if (typeof item === "string") { - return { - type, - value: { - loader: item, - options: undefined, - ident: undefined - } - }; - } else { - const loader = item.loader; - const options = item.options; - let ident = item.ident; - if (options && typeof options === "object") { - if (!ident) ident = defaultIdent; - references.set(ident, options); - } - if (typeof options === "string") { - util.deprecate( - () => {}, - `Using a string as loader options is deprecated (${path}.options)`, - "DEP_WEBPACK_RULE_LOADER_OPTIONS_STRING" - )(); - } - return { - type: enforce ? `use-${enforce}` : "use", - value: { - loader, - options, - ident - } - }; - } - }; + // Add imports to possible candidates list + for (const imp of this._getImports(compilation, module, runtime)) { + candidates.add(imp); + } + statistics.added++; + return null; + } +} - /** - * @param {string} path options path - * @param {any} items user provided use value - * @returns {Effect[]} effects - */ - const useToEffectsWithoutIdent = (path, items) => { - if (Array.isArray(items)) { - return items.map((item, idx) => - useToEffectRaw(`${path}[${idx}]`, "[[missing ident]]", item) - ); - } - return [useToEffectRaw(path, "[[missing ident]]", items)]; - }; +class ConcatConfiguration { + /** + * @param {Module} rootModule the root module + * @param {RuntimeSpec} runtime the runtime + */ + constructor(rootModule, runtime) { + this.rootModule = rootModule; + this.runtime = runtime; + /** @type {Set} */ + this.modules = new Set(); + this.modules.add(rootModule); + /** @type {Map} */ + this.warnings = new Map(); + } - /** - * @param {string} path current path - * @param {any} items user provided use value - * @returns {(Effect|function(any): Effect[])[]} effects - */ - const useToEffects = (path, items) => { - if (Array.isArray(items)) { - return items.map((item, idx) => { - const subPath = `${path}[${idx}]`; - return useToEffect(subPath, subPath, item); - }); - } - return [useToEffect(path, path, items)]; - }; + add(module) { + this.modules.add(module); + } - if (typeof use === "function") { - result.effects.push(data => - useToEffectsWithoutIdent(`${path}.use`, use(data)) - ); - } else { - for (const effect of useToEffects(`${path}.use`, use)) { - result.effects.push(effect); - } - } - } + has(module) { + return this.modules.has(module); + } - if (unhandledProperties.has("loader")) { - unhandledProperties.delete("loader"); - unhandledProperties.delete("options"); - unhandledProperties.delete("enforce"); + isEmpty() { + return this.modules.size === 1; + } - const loader = rule.loader; - const options = rule.options; - const enforce = rule.enforce; + addWarning(module, problem) { + this.warnings.set(module, problem); + } - if (loader.includes("!")) { - throw ruleSetCompiler.error( - `${path}.loader`, - loader, - "Exclamation mark separated loader lists has been removed in favor of the 'use' property with arrays" - ); - } + getWarningsSorted() { + return new Map( + Array.from(this.warnings).sort((a, b) => { + const ai = a[0].identifier(); + const bi = b[0].identifier(); + if (ai < bi) return -1; + if (ai > bi) return 1; + return 0; + }) + ); + } - if (loader.includes("?")) { - throw ruleSetCompiler.error( - `${path}.loader`, - loader, - "Query arguments on 'loader' has been removed in favor of the 'options' property" - ); - } + /** + * @returns {Set} modules as set + */ + getModules() { + return this.modules; + } - if (typeof options === "string") { - util.deprecate( - () => {}, - `Using a string as loader options is deprecated (${path}.options)`, - "DEP_WEBPACK_RULE_LOADER_OPTIONS_STRING" - )(); - } + snapshot() { + return this.modules.size; + } - const ident = - options && typeof options === "object" ? path : undefined; - references.set(ident, options); - result.effects.push({ - type: enforce ? `use-${enforce}` : "use", - value: { - loader, - options, - ident - } - }); - } + rollback(snapshot) { + const modules = this.modules; + for (const m of modules) { + if (snapshot === 0) { + modules.delete(m); + } else { + snapshot--; } - ); + } } - - useItemToEffects(path, item) {} } -module.exports = UseEffectRulePlugin; +module.exports = ModuleConcatenationPlugin; /***/ }), -/***/ 31372: +/***/ 6669: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; /* MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra */ -const RuntimeGlobals = __webpack_require__(49404); -const Template = __webpack_require__(92066); -const HelperRuntimeModule = __webpack_require__(22970); +const { SyncBailHook } = __webpack_require__(34718); +const { RawSource, CachedSource, CompatSource } = __webpack_require__(96192); +const Compilation = __webpack_require__(59622); +const WebpackError = __webpack_require__(68422); +const { compareSelect, compareStrings } = __webpack_require__(26296); +const createHash = __webpack_require__(24123); -class AsyncModuleRuntimeModule extends HelperRuntimeModule { - constructor() { - super("async module"); +/** @typedef {import("webpack-sources").Source} Source */ +/** @typedef {import("../Compilation").AssetInfo} AssetInfo */ +/** @typedef {import("../Compiler")} Compiler */ + +const EMPTY_SET = new Set(); + +const addToList = (itemOrItems, list) => { + if (Array.isArray(itemOrItems)) { + for (const item of itemOrItems) { + list.add(item); + } + } else if (itemOrItems) { + list.add(itemOrItems); + } +}; + +/** + * @template T + * @param {T[]} input list + * @param {function(T): Buffer} fn map function + * @returns {Buffer[]} buffers without duplicates + */ +const mapAndDeduplicateBuffers = (input, fn) => { + // Buffer.equals compares size first so this should be efficient enough + // If it becomes a performance problem we can use a map and group by size + // instead of looping over all assets. + const result = []; + outer: for (const value of input) { + const buf = fn(value); + for (const other of result) { + if (buf.equals(other)) continue outer; + } + result.push(buf); + } + return result; +}; + +/** + * Escapes regular expression metacharacters + * @param {string} str String to quote + * @returns {string} Escaped string + */ +const quoteMeta = str => { + return str.replace(/[-[\]\\/{}()*+?.^$|]/g, "\\$&"); +}; + +const cachedSourceMap = new WeakMap(); + +const toCachedSource = source => { + if (source instanceof CachedSource) { + return source; } + const entry = cachedSourceMap.get(source); + if (entry !== undefined) return entry; + const newSource = new CachedSource(CompatSource.from(source)); + cachedSourceMap.set(source, newSource); + return newSource; +}; + +/** + * @typedef {Object} AssetInfoForRealContentHash + * @property {string} name + * @property {AssetInfo} info + * @property {Source} source + * @property {RawSource | undefined} newSource + * @property {RawSource | undefined} newSourceWithoutOwn + * @property {string} content + * @property {Set} ownHashes + * @property {Promise} contentComputePromise + * @property {Promise} contentComputeWithoutOwnPromise + * @property {Set} referencedHashes + * @property {Set} hashes + */ + +/** + * @typedef {Object} CompilationHooks + * @property {SyncBailHook<[Buffer[], string], string>} updateHash + */ + +/** @type {WeakMap} */ +const compilationHooksMap = new WeakMap(); +class RealContentHashPlugin { /** - * @returns {string} runtime code + * @param {Compilation} compilation the compilation + * @returns {CompilationHooks} the attached hooks */ - generate() { - const { runtimeTemplate } = this.compilation; - const fn = RuntimeGlobals.asyncModule; - return Template.asString([ - 'var webpackThen = typeof Symbol === "function" ? Symbol("webpack then") : "__webpack_then__";', - 'var webpackExports = typeof Symbol === "function" ? Symbol("webpack exports") : "__webpack_exports__";', - `var completeQueue = ${runtimeTemplate.basicFunction("queue", [ - "if(queue) {", - Template.indent([ - `queue.forEach(${runtimeTemplate.expressionFunction( - "fn.r--", - "fn" - )});`, - `queue.forEach(${runtimeTemplate.expressionFunction( - "fn.r-- ? fn.r++ : fn()", - "fn" - )});` - ]), - "}" - ])}`, - `var completeFunction = ${runtimeTemplate.expressionFunction( - "!--fn.r && fn()", - "fn" - )};`, - `var queueFunction = ${runtimeTemplate.expressionFunction( - "queue ? queue.push(fn) : completeFunction(fn)", - "queue, fn" - )};`, - `var wrapDeps = ${runtimeTemplate.returningFunction( - `deps.map(${runtimeTemplate.basicFunction("dep", [ - 'if(dep !== null && typeof dep === "object") {', - Template.indent([ - "if(dep[webpackThen]) return dep;", - "if(dep.then) {", - Template.indent([ - "var queue = [];", - `dep.then(${runtimeTemplate.basicFunction("r", [ - "obj[webpackExports] = r;", - "completeQueue(queue);", - "queue = 0;" - ])});`, - `var obj = {}; - obj[webpackThen] = ${runtimeTemplate.expressionFunction( - "queueFunction(queue, fn), dep['catch'](reject)", - "fn, reject" - )};`, - "return obj;" - ]), - "}" - ]), - "}", - `var ret = {}; - ret[webpackThen] = ${runtimeTemplate.expressionFunction( - "completeFunction(fn)", - "fn" - )}; - ret[webpackExports] = dep; - return ret;` - ])})`, - "deps" - )};`, - `${fn} = ${runtimeTemplate.basicFunction("module, body, hasAwait", [ - "var queue = hasAwait && [];", - "var exports = module.exports;", - "var currentDeps;", - "var outerResolve;", - "var reject;", - "var isEvaluating = true;", - "var nested = false;", - `var whenAll = ${runtimeTemplate.basicFunction( - "deps, onResolve, onReject", - [ - "if (nested) return;", - "nested = true;", - "onResolve.r += deps.length;", - `deps.map(${runtimeTemplate.expressionFunction( - "dep[webpackThen](onResolve, onReject)", - "dep, i" - )});`, - "nested = false;" - ] - )};`, - `var promise = new Promise(${runtimeTemplate.basicFunction( - "resolve, rej", - [ - "reject = rej;", - `outerResolve = ${runtimeTemplate.expressionFunction( - "resolve(exports), completeQueue(queue), queue = 0" - )};` - ] - )});`, - "promise[webpackExports] = exports;", - `promise[webpackThen] = ${runtimeTemplate.basicFunction( - "fn, rejectFn", - [ - "if (isEvaluating) { return completeFunction(fn); }", - "if (currentDeps) whenAll(currentDeps, fn, rejectFn);", - "queueFunction(queue, fn);", - "promise['catch'](rejectFn);" - ] - )};`, - "module.exports = promise;", - `body(${runtimeTemplate.basicFunction("deps", [ - "if(!deps) return outerResolve();", - "currentDeps = wrapDeps(deps);", - "var fn, result;", - `var promise = new Promise(${runtimeTemplate.basicFunction( - "resolve, reject", - [ - `fn = ${runtimeTemplate.expressionFunction( - `resolve(result = currentDeps.map(${runtimeTemplate.returningFunction( - "d[webpackExports]", - "d" - )}))` - )};`, - "fn.r = 0;", - "whenAll(currentDeps, fn, reject);" - ] - )});`, - "return fn.r ? promise : result;" - ])}).then(outerResolve, reject);`, - "isEvaluating = false;" - ])};` - ]); + static getCompilationHooks(compilation) { + if (!(compilation instanceof Compilation)) { + throw new TypeError( + "The 'compilation' argument must be an instance of Compilation" + ); + } + let hooks = compilationHooksMap.get(compilation); + if (hooks === undefined) { + hooks = { + updateHash: new SyncBailHook(["content", "oldHash"]) + }; + compilationHooksMap.set(compilation, hooks); + } + return hooks; + } + + constructor({ hashFunction, hashDigest }) { + this._hashFunction = hashFunction; + this._hashDigest = hashDigest; + } + + /** + * Apply the plugin + * @param {Compiler} compiler the compiler instance + * @returns {void} + */ + apply(compiler) { + compiler.hooks.compilation.tap("RealContentHashPlugin", compilation => { + const cacheAnalyse = compilation.getCache( + "RealContentHashPlugin|analyse" + ); + const cacheGenerate = compilation.getCache( + "RealContentHashPlugin|generate" + ); + const hooks = RealContentHashPlugin.getCompilationHooks(compilation); + compilation.hooks.processAssets.tapPromise( + { + name: "RealContentHashPlugin", + stage: Compilation.PROCESS_ASSETS_STAGE_OPTIMIZE_HASH + }, + async () => { + const assets = compilation.getAssets(); + /** @type {AssetInfoForRealContentHash[]} */ + const assetsWithInfo = []; + const hashToAssets = new Map(); + for (const { source, info, name } of assets) { + const cachedSource = toCachedSource(source); + const content = cachedSource.source(); + /** @type {Set} */ + const hashes = new Set(); + addToList(info.contenthash, hashes); + const data = { + name, + info, + source: cachedSource, + /** @type {RawSource | undefined} */ + newSource: undefined, + /** @type {RawSource | undefined} */ + newSourceWithoutOwn: undefined, + content, + /** @type {Set} */ + ownHashes: undefined, + contentComputePromise: undefined, + contentComputeWithoutOwnPromise: undefined, + /** @type {Set} */ + referencedHashes: undefined, + hashes + }; + assetsWithInfo.push(data); + for (const hash of hashes) { + const list = hashToAssets.get(hash); + if (list === undefined) { + hashToAssets.set(hash, [data]); + } else { + list.push(data); + } + } + } + if (hashToAssets.size === 0) return; + const hashRegExp = new RegExp( + Array.from(hashToAssets.keys(), quoteMeta).join("|"), + "g" + ); + await Promise.all( + assetsWithInfo.map(async asset => { + const { name, source, content, hashes } = asset; + if (Buffer.isBuffer(content)) { + asset.referencedHashes = EMPTY_SET; + asset.ownHashes = EMPTY_SET; + return; + } + const etag = cacheAnalyse.mergeEtags( + cacheAnalyse.getLazyHashedEtag(source), + Array.from(hashes).join("|") + ); + [asset.referencedHashes, asset.ownHashes] = + await cacheAnalyse.providePromise(name, etag, () => { + const referencedHashes = new Set(); + let ownHashes = new Set(); + const inContent = content.match(hashRegExp); + if (inContent) { + for (const hash of inContent) { + if (hashes.has(hash)) { + ownHashes.add(hash); + continue; + } + referencedHashes.add(hash); + } + } + return [referencedHashes, ownHashes]; + }); + }) + ); + const getDependencies = hash => { + const assets = hashToAssets.get(hash); + if (!assets) { + const referencingAssets = assetsWithInfo.filter(asset => + asset.referencedHashes.has(hash) + ); + const err = new WebpackError(`RealContentHashPlugin +Some kind of unexpected caching problem occurred. +An asset was cached with a reference to another asset (${hash}) that's not in the compilation anymore. +Either the asset was incorrectly cached, or the referenced asset should also be restored from cache. +Referenced by: +${referencingAssets + .map(a => { + const match = new RegExp(`.{0,20}${quoteMeta(hash)}.{0,20}`).exec( + a.content + ); + return ` - ${a.name}: ...${match ? match[0] : "???"}...`; + }) + .join("\n")}`); + compilation.errors.push(err); + return undefined; + } + const hashes = new Set(); + for (const { referencedHashes, ownHashes } of assets) { + if (!ownHashes.has(hash)) { + for (const hash of ownHashes) { + hashes.add(hash); + } + } + for (const hash of referencedHashes) { + hashes.add(hash); + } + } + return hashes; + }; + const hashInfo = hash => { + const assets = hashToAssets.get(hash); + return `${hash} (${Array.from(assets, a => a.name)})`; + }; + const hashesInOrder = new Set(); + for (const hash of hashToAssets.keys()) { + const add = (hash, stack) => { + const deps = getDependencies(hash); + if (!deps) return; + stack.add(hash); + for (const dep of deps) { + if (hashesInOrder.has(dep)) continue; + if (stack.has(dep)) { + throw new Error( + `Circular hash dependency ${Array.from( + stack, + hashInfo + ).join(" -> ")} -> ${hashInfo(dep)}` + ); + } + add(dep, stack); + } + hashesInOrder.add(hash); + stack.delete(hash); + }; + if (hashesInOrder.has(hash)) continue; + add(hash, new Set()); + } + const hashToNewHash = new Map(); + const getEtag = asset => + cacheGenerate.mergeEtags( + cacheGenerate.getLazyHashedEtag(asset.source), + Array.from(asset.referencedHashes, hash => + hashToNewHash.get(hash) + ).join("|") + ); + const computeNewContent = asset => { + if (asset.contentComputePromise) return asset.contentComputePromise; + return (asset.contentComputePromise = (async () => { + if ( + asset.ownHashes.size > 0 || + Array.from(asset.referencedHashes).some( + hash => hashToNewHash.get(hash) !== hash + ) + ) { + const identifier = asset.name; + const etag = getEtag(asset); + asset.newSource = await cacheGenerate.providePromise( + identifier, + etag, + () => { + const newContent = asset.content.replace(hashRegExp, hash => + hashToNewHash.get(hash) + ); + return new RawSource(newContent); + } + ); + } + })()); + }; + const computeNewContentWithoutOwn = asset => { + if (asset.contentComputeWithoutOwnPromise) + return asset.contentComputeWithoutOwnPromise; + return (asset.contentComputeWithoutOwnPromise = (async () => { + if ( + asset.ownHashes.size > 0 || + Array.from(asset.referencedHashes).some( + hash => hashToNewHash.get(hash) !== hash + ) + ) { + const identifier = asset.name + "|without-own"; + const etag = getEtag(asset); + asset.newSourceWithoutOwn = await cacheGenerate.providePromise( + identifier, + etag, + () => { + const newContent = asset.content.replace( + hashRegExp, + hash => { + if (asset.ownHashes.has(hash)) { + return ""; + } + return hashToNewHash.get(hash); + } + ); + return new RawSource(newContent); + } + ); + } + })()); + }; + const comparator = compareSelect(a => a.name, compareStrings); + for (const oldHash of hashesInOrder) { + const assets = hashToAssets.get(oldHash); + assets.sort(comparator); + const hash = createHash(this._hashFunction); + await Promise.all( + assets.map(asset => + asset.ownHashes.has(oldHash) + ? computeNewContentWithoutOwn(asset) + : computeNewContent(asset) + ) + ); + const assetsContent = mapAndDeduplicateBuffers(assets, asset => { + if (asset.ownHashes.has(oldHash)) { + return asset.newSourceWithoutOwn + ? asset.newSourceWithoutOwn.buffer() + : asset.source.buffer(); + } else { + return asset.newSource + ? asset.newSource.buffer() + : asset.source.buffer(); + } + }); + let newHash = hooks.updateHash.call(assetsContent, oldHash); + if (!newHash) { + for (const content of assetsContent) { + hash.update(content); + } + const digest = hash.digest(this._hashDigest); + newHash = /** @type {string} */ (digest.slice(0, oldHash.length)); + } + hashToNewHash.set(oldHash, newHash); + } + await Promise.all( + assetsWithInfo.map(async asset => { + await computeNewContent(asset); + const newName = asset.name.replace(hashRegExp, hash => + hashToNewHash.get(hash) + ); + + const infoUpdate = {}; + const hash = asset.info.contenthash; + infoUpdate.contenthash = Array.isArray(hash) + ? hash.map(hash => hashToNewHash.get(hash)) + : hashToNewHash.get(hash); + + if (asset.newSource !== undefined) { + compilation.updateAsset( + asset.name, + asset.newSource, + infoUpdate + ); + } else { + compilation.updateAsset(asset.name, asset.source, infoUpdate); + } + + if (asset.name !== newName) { + compilation.renameAsset(asset.name, newName); + } + }) + ); + } + ); + }); } } -module.exports = AsyncModuleRuntimeModule; +module.exports = RealContentHashPlugin; /***/ }), -/***/ 86150: +/***/ 66290: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; /* MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra */ -const RuntimeGlobals = __webpack_require__(49404); -const RuntimeModule = __webpack_require__(61439); -const Template = __webpack_require__(92066); -const JavascriptModulesPlugin = __webpack_require__(76767); -const { getUndoPath } = __webpack_require__(96236); +const { STAGE_BASIC, STAGE_ADVANCED } = __webpack_require__(68145); -class AutoPublicPathRuntimeModule extends RuntimeModule { - constructor() { - super("publicPath", RuntimeModule.STAGE_BASIC); - } +/** @typedef {import("../Chunk")} Chunk */ +/** @typedef {import("../Compiler")} Compiler */ +class RemoveEmptyChunksPlugin { /** - * @returns {string} runtime code + * Apply the plugin + * @param {Compiler} compiler the compiler instance + * @returns {void} */ - generate() { - const { compilation } = this; - const { scriptType, importMetaName, path } = compilation.outputOptions; - const chunkName = compilation.getPath( - JavascriptModulesPlugin.getChunkFilenameTemplate( - this.chunk, - compilation.outputOptions - ), - { - chunk: this.chunk, - contentHashType: "javascript" - } - ); - const undoPath = getUndoPath(chunkName, path, false); + apply(compiler) { + compiler.hooks.compilation.tap("RemoveEmptyChunksPlugin", compilation => { + /** + * @param {Iterable} chunks the chunks array + * @returns {void} + */ + const handler = chunks => { + const chunkGraph = compilation.chunkGraph; + for (const chunk of chunks) { + if ( + chunkGraph.getNumberOfChunkModules(chunk) === 0 && + !chunk.hasRuntime() && + chunkGraph.getNumberOfEntryModules(chunk) === 0 + ) { + compilation.chunkGraph.disconnectChunk(chunk); + compilation.chunks.delete(chunk); + } + } + }; - return Template.asString([ - "var scriptUrl;", - scriptType === "module" - ? `if (typeof ${importMetaName}.url === "string") scriptUrl = ${importMetaName}.url` - : Template.asString([ - `if (${RuntimeGlobals.global}.importScripts) scriptUrl = ${RuntimeGlobals.global}.location + "";`, - `var document = ${RuntimeGlobals.global}.document;`, - "if (!scriptUrl && document) {", - Template.indent([ - `if (document.currentScript)`, - Template.indent(`scriptUrl = document.currentScript.src`), - "if (!scriptUrl) {", - Template.indent([ - 'var scripts = document.getElementsByTagName("script");', - "if(scripts.length) scriptUrl = scripts[scripts.length - 1].src" - ]), - "}" - ]), - "}" - ]), - "// When supporting browsers where an automatic publicPath is not supported you must specify an output.publicPath manually via configuration", - '// or pass an empty string ("") and set the __webpack_public_path__ variable from your code to use your own logic.', - 'if (!scriptUrl) throw new Error("Automatic publicPath is not supported in this browser");', - 'scriptUrl = scriptUrl.replace(/#.*$/, "").replace(/\\?.*$/, "").replace(/\\/[^\\/]+$/, "/");', - !undoPath - ? `${RuntimeGlobals.publicPath} = scriptUrl;` - : `${RuntimeGlobals.publicPath} = scriptUrl + ${JSON.stringify( - undoPath - )};` - ]); + // TODO do it once + compilation.hooks.optimizeChunks.tap( + { + name: "RemoveEmptyChunksPlugin", + stage: STAGE_BASIC + }, + handler + ); + compilation.hooks.optimizeChunks.tap( + { + name: "RemoveEmptyChunksPlugin", + stage: STAGE_ADVANCED + }, + handler + ); + }); } } - -module.exports = AutoPublicPathRuntimeModule; +module.exports = RemoveEmptyChunksPlugin; /***/ }), -/***/ 43818: +/***/ 75072: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; /* MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra */ -const RuntimeGlobals = __webpack_require__(49404); -const RuntimeModule = __webpack_require__(61439); +const { STAGE_BASIC } = __webpack_require__(68145); +const Queue = __webpack_require__(65753); +const { intersect } = __webpack_require__(34715); -class ChunkNameRuntimeModule extends RuntimeModule { - /** - * @param {string} chunkName the chunk's name - */ - constructor(chunkName) { - super("chunkName"); - this.chunkName = chunkName; - } +/** @typedef {import("../Compiler")} Compiler */ +class RemoveParentModulesPlugin { /** - * @returns {string} runtime code + * @param {Compiler} compiler the compiler + * @returns {void} */ - generate() { - return `${RuntimeGlobals.chunkName} = ${JSON.stringify(this.chunkName)};`; - } -} - -module.exports = ChunkNameRuntimeModule; - - -/***/ }), - -/***/ 24013: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php -*/ - - + apply(compiler) { + compiler.hooks.compilation.tap("RemoveParentModulesPlugin", compilation => { + const handler = (chunks, chunkGroups) => { + const chunkGraph = compilation.chunkGraph; + const queue = new Queue(); + const availableModulesMap = new WeakMap(); -const RuntimeGlobals = __webpack_require__(49404); -const Template = __webpack_require__(92066); -const HelperRuntimeModule = __webpack_require__(22970); + for (const chunkGroup of compilation.entrypoints.values()) { + // initialize available modules for chunks without parents + availableModulesMap.set(chunkGroup, new Set()); + for (const child of chunkGroup.childrenIterable) { + queue.enqueue(child); + } + } + for (const chunkGroup of compilation.asyncEntrypoints) { + // initialize available modules for chunks without parents + availableModulesMap.set(chunkGroup, new Set()); + for (const child of chunkGroup.childrenIterable) { + queue.enqueue(child); + } + } -class CompatGetDefaultExportRuntimeModule extends HelperRuntimeModule { - constructor() { - super("compat get default export"); - } + while (queue.length > 0) { + const chunkGroup = queue.dequeue(); + let availableModules = availableModulesMap.get(chunkGroup); + let changed = false; + for (const parent of chunkGroup.parentsIterable) { + const availableModulesInParent = availableModulesMap.get(parent); + if (availableModulesInParent !== undefined) { + // If we know the available modules in parent: process these + if (availableModules === undefined) { + // if we have not own info yet: create new entry + availableModules = new Set(availableModulesInParent); + for (const chunk of parent.chunks) { + for (const m of chunkGraph.getChunkModulesIterable(chunk)) { + availableModules.add(m); + } + } + availableModulesMap.set(chunkGroup, availableModules); + changed = true; + } else { + for (const m of availableModules) { + if ( + !chunkGraph.isModuleInChunkGroup(m, parent) && + !availableModulesInParent.has(m) + ) { + availableModules.delete(m); + changed = true; + } + } + } + } + } + if (changed) { + // if something changed: enqueue our children + for (const child of chunkGroup.childrenIterable) { + queue.enqueue(child); + } + } + } - /** - * @returns {string} runtime code - */ - generate() { - const { runtimeTemplate } = this.compilation; - const fn = RuntimeGlobals.compatGetDefaultExport; - return Template.asString([ - "// getDefaultExport function for compatibility with non-harmony modules", - `${fn} = ${runtimeTemplate.basicFunction("module", [ - "var getter = module && module.__esModule ?", - Template.indent([ - `${runtimeTemplate.returningFunction("module['default']")} :`, - `${runtimeTemplate.returningFunction("module")};` - ]), - `${RuntimeGlobals.definePropertyGetters}(getter, { a: getter });`, - "return getter;" - ])};` - ]); + // now we have available modules for every chunk + for (const chunk of chunks) { + const availableModulesSets = Array.from( + chunk.groupsIterable, + chunkGroup => availableModulesMap.get(chunkGroup) + ); + if (availableModulesSets.some(s => s === undefined)) continue; // No info about this chunk group + const availableModules = + availableModulesSets.length === 1 + ? availableModulesSets[0] + : intersect(availableModulesSets); + const numberOfModules = chunkGraph.getNumberOfChunkModules(chunk); + const toRemove = new Set(); + if (numberOfModules < availableModules.size) { + for (const m of chunkGraph.getChunkModulesIterable(chunk)) { + if (availableModules.has(m)) { + toRemove.add(m); + } + } + } else { + for (const m of availableModules) { + if (chunkGraph.isModuleInChunk(m, chunk)) { + toRemove.add(m); + } + } + } + for (const module of toRemove) { + chunkGraph.disconnectChunkAndModule(chunk, module); + } + } + }; + compilation.hooks.optimizeChunks.tap( + { + name: "RemoveParentModulesPlugin", + stage: STAGE_BASIC + }, + handler + ); + }); } } - -module.exports = CompatGetDefaultExportRuntimeModule; +module.exports = RemoveParentModulesPlugin; /***/ }), -/***/ 65788: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { +/***/ 23821: +/***/ (function(module) { "use strict"; /* MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra */ -const RuntimeGlobals = __webpack_require__(49404); -const RuntimeModule = __webpack_require__(61439); - -/** @typedef {import("../MainTemplate")} MainTemplate */ +/** @typedef {import("../Compiler")} Compiler */ -class CompatRuntimeModule extends RuntimeModule { - constructor() { - super("compat", RuntimeModule.STAGE_ATTACH); - this.fullHash = true; +class RuntimeChunkPlugin { + constructor(options) { + this.options = { + name: entrypoint => `runtime~${entrypoint.name}`, + ...options + }; } /** - * @returns {string} runtime code + * Apply the plugin + * @param {Compiler} compiler the compiler instance + * @returns {void} */ - generate() { - const { chunkGraph, chunk, compilation } = this; - const { - runtimeTemplate, - mainTemplate, - moduleTemplates, - dependencyTemplates - } = compilation; - const bootstrap = mainTemplate.hooks.bootstrap.call( - "", - chunk, - compilation.hash || "XXXX", - moduleTemplates.javascript, - dependencyTemplates - ); - const localVars = mainTemplate.hooks.localVars.call( - "", - chunk, - compilation.hash || "XXXX" - ); - const requireExtensions = mainTemplate.hooks.requireExtensions.call( - "", - chunk, - compilation.hash || "XXXX" - ); - const runtimeRequirements = chunkGraph.getTreeRuntimeRequirements(chunk); - let requireEnsure = ""; - if (runtimeRequirements.has(RuntimeGlobals.ensureChunk)) { - const requireEnsureHandler = mainTemplate.hooks.requireEnsure.call( - "", - chunk, - compilation.hash || "XXXX", - "chunkId" + apply(compiler) { + compiler.hooks.thisCompilation.tap("RuntimeChunkPlugin", compilation => { + compilation.hooks.addEntry.tap( + "RuntimeChunkPlugin", + (_, { name: entryName }) => { + if (entryName === undefined) return; + const data = compilation.entries.get(entryName); + if (data.options.runtime === undefined && !data.options.dependOn) { + // Determine runtime chunk name + let name = this.options.name; + if (typeof name === "function") { + name = name({ name: entryName }); + } + data.options.runtime = name; + } + } ); - if (requireEnsureHandler) { - requireEnsure = `${ - RuntimeGlobals.ensureChunkHandlers - }.compat = ${runtimeTemplate.basicFunction( - "chunkId, promises", - requireEnsureHandler - )};`; - } - } - return [bootstrap, localVars, requireEnsure, requireExtensions] - .filter(Boolean) - .join("\n"); - } - - /** - * @returns {boolean} true, if the runtime module should get it's own scope - */ - shouldIsolate() { - // We avoid isolating this to have better backward-compat - return false; + }); } } -module.exports = CompatRuntimeModule; +module.exports = RuntimeChunkPlugin; /***/ }), -/***/ 58470: +/***/ 47844: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; /* MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra */ -const RuntimeGlobals = __webpack_require__(49404); -const Template = __webpack_require__(92066); -const HelperRuntimeModule = __webpack_require__(22970); - -class CreateFakeNamespaceObjectRuntimeModule extends HelperRuntimeModule { - constructor() { - super("create fake namespace object"); - } - - /** - * @returns {string} runtime code - */ - generate() { - const { runtimeTemplate } = this.compilation; - const fn = RuntimeGlobals.createFakeNamespaceObject; - return Template.asString([ - `var getProto = Object.getPrototypeOf ? ${runtimeTemplate.returningFunction( - "Object.getPrototypeOf(obj)", - "obj" - )} : ${runtimeTemplate.returningFunction("obj.__proto__", "obj")};`, - "var leafPrototypes;", - "// create a fake namespace object", - "// mode & 1: value is a module id, require it", - "// mode & 2: merge all properties of value into the ns", - "// mode & 4: return value when already ns object", - "// mode & 16: return value when it's Promise-like", - "// mode & 8|1: behave like require", - // Note: must be a function (not arrow), because this is used in body! - `${fn} = function(value, mode) {`, - Template.indent([ - `if(mode & 1) value = this(value);`, - `if(mode & 8) return value;`, - "if(typeof value === 'object' && value) {", - Template.indent([ - "if((mode & 4) && value.__esModule) return value;", - "if((mode & 16) && typeof value.then === 'function') return value;" - ]), - "}", - "var ns = Object.create(null);", - `${RuntimeGlobals.makeNamespaceObject}(ns);`, - "var def = {};", - "leafPrototypes = leafPrototypes || [null, getProto({}), getProto([]), getProto(getProto)];", - "for(var current = mode & 2 && value; typeof current == 'object' && !~leafPrototypes.indexOf(current); current = getProto(current)) {", - Template.indent([ - `Object.getOwnPropertyNames(current).forEach(${runtimeTemplate.expressionFunction( - `def[key] = ${runtimeTemplate.returningFunction("value[key]", "")}`, - "key" - )});` - ]), - "}", - `def['default'] = ${runtimeTemplate.returningFunction("value", "")};`, - `${RuntimeGlobals.definePropertyGetters}(ns, def);`, - "return ns;" - ]), - "};" - ]); - } -} +const glob2regexp = __webpack_require__(22797); +const { STAGE_DEFAULT } = __webpack_require__(68145); +const HarmonyExportImportedSpecifierDependency = __webpack_require__(77952); +const HarmonyImportSpecifierDependency = __webpack_require__(61994); +const formatLocation = __webpack_require__(57261); -module.exports = CreateFakeNamespaceObjectRuntimeModule; +/** @typedef {import("../Compiler")} Compiler */ +/** @typedef {import("../Dependency")} Dependency */ +/** @typedef {import("../Module")} Module */ +/** @typedef {import("../javascript/JavascriptParser")} JavascriptParser */ +/** + * @typedef {Object} ExportInModule + * @property {Module} module the module + * @property {string} exportName the name of the export + * @property {boolean} checked if the export is conditional + */ -/***/ }), +/** + * @typedef {Object} ReexportInfo + * @property {Map} static + * @property {Map>} dynamic + */ -/***/ 41690: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { +/** @type {WeakMap>} */ +const globToRegexpCache = new WeakMap(); -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php -*/ +/** + * @param {string} glob the pattern + * @param {Map} cache the glob to RegExp cache + * @returns {RegExp} a regular expression + */ +const globToRegexp = (glob, cache) => { + const cacheEntry = cache.get(glob); + if (cacheEntry !== undefined) return cacheEntry; + if (!glob.includes("/")) { + glob = `**/${glob}`; + } + const baseRegexp = glob2regexp(glob, { globstar: true, extended: true }); + const regexpSource = baseRegexp.source; + const regexp = new RegExp("^(\\./)?" + regexpSource.slice(1)); + cache.set(glob, regexp); + return regexp; +}; +class SideEffectsFlagPlugin { + /** + * @param {boolean} analyseSource analyse source code for side effects + */ + constructor(analyseSource = true) { + this._analyseSource = analyseSource; + } + /** + * Apply the plugin + * @param {Compiler} compiler the compiler instance + * @returns {void} + */ + apply(compiler) { + let cache = globToRegexpCache.get(compiler.root); + if (cache === undefined) { + cache = new Map(); + globToRegexpCache.set(compiler.root, cache); + } + compiler.hooks.compilation.tap( + "SideEffectsFlagPlugin", + (compilation, { normalModuleFactory }) => { + const moduleGraph = compilation.moduleGraph; + normalModuleFactory.hooks.module.tap( + "SideEffectsFlagPlugin", + (module, data) => { + const resolveData = data.resourceResolveData; + if ( + resolveData && + resolveData.descriptionFileData && + resolveData.relativePath + ) { + const sideEffects = resolveData.descriptionFileData.sideEffects; + if (sideEffects !== undefined) { + if (module.factoryMeta === undefined) { + module.factoryMeta = {}; + } + const hasSideEffects = + SideEffectsFlagPlugin.moduleHasSideEffects( + resolveData.relativePath, + sideEffects, + cache + ); + module.factoryMeta.sideEffectFree = !hasSideEffects; + } + } + return module; + } + ); + normalModuleFactory.hooks.module.tap( + "SideEffectsFlagPlugin", + (module, data) => { + if (typeof data.settings.sideEffects === "boolean") { + if (module.factoryMeta === undefined) { + module.factoryMeta = {}; + } + module.factoryMeta.sideEffectFree = !data.settings.sideEffects; + } + return module; + } + ); + if (this._analyseSource) { + /** + * @param {JavascriptParser} parser the parser + * @returns {void} + */ + const parserHandler = parser => { + let sideEffectsStatement; + parser.hooks.program.tap("SideEffectsFlagPlugin", () => { + sideEffectsStatement = undefined; + }); + parser.hooks.statement.tap( + { name: "SideEffectsFlagPlugin", stage: -100 }, + statement => { + if (sideEffectsStatement) return; + if (parser.scope.topLevelScope !== true) return; + switch (statement.type) { + case "ExpressionStatement": + if ( + !parser.isPure(statement.expression, statement.range[0]) + ) { + sideEffectsStatement = statement; + } + break; + case "IfStatement": + case "WhileStatement": + case "DoWhileStatement": + if (!parser.isPure(statement.test, statement.range[0])) { + sideEffectsStatement = statement; + } + // statement hook will be called for child statements too + break; + case "ForStatement": + if ( + !parser.isPure(statement.init, statement.range[0]) || + !parser.isPure( + statement.test, + statement.init + ? statement.init.range[1] + : statement.range[0] + ) || + !parser.isPure( + statement.update, + statement.test + ? statement.test.range[1] + : statement.init + ? statement.init.range[1] + : statement.range[0] + ) + ) { + sideEffectsStatement = statement; + } + // statement hook will be called for child statements too + break; + case "SwitchStatement": + if ( + !parser.isPure(statement.discriminant, statement.range[0]) + ) { + sideEffectsStatement = statement; + } + // statement hook will be called for child statements too + break; + case "VariableDeclaration": + case "ClassDeclaration": + case "FunctionDeclaration": + if (!parser.isPure(statement, statement.range[0])) { + sideEffectsStatement = statement; + } + break; + case "ExportNamedDeclaration": + case "ExportDefaultDeclaration": + if ( + !parser.isPure(statement.declaration, statement.range[0]) + ) { + sideEffectsStatement = statement; + } + break; + case "LabeledStatement": + case "BlockStatement": + // statement hook will be called for child statements too + break; + case "EmptyStatement": + break; + case "ExportAllDeclaration": + case "ImportDeclaration": + // imports will be handled by the dependencies + break; + default: + sideEffectsStatement = statement; + break; + } + } + ); + parser.hooks.finish.tap("SideEffectsFlagPlugin", () => { + if (sideEffectsStatement === undefined) { + parser.state.module.buildMeta.sideEffectFree = true; + } else { + const { loc, type } = sideEffectsStatement; + moduleGraph + .getOptimizationBailout(parser.state.module) + .push( + () => + `Statement (${type}) with side effects in source code at ${formatLocation( + loc + )}` + ); + } + }); + }; + for (const key of [ + "javascript/auto", + "javascript/esm", + "javascript/dynamic" + ]) { + normalModuleFactory.hooks.parser + .for(key) + .tap("SideEffectsFlagPlugin", parserHandler); + } + } + compilation.hooks.optimizeDependencies.tap( + { + name: "SideEffectsFlagPlugin", + stage: STAGE_DEFAULT + }, + modules => { + const logger = compilation.getLogger( + "webpack.SideEffectsFlagPlugin" + ); -const RuntimeGlobals = __webpack_require__(49404); -const Template = __webpack_require__(92066); -const HelperRuntimeModule = __webpack_require__(22970); + logger.time("update dependencies"); + for (const module of modules) { + if (module.getSideEffectsConnectionState(moduleGraph) === false) { + const exportsInfo = moduleGraph.getExportsInfo(module); + for (const connection of moduleGraph.getIncomingConnections( + module + )) { + const dep = connection.dependency; + let isReexport; + if ( + (isReexport = + dep instanceof + HarmonyExportImportedSpecifierDependency) || + (dep instanceof HarmonyImportSpecifierDependency && + !dep.namespaceObjectAsContext) + ) { + // TODO improve for export * + if (isReexport && dep.name) { + const exportInfo = moduleGraph.getExportInfo( + connection.originModule, + dep.name + ); + exportInfo.moveTarget( + moduleGraph, + ({ module }) => + module.getSideEffectsConnectionState(moduleGraph) === + false, + ({ module: newModule, export: exportName }) => { + moduleGraph.updateModule(dep, newModule); + moduleGraph.addExplanation( + dep, + "(skipped side-effect-free modules)" + ); + const ids = dep.getIds(moduleGraph); + dep.setIds( + moduleGraph, + exportName + ? [...exportName, ...ids.slice(1)] + : ids.slice(1) + ); + return moduleGraph.getConnection(dep); + } + ); + continue; + } + // TODO improve for nested imports + const ids = dep.getIds(moduleGraph); + if (ids.length > 0) { + const exportInfo = exportsInfo.getExportInfo(ids[0]); + const target = exportInfo.getTarget( + moduleGraph, + ({ module }) => + module.getSideEffectsConnectionState(moduleGraph) === + false + ); + if (!target) continue; -class CreateScriptUrlRuntimeModule extends HelperRuntimeModule { - constructor() { - super("trusted types"); + moduleGraph.updateModule(dep, target.module); + moduleGraph.addExplanation( + dep, + "(skipped side-effect-free modules)" + ); + dep.setIds( + moduleGraph, + target.export + ? [...target.export, ...ids.slice(1)] + : ids.slice(1) + ); + } + } + } + } + } + logger.timeEnd("update dependencies"); + } + ); + } + ); } - /** - * @returns {string} runtime code - */ - generate() { - const { compilation } = this; - const { runtimeTemplate, outputOptions } = compilation; - const { trustedTypes } = outputOptions; - const fn = RuntimeGlobals.createScriptUrl; - - if (!trustedTypes) { - // Skip Trusted Types logic. - return Template.asString([ - `${fn} = ${runtimeTemplate.returningFunction("url", "url")};` - ]); + static moduleHasSideEffects(moduleName, flagValue, cache) { + switch (typeof flagValue) { + case "undefined": + return true; + case "boolean": + return flagValue; + case "string": + return globToRegexp(flagValue, cache).test(moduleName); + case "object": + return flagValue.some(glob => + SideEffectsFlagPlugin.moduleHasSideEffects(moduleName, glob, cache) + ); } - - return Template.asString([ - "var policy;", - `${fn} = ${runtimeTemplate.basicFunction("url", [ - "// Create Trusted Type policy if Trusted Types are available and the policy doesn't exist yet.", - "if (policy === undefined) {", - Template.indent([ - "policy = {", - Template.indent([ - `createScriptURL: ${runtimeTemplate.returningFunction( - "url", - "url" - )}` - ]), - "};", - 'if (typeof trustedTypes !== "undefined" && trustedTypes.createPolicy) {', - Template.indent([ - `policy = trustedTypes.createPolicy(${JSON.stringify( - trustedTypes.policyName - )}, policy);` - ]), - "}" - ]), - "}", - "return policy.createScriptURL(url);" - ])};` - ]); } } - -module.exports = CreateScriptUrlRuntimeModule; +module.exports = SideEffectsFlagPlugin; /***/ }), -/***/ 24905: +/***/ 57073: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; /* MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra */ -const RuntimeGlobals = __webpack_require__(49404); -const Template = __webpack_require__(92066); -const HelperRuntimeModule = __webpack_require__(22970); - -class DefinePropertyGettersRuntimeModule extends HelperRuntimeModule { - constructor() { - super("define property getters"); - } +const Chunk = __webpack_require__(65574); +const { STAGE_ADVANCED } = __webpack_require__(68145); +const WebpackError = __webpack_require__(68422); +const { requestToId } = __webpack_require__(72922); +const { isSubset } = __webpack_require__(34715); +const SortableSet = __webpack_require__(67563); +const { + compareModulesByIdentifier, + compareIterables +} = __webpack_require__(26296); +const createHash = __webpack_require__(24123); +const deterministicGrouping = __webpack_require__(37906); +const { makePathsRelative } = __webpack_require__(96236); +const memoize = __webpack_require__(84297); +const MinMaxSizeWarning = __webpack_require__(46681); - /** - * @returns {string} runtime code - */ - generate() { - const { runtimeTemplate } = this.compilation; - const fn = RuntimeGlobals.definePropertyGetters; - return Template.asString([ - "// define getter functions for harmony exports", - `${fn} = ${runtimeTemplate.basicFunction("exports, definition", [ - `for(var key in definition) {`, - Template.indent([ - `if(${RuntimeGlobals.hasOwnProperty}(definition, key) && !${RuntimeGlobals.hasOwnProperty}(exports, key)) {`, - Template.indent([ - "Object.defineProperty(exports, key, { enumerable: true, get: definition[key] });" - ]), - "}" - ]), - "}" - ])};` - ]); - } -} +/** @typedef {import("../../declarations/WebpackOptions").OptimizationSplitChunksCacheGroup} OptimizationSplitChunksCacheGroup */ +/** @typedef {import("../../declarations/WebpackOptions").OptimizationSplitChunksGetCacheGroups} OptimizationSplitChunksGetCacheGroups */ +/** @typedef {import("../../declarations/WebpackOptions").OptimizationSplitChunksOptions} OptimizationSplitChunksOptions */ +/** @typedef {import("../../declarations/WebpackOptions").OptimizationSplitChunksSizes} OptimizationSplitChunksSizes */ +/** @typedef {import("../../declarations/WebpackOptions").Output} OutputOptions */ +/** @typedef {import("../ChunkGraph")} ChunkGraph */ +/** @typedef {import("../ChunkGroup")} ChunkGroup */ +/** @typedef {import("../Compilation").AssetInfo} AssetInfo */ +/** @typedef {import("../Compilation").PathData} PathData */ +/** @typedef {import("../Compiler")} Compiler */ +/** @typedef {import("../Module")} Module */ +/** @typedef {import("../ModuleGraph")} ModuleGraph */ +/** @typedef {import("../util/deterministicGrouping").GroupedItems} DeterministicGroupingGroupedItemsForModule */ +/** @typedef {import("../util/deterministicGrouping").Options} DeterministicGroupingOptionsForModule */ -module.exports = DefinePropertyGettersRuntimeModule; +/** @typedef {Record} SplitChunksSizes */ +/** + * @callback ChunkFilterFunction + * @param {Chunk} chunk + * @returns {boolean} + */ -/***/ }), +/** + * @callback CombineSizeFunction + * @param {number} a + * @param {number} b + * @returns {number} + */ -/***/ 92857: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { +/** + * @typedef {Object} CacheGroupSource + * @property {string=} key + * @property {number=} priority + * @property {GetName=} getName + * @property {ChunkFilterFunction=} chunksFilter + * @property {boolean=} enforce + * @property {SplitChunksSizes} minSize + * @property {SplitChunksSizes} minSizeReduction + * @property {SplitChunksSizes} minRemainingSize + * @property {SplitChunksSizes} enforceSizeThreshold + * @property {SplitChunksSizes} maxAsyncSize + * @property {SplitChunksSizes} maxInitialSize + * @property {number=} minChunks + * @property {number=} maxAsyncRequests + * @property {number=} maxInitialRequests + * @property {(string | function(PathData, AssetInfo=): string)=} filename + * @property {string=} idHint + * @property {string} automaticNameDelimiter + * @property {boolean=} reuseExistingChunk + * @property {boolean=} usedExports + */ -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php -*/ +/** + * @typedef {Object} CacheGroup + * @property {string} key + * @property {number=} priority + * @property {GetName=} getName + * @property {ChunkFilterFunction=} chunksFilter + * @property {SplitChunksSizes} minSize + * @property {SplitChunksSizes} minSizeReduction + * @property {SplitChunksSizes} minRemainingSize + * @property {SplitChunksSizes} enforceSizeThreshold + * @property {SplitChunksSizes} maxAsyncSize + * @property {SplitChunksSizes} maxInitialSize + * @property {number=} minChunks + * @property {number=} maxAsyncRequests + * @property {number=} maxInitialRequests + * @property {(string | function(PathData, AssetInfo=): string)=} filename + * @property {string=} idHint + * @property {string} automaticNameDelimiter + * @property {boolean} reuseExistingChunk + * @property {boolean} usedExports + * @property {boolean} _validateSize + * @property {boolean} _validateRemainingSize + * @property {SplitChunksSizes} _minSizeForMaxSize + * @property {boolean} _conditionalEnforce + */ +/** + * @typedef {Object} FallbackCacheGroup + * @property {ChunkFilterFunction} chunksFilter + * @property {SplitChunksSizes} minSize + * @property {SplitChunksSizes} maxAsyncSize + * @property {SplitChunksSizes} maxInitialSize + * @property {string} automaticNameDelimiter + */ +/** + * @typedef {Object} CacheGroupsContext + * @property {ModuleGraph} moduleGraph + * @property {ChunkGraph} chunkGraph + */ -const RuntimeGlobals = __webpack_require__(49404); -const RuntimeModule = __webpack_require__(61439); -const Template = __webpack_require__(92066); +/** + * @callback GetCacheGroups + * @param {Module} module + * @param {CacheGroupsContext} context + * @returns {CacheGroupSource[]} + */ -class EnsureChunkRuntimeModule extends RuntimeModule { - constructor(runtimeRequirements) { - super("ensure chunk"); - this.runtimeRequirements = runtimeRequirements; - } +/** + * @callback GetName + * @param {Module=} module + * @param {Chunk[]=} chunks + * @param {string=} key + * @returns {string=} + */ - /** - * @returns {string} runtime code - */ - generate() { - const { runtimeTemplate } = this.compilation; - // Check if there are non initial chunks which need to be imported using require-ensure - if (this.runtimeRequirements.has(RuntimeGlobals.ensureChunkHandlers)) { - const handlers = RuntimeGlobals.ensureChunkHandlers; - return Template.asString([ - `${handlers} = {};`, - "// This file contains only the entry chunk.", - "// The chunk loading function for additional chunks", - `${RuntimeGlobals.ensureChunk} = ${runtimeTemplate.basicFunction( - "chunkId", - [ - `return Promise.all(Object.keys(${handlers}).reduce(${runtimeTemplate.basicFunction( - "promises, key", - [`${handlers}[key](chunkId, promises);`, "return promises;"] - )}, []));` - ] - )};` - ]); - } else { - // There ensureChunk is used somewhere in the tree, so we need an empty requireEnsure - // function. This can happen with multiple entrypoints. - return Template.asString([ - "// The chunk loading function for additional chunks", - "// Since all referenced chunks are already included", - "// in this file, this function is empty here.", - `${RuntimeGlobals.ensureChunk} = ${runtimeTemplate.returningFunction( - "Promise.resolve()" - )};` - ]); - } - } -} +/** + * @typedef {Object} SplitChunksOptions + * @property {ChunkFilterFunction} chunksFilter + * @property {string[]} defaultSizeTypes + * @property {SplitChunksSizes} minSize + * @property {SplitChunksSizes} minSizeReduction + * @property {SplitChunksSizes} minRemainingSize + * @property {SplitChunksSizes} enforceSizeThreshold + * @property {SplitChunksSizes} maxInitialSize + * @property {SplitChunksSizes} maxAsyncSize + * @property {number} minChunks + * @property {number} maxAsyncRequests + * @property {number} maxInitialRequests + * @property {boolean} hidePathInfo + * @property {string | function(PathData, AssetInfo=): string} filename + * @property {string} automaticNameDelimiter + * @property {GetCacheGroups} getCacheGroups + * @property {GetName} getName + * @property {boolean} usedExports + * @property {FallbackCacheGroup} fallbackCacheGroup + */ -module.exports = EnsureChunkRuntimeModule; +/** + * @typedef {Object} ChunksInfoItem + * @property {SortableSet} modules + * @property {CacheGroup} cacheGroup + * @property {number} cacheGroupIndex + * @property {string} name + * @property {Record} sizes + * @property {Set} chunks + * @property {Set} reuseableChunks + * @property {Set} chunksKeys + */ +const defaultGetName = /** @type {GetName} */ (() => {}); -/***/ }), +const deterministicGroupingForModules = + /** @type {function(DeterministicGroupingOptionsForModule): DeterministicGroupingGroupedItemsForModule[]} */ ( + deterministicGrouping + ); -/***/ 53288: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { +/** @type {WeakMap} */ +const getKeyCache = new WeakMap(); -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php -*/ +/** + * @param {string} name a filename to hash + * @param {OutputOptions} outputOptions hash function used + * @returns {string} hashed filename + */ +const hashFilename = (name, outputOptions) => { + const digest = /** @type {string} */ ( + createHash(outputOptions.hashFunction) + .update(name) + .digest(outputOptions.hashDigest) + ); + return digest.slice(0, 8); +}; +/** + * @param {Chunk} chunk the chunk + * @returns {number} the number of requests + */ +const getRequests = chunk => { + let requests = 0; + for (const chunkGroup of chunk.groupsIterable) { + requests = Math.max(requests, chunkGroup.chunks.length); + } + return requests; +}; +const mapObject = (obj, fn) => { + const newObj = Object.create(null); + for (const key of Object.keys(obj)) { + newObj[key] = fn(obj[key], key); + } + return newObj; +}; -const RuntimeGlobals = __webpack_require__(49404); -const RuntimeModule = __webpack_require__(61439); -const Template = __webpack_require__(92066); -const { first } = __webpack_require__(34715); +/** + * @template T + * @param {Set} a set + * @param {Set} b other set + * @returns {boolean} true if at least one item of a is in b + */ +const isOverlap = (a, b) => { + for (const item of a) { + if (b.has(item)) return true; + } + return false; +}; -/** @typedef {import("../Chunk")} Chunk */ -/** @typedef {import("../Compilation")} Compilation */ -/** @typedef {import("../Compilation").AssetInfo} AssetInfo */ -/** @typedef {import("../Compilation").PathData} PathData */ +const compareModuleIterables = compareIterables(compareModulesByIdentifier); -/** @typedef {function(PathData, AssetInfo=): string} FilenameFunction */ +/** + * @param {ChunksInfoItem} a item + * @param {ChunksInfoItem} b item + * @returns {number} compare result + */ +const compareEntries = (a, b) => { + // 1. by priority + const diffPriority = a.cacheGroup.priority - b.cacheGroup.priority; + if (diffPriority) return diffPriority; + // 2. by number of chunks + const diffCount = a.chunks.size - b.chunks.size; + if (diffCount) return diffCount; + // 3. by size reduction + const aSizeReduce = totalSize(a.sizes) * (a.chunks.size - 1); + const bSizeReduce = totalSize(b.sizes) * (b.chunks.size - 1); + const diffSizeReduce = aSizeReduce - bSizeReduce; + if (diffSizeReduce) return diffSizeReduce; + // 4. by cache group index + const indexDiff = b.cacheGroupIndex - a.cacheGroupIndex; + if (indexDiff) return indexDiff; + // 5. by number of modules (to be able to compare by identifier) + const modulesA = a.modules; + const modulesB = b.modules; + const diff = modulesA.size - modulesB.size; + if (diff) return diff; + // 6. by module identifiers + modulesA.sort(); + modulesB.sort(); + return compareModuleIterables(modulesA, modulesB); +}; -class GetChunkFilenameRuntimeModule extends RuntimeModule { - /** - * @param {string} contentType the contentType to use the content hash for - * @param {string} name kind of filename - * @param {string} global function name to be assigned - * @param {function(Chunk): string | FilenameFunction} getFilenameForChunk functor to get the filename or function - * @param {boolean} allChunks when false, only async chunks are included - */ - constructor(contentType, name, global, getFilenameForChunk, allChunks) { - super(`get ${name} chunk filename`); - this.contentType = contentType; - this.global = global; - this.getFilenameForChunk = getFilenameForChunk; - this.allChunks = allChunks; - this.dependentHash = true; - } +const INITIAL_CHUNK_FILTER = chunk => chunk.canBeInitial(); +const ASYNC_CHUNK_FILTER = chunk => !chunk.canBeInitial(); +const ALL_CHUNK_FILTER = chunk => true; - /** - * @returns {string} runtime code - */ - generate() { - const { - global, - chunk, - chunkGraph, - contentType, - getFilenameForChunk, - allChunks, - compilation - } = this; - const { runtimeTemplate } = compilation; +/** + * @param {OptimizationSplitChunksSizes} value the sizes + * @param {string[]} defaultSizeTypes the default size types + * @returns {SplitChunksSizes} normalized representation + */ +const normalizeSizes = (value, defaultSizeTypes) => { + if (typeof value === "number") { + /** @type {Record} */ + const o = {}; + for (const sizeType of defaultSizeTypes) o[sizeType] = value; + return o; + } else if (typeof value === "object" && value !== null) { + return { ...value }; + } else { + return {}; + } +}; - /** @type {Map>} */ - const chunkFilenames = new Map(); - let maxChunks = 0; - /** @type {string} */ - let dynamicFilename; +/** + * @param {...SplitChunksSizes} sizes the sizes + * @returns {SplitChunksSizes} the merged sizes + */ +const mergeSizes = (...sizes) => { + /** @type {SplitChunksSizes} */ + let merged = {}; + for (let i = sizes.length - 1; i >= 0; i--) { + merged = Object.assign(merged, sizes[i]); + } + return merged; +}; - /** - * @param {Chunk} c the chunk - * @returns {void} - */ - const addChunk = c => { - const chunkFilename = getFilenameForChunk(c); - if (chunkFilename) { - let set = chunkFilenames.get(chunkFilename); - if (set === undefined) { - chunkFilenames.set(chunkFilename, (set = new Set())); - } - set.add(c); - if (typeof chunkFilename === "string") { - if (set.size < maxChunks) return; - if (set.size === maxChunks) { - if (chunkFilename.length < dynamicFilename.length) return; - if (chunkFilename.length === dynamicFilename.length) { - if (chunkFilename < dynamicFilename) return; - } - } - maxChunks = set.size; - dynamicFilename = chunkFilename; - } - } - }; +/** + * @param {SplitChunksSizes} sizes the sizes + * @returns {boolean} true, if there are sizes > 0 + */ +const hasNonZeroSizes = sizes => { + for (const key of Object.keys(sizes)) { + if (sizes[key] > 0) return true; + } + return false; +}; - /** @type {string[]} */ - const includedChunksMessages = []; - if (allChunks) { - includedChunksMessages.push("all chunks"); - for (const c of chunk.getAllReferencedChunks()) { - addChunk(c); - } +/** + * @param {SplitChunksSizes} a first sizes + * @param {SplitChunksSizes} b second sizes + * @param {CombineSizeFunction} combine a function to combine sizes + * @returns {SplitChunksSizes} the combine sizes + */ +const combineSizes = (a, b, combine) => { + const aKeys = new Set(Object.keys(a)); + const bKeys = new Set(Object.keys(b)); + /** @type {SplitChunksSizes} */ + const result = {}; + for (const key of aKeys) { + if (bKeys.has(key)) { + result[key] = combine(a[key], b[key]); } else { - includedChunksMessages.push("async chunks"); - for (const c of chunk.getAllAsyncChunks()) { - addChunk(c); - } - const includeEntries = chunkGraph - .getTreeRuntimeRequirements(chunk) - .has(RuntimeGlobals.ensureChunkIncludeEntries); - if (includeEntries) { - includedChunksMessages.push("sibling chunks for the entrypoint"); - for (const c of chunkGraph.getChunkEntryDependentChunksIterable( - chunk - )) { - addChunk(c); - } - } + result[key] = a[key]; } - for (const entrypoint of chunk.getAllReferencedAsyncEntrypoints()) { - addChunk(entrypoint.chunks[entrypoint.chunks.length - 1]); + } + for (const key of bKeys) { + if (!aKeys.has(key)) { + result[key] = b[key]; } + } + return result; +}; - /** @type {Map>} */ - const staticUrls = new Map(); - /** @type {Set} */ - const dynamicUrlChunks = new Set(); +/** + * @param {SplitChunksSizes} sizes the sizes + * @param {SplitChunksSizes} minSize the min sizes + * @returns {boolean} true if there are sizes and all existing sizes are at least `minSize` + */ +const checkMinSize = (sizes, minSize) => { + for (const key of Object.keys(minSize)) { + const size = sizes[key]; + if (size === undefined || size === 0) continue; + if (size < minSize[key]) return false; + } + return true; +}; - /** - * @param {Chunk} c the chunk - * @param {string | FilenameFunction} chunkFilename the filename template for the chunk - * @returns {void} - */ - const addStaticUrl = (c, chunkFilename) => { - /** - * @param {string | number} value a value - * @returns {string} string to put in quotes - */ - const unquotedStringify = value => { - const str = `${value}`; - if (str.length >= 5 && str === `${c.id}`) { - // This is shorter and generates the same result - return '" + chunkId + "'; - } - const s = JSON.stringify(str); - return s.slice(1, s.length - 1); - }; - const unquotedStringifyWithLength = value => length => - unquotedStringify(`${value}`.slice(0, length)); - const chunkFilenameValue = - typeof chunkFilename === "function" - ? JSON.stringify( - chunkFilename({ - chunk: c, - contentHashType: contentType - }) - ) - : JSON.stringify(chunkFilename); - const staticChunkFilename = compilation.getPath(chunkFilenameValue, { - hash: `" + ${RuntimeGlobals.getFullHash}() + "`, - hashWithLength: length => - `" + ${RuntimeGlobals.getFullHash}().slice(0, ${length}) + "`, - chunk: { - id: unquotedStringify(c.id), - hash: unquotedStringify(c.renderedHash), - hashWithLength: unquotedStringifyWithLength(c.renderedHash), - name: unquotedStringify(c.name || c.id), - contentHash: { - [contentType]: unquotedStringify(c.contentHash[contentType]) - }, - contentHashWithLength: { - [contentType]: unquotedStringifyWithLength( - c.contentHash[contentType] - ) - } - }, - contentHashType: contentType - }); - let set = staticUrls.get(staticChunkFilename); - if (set === undefined) { - staticUrls.set(staticChunkFilename, (set = new Set())); - } - set.add(c.id); - }; +/** + * @param {SplitChunksSizes} sizes the sizes + * @param {SplitChunksSizes} minSizeReduction the min sizes + * @param {number} chunkCount number of chunks + * @returns {boolean} true if there are sizes and all existing sizes are at least `minSizeReduction` + */ +const checkMinSizeReduction = (sizes, minSizeReduction, chunkCount) => { + for (const key of Object.keys(minSizeReduction)) { + const size = sizes[key]; + if (size === undefined || size === 0) continue; + if (size * chunkCount < minSizeReduction[key]) return false; + } + return true; +}; - for (const [filename, chunks] of chunkFilenames) { - if (filename !== dynamicFilename) { - for (const c of chunks) addStaticUrl(c, filename); - } else { - for (const c of chunks) dynamicUrlChunks.add(c); - } +/** + * @param {SplitChunksSizes} sizes the sizes + * @param {SplitChunksSizes} minSize the min sizes + * @returns {undefined | string[]} list of size types that are below min size + */ +const getViolatingMinSizes = (sizes, minSize) => { + let list; + for (const key of Object.keys(minSize)) { + const size = sizes[key]; + if (size === undefined || size === 0) continue; + if (size < minSize[key]) { + if (list === undefined) list = [key]; + else list.push(key); } + } + return list; +}; - /** - * @param {function(Chunk): string | number} fn function from chunk to value - * @returns {string} code with static mapping of results of fn - */ - const createMap = fn => { - const obj = {}; - let useId = false; - let lastKey; - let entries = 0; - for (const c of dynamicUrlChunks) { - const value = fn(c); - if (value === c.id) { - useId = true; - } else { - obj[c.id] = value; - lastKey = c.id; - entries++; - } - } - if (entries === 0) return "chunkId"; - if (entries === 1) { - return useId - ? `(chunkId === ${JSON.stringify(lastKey)} ? ${JSON.stringify( - obj[lastKey] - )} : chunkId)` - : JSON.stringify(obj[lastKey]); - } - return useId - ? `(${JSON.stringify(obj)}[chunkId] || chunkId)` - : `${JSON.stringify(obj)}[chunkId]`; - }; +/** + * @param {SplitChunksSizes} sizes the sizes + * @returns {number} the total size + */ +const totalSize = sizes => { + let size = 0; + for (const key of Object.keys(sizes)) { + size += sizes[key]; + } + return size; +}; - /** - * @param {function(Chunk): string | number} fn function from chunk to value - * @returns {string} code with static mapping of results of fn for including in quoted string - */ - const mapExpr = fn => { - return `" + ${createMap(fn)} + "`; - }; +/** + * @param {false|string|Function} name the chunk name + * @returns {GetName} a function to get the name of the chunk + */ +const normalizeName = name => { + if (typeof name === "string") { + return () => name; + } + if (typeof name === "function") { + return /** @type {GetName} */ (name); + } +}; + +/** + * @param {OptimizationSplitChunksCacheGroup["chunks"]} chunks the chunk filter option + * @returns {ChunkFilterFunction} the chunk filter function + */ +const normalizeChunksFilter = chunks => { + if (chunks === "initial") { + return INITIAL_CHUNK_FILTER; + } + if (chunks === "async") { + return ASYNC_CHUNK_FILTER; + } + if (chunks === "all") { + return ALL_CHUNK_FILTER; + } + if (typeof chunks === "function") { + return chunks; + } +}; +/** + * @param {GetCacheGroups | Record} cacheGroups the cache group options + * @param {string[]} defaultSizeTypes the default size types + * @returns {GetCacheGroups} a function to get the cache groups + */ +const normalizeCacheGroups = (cacheGroups, defaultSizeTypes) => { + if (typeof cacheGroups === "function") { + return cacheGroups; + } + if (typeof cacheGroups === "object" && cacheGroups !== null) { + /** @type {(function(Module, CacheGroupsContext, CacheGroupSource[]): void)[]} */ + const handlers = []; + for (const key of Object.keys(cacheGroups)) { + const option = cacheGroups[key]; + if (option === false) { + continue; + } + if (typeof option === "string" || option instanceof RegExp) { + const source = createCacheGroupSource({}, key, defaultSizeTypes); + handlers.push((module, context, results) => { + if (checkTest(option, module, context)) { + results.push(source); + } + }); + } else if (typeof option === "function") { + const cache = new WeakMap(); + handlers.push((module, context, results) => { + const result = option(module); + if (result) { + const groups = Array.isArray(result) ? result : [result]; + for (const group of groups) { + const cachedSource = cache.get(group); + if (cachedSource !== undefined) { + results.push(cachedSource); + } else { + const source = createCacheGroupSource( + group, + key, + defaultSizeTypes + ); + cache.set(group, source); + results.push(source); + } + } + } + }); + } else { + const source = createCacheGroupSource(option, key, defaultSizeTypes); + handlers.push((module, context, results) => { + if ( + checkTest(option.test, module, context) && + checkModuleType(option.type, module) && + checkModuleLayer(option.layer, module) + ) { + results.push(source); + } + }); + } + } /** - * @param {function(Chunk): string | number} fn function from chunk to value - * @returns {function(number): string} function which generates code with static mapping of results of fn for including in quoted string for specific length + * @param {Module} module the current module + * @param {CacheGroupsContext} context the current context + * @returns {CacheGroupSource[]} the matching cache groups */ - const mapExprWithLength = fn => length => { - return `" + ${createMap(c => `${fn(c)}`.slice(0, length))} + "`; + const fn = (module, context) => { + /** @type {CacheGroupSource[]} */ + let results = []; + for (const fn of handlers) { + fn(module, context, results); + } + return results; }; - - const url = - dynamicFilename && - compilation.getPath(JSON.stringify(dynamicFilename), { - hash: `" + ${RuntimeGlobals.getFullHash}() + "`, - hashWithLength: length => - `" + ${RuntimeGlobals.getFullHash}().slice(0, ${length}) + "`, - chunk: { - id: `" + chunkId + "`, - hash: mapExpr(c => c.renderedHash), - hashWithLength: mapExprWithLength(c => c.renderedHash), - name: mapExpr(c => c.name || c.id), - contentHash: { - [contentType]: mapExpr(c => c.contentHash[contentType]) - }, - contentHashWithLength: { - [contentType]: mapExprWithLength(c => c.contentHash[contentType]) - } - }, - contentHashType: contentType - }); - - return Template.asString([ - `// This function allow to reference ${includedChunksMessages.join( - " and " - )}`, - `${global} = ${runtimeTemplate.basicFunction( - "chunkId", - - staticUrls.size > 0 - ? [ - "// return url for filenames not based on template", - // it minimizes to `x===1?"...":x===2?"...":"..."` - Template.asString( - Array.from(staticUrls, ([url, ids]) => { - const condition = - ids.size === 1 - ? `chunkId === ${JSON.stringify(first(ids))}` - : `{${Array.from( - ids, - id => `${JSON.stringify(id)}:1` - ).join(",")}}[chunkId]`; - return `if (${condition}) return ${url};`; - }) - ), - "// return url for filenames based on template", - `return ${url};` - ] - : ["// return url for filenames based on template", `return ${url};`] - )};` - ]); + return fn; } -} - -module.exports = GetChunkFilenameRuntimeModule; - - -/***/ }), - -/***/ 28454: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php -*/ - - - -const RuntimeGlobals = __webpack_require__(49404); -const RuntimeModule = __webpack_require__(61439); - -/** @typedef {import("../Compilation")} Compilation */ + return () => null; +}; -class GetFullHashRuntimeModule extends RuntimeModule { - constructor() { - super("getFullHash"); - this.fullHash = true; +/** + * @param {undefined|boolean|string|RegExp|Function} test test option + * @param {Module} module the module + * @param {CacheGroupsContext} context context object + * @returns {boolean} true, if the module should be selected + */ +const checkTest = (test, module, context) => { + if (test === undefined) return true; + if (typeof test === "function") { + return test(module, context); } - - /** - * @returns {string} runtime code - */ - generate() { - const { runtimeTemplate } = this.compilation; - return `${RuntimeGlobals.getFullHash} = ${runtimeTemplate.returningFunction( - JSON.stringify(this.compilation.hash || "XXXX") - )}`; + if (typeof test === "boolean") return test; + if (typeof test === "string") { + const name = module.nameForCondition(); + return name && name.startsWith(test); } -} - -module.exports = GetFullHashRuntimeModule; - - -/***/ }), + if (test instanceof RegExp) { + const name = module.nameForCondition(); + return name && test.test(name); + } + return false; +}; -/***/ 10034: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { +/** + * @param {undefined|string|RegExp|Function} test type option + * @param {Module} module the module + * @returns {boolean} true, if the module should be selected + */ +const checkModuleType = (test, module) => { + if (test === undefined) return true; + if (typeof test === "function") { + return test(module.type); + } + if (typeof test === "string") { + const type = module.type; + return test === type; + } + if (test instanceof RegExp) { + const type = module.type; + return test.test(type); + } + return false; +}; -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php -*/ +/** + * @param {undefined|string|RegExp|Function} test type option + * @param {Module} module the module + * @returns {boolean} true, if the module should be selected + */ +const checkModuleLayer = (test, module) => { + if (test === undefined) return true; + if (typeof test === "function") { + return test(module.layer); + } + if (typeof test === "string") { + const layer = module.layer; + return test === "" ? !layer : layer && layer.startsWith(test); + } + if (test instanceof RegExp) { + const layer = module.layer; + return test.test(layer); + } + return false; +}; +/** + * @param {OptimizationSplitChunksCacheGroup} options the group options + * @param {string} key key of cache group + * @param {string[]} defaultSizeTypes the default size types + * @returns {CacheGroupSource} the normalized cached group + */ +const createCacheGroupSource = (options, key, defaultSizeTypes) => { + const minSize = normalizeSizes(options.minSize, defaultSizeTypes); + const minSizeReduction = normalizeSizes( + options.minSizeReduction, + defaultSizeTypes + ); + const maxSize = normalizeSizes(options.maxSize, defaultSizeTypes); + return { + key, + priority: options.priority, + getName: normalizeName(options.name), + chunksFilter: normalizeChunksFilter(options.chunks), + enforce: options.enforce, + minSize, + minSizeReduction, + minRemainingSize: mergeSizes( + normalizeSizes(options.minRemainingSize, defaultSizeTypes), + minSize + ), + enforceSizeThreshold: normalizeSizes( + options.enforceSizeThreshold, + defaultSizeTypes + ), + maxAsyncSize: mergeSizes( + normalizeSizes(options.maxAsyncSize, defaultSizeTypes), + maxSize + ), + maxInitialSize: mergeSizes( + normalizeSizes(options.maxInitialSize, defaultSizeTypes), + maxSize + ), + minChunks: options.minChunks, + maxAsyncRequests: options.maxAsyncRequests, + maxInitialRequests: options.maxInitialRequests, + filename: options.filename, + idHint: options.idHint, + automaticNameDelimiter: options.automaticNameDelimiter, + reuseExistingChunk: options.reuseExistingChunk, + usedExports: options.usedExports + }; +}; +module.exports = class SplitChunksPlugin { + /** + * @param {OptimizationSplitChunksOptions=} options plugin options + */ + constructor(options = {}) { + const defaultSizeTypes = options.defaultSizeTypes || [ + "javascript", + "unknown" + ]; + const fallbackCacheGroup = options.fallbackCacheGroup || {}; + const minSize = normalizeSizes(options.minSize, defaultSizeTypes); + const minSizeReduction = normalizeSizes( + options.minSizeReduction, + defaultSizeTypes + ); + const maxSize = normalizeSizes(options.maxSize, defaultSizeTypes); -const RuntimeGlobals = __webpack_require__(49404); -const RuntimeModule = __webpack_require__(61439); -const Template = __webpack_require__(92066); + /** @type {SplitChunksOptions} */ + this.options = { + chunksFilter: normalizeChunksFilter(options.chunks || "all"), + defaultSizeTypes, + minSize, + minSizeReduction, + minRemainingSize: mergeSizes( + normalizeSizes(options.minRemainingSize, defaultSizeTypes), + minSize + ), + enforceSizeThreshold: normalizeSizes( + options.enforceSizeThreshold, + defaultSizeTypes + ), + maxAsyncSize: mergeSizes( + normalizeSizes(options.maxAsyncSize, defaultSizeTypes), + maxSize + ), + maxInitialSize: mergeSizes( + normalizeSizes(options.maxInitialSize, defaultSizeTypes), + maxSize + ), + minChunks: options.minChunks || 1, + maxAsyncRequests: options.maxAsyncRequests || 1, + maxInitialRequests: options.maxInitialRequests || 1, + hidePathInfo: options.hidePathInfo || false, + filename: options.filename || undefined, + getCacheGroups: normalizeCacheGroups( + options.cacheGroups, + defaultSizeTypes + ), + getName: options.name ? normalizeName(options.name) : defaultGetName, + automaticNameDelimiter: options.automaticNameDelimiter, + usedExports: options.usedExports, + fallbackCacheGroup: { + chunksFilter: normalizeChunksFilter( + fallbackCacheGroup.chunks || options.chunks || "all" + ), + minSize: mergeSizes( + normalizeSizes(fallbackCacheGroup.minSize, defaultSizeTypes), + minSize + ), + maxAsyncSize: mergeSizes( + normalizeSizes(fallbackCacheGroup.maxAsyncSize, defaultSizeTypes), + normalizeSizes(fallbackCacheGroup.maxSize, defaultSizeTypes), + normalizeSizes(options.maxAsyncSize, defaultSizeTypes), + normalizeSizes(options.maxSize, defaultSizeTypes) + ), + maxInitialSize: mergeSizes( + normalizeSizes(fallbackCacheGroup.maxInitialSize, defaultSizeTypes), + normalizeSizes(fallbackCacheGroup.maxSize, defaultSizeTypes), + normalizeSizes(options.maxInitialSize, defaultSizeTypes), + normalizeSizes(options.maxSize, defaultSizeTypes) + ), + automaticNameDelimiter: + fallbackCacheGroup.automaticNameDelimiter || + options.automaticNameDelimiter || + "~" + } + }; -/** @typedef {import("../Compilation")} Compilation */ + /** @type {WeakMap} */ + this._cacheGroupCache = new WeakMap(); + } -class GetMainFilenameRuntimeModule extends RuntimeModule { /** - * @param {string} name readable name - * @param {string} global global object binding - * @param {string} filename main file name + * @param {CacheGroupSource} cacheGroupSource source + * @returns {CacheGroup} the cache group (cached) */ - constructor(name, global, filename) { - super(`get ${name} filename`); - this.global = global; - this.filename = filename; + _getCacheGroup(cacheGroupSource) { + const cacheEntry = this._cacheGroupCache.get(cacheGroupSource); + if (cacheEntry !== undefined) return cacheEntry; + const minSize = mergeSizes( + cacheGroupSource.minSize, + cacheGroupSource.enforce ? undefined : this.options.minSize + ); + const minSizeReduction = mergeSizes( + cacheGroupSource.minSizeReduction, + cacheGroupSource.enforce ? undefined : this.options.minSizeReduction + ); + const minRemainingSize = mergeSizes( + cacheGroupSource.minRemainingSize, + cacheGroupSource.enforce ? undefined : this.options.minRemainingSize + ); + const enforceSizeThreshold = mergeSizes( + cacheGroupSource.enforceSizeThreshold, + cacheGroupSource.enforce ? undefined : this.options.enforceSizeThreshold + ); + const cacheGroup = { + key: cacheGroupSource.key, + priority: cacheGroupSource.priority || 0, + chunksFilter: cacheGroupSource.chunksFilter || this.options.chunksFilter, + minSize, + minSizeReduction, + minRemainingSize, + enforceSizeThreshold, + maxAsyncSize: mergeSizes( + cacheGroupSource.maxAsyncSize, + cacheGroupSource.enforce ? undefined : this.options.maxAsyncSize + ), + maxInitialSize: mergeSizes( + cacheGroupSource.maxInitialSize, + cacheGroupSource.enforce ? undefined : this.options.maxInitialSize + ), + minChunks: + cacheGroupSource.minChunks !== undefined + ? cacheGroupSource.minChunks + : cacheGroupSource.enforce + ? 1 + : this.options.minChunks, + maxAsyncRequests: + cacheGroupSource.maxAsyncRequests !== undefined + ? cacheGroupSource.maxAsyncRequests + : cacheGroupSource.enforce + ? Infinity + : this.options.maxAsyncRequests, + maxInitialRequests: + cacheGroupSource.maxInitialRequests !== undefined + ? cacheGroupSource.maxInitialRequests + : cacheGroupSource.enforce + ? Infinity + : this.options.maxInitialRequests, + getName: + cacheGroupSource.getName !== undefined + ? cacheGroupSource.getName + : this.options.getName, + usedExports: + cacheGroupSource.usedExports !== undefined + ? cacheGroupSource.usedExports + : this.options.usedExports, + filename: + cacheGroupSource.filename !== undefined + ? cacheGroupSource.filename + : this.options.filename, + automaticNameDelimiter: + cacheGroupSource.automaticNameDelimiter !== undefined + ? cacheGroupSource.automaticNameDelimiter + : this.options.automaticNameDelimiter, + idHint: + cacheGroupSource.idHint !== undefined + ? cacheGroupSource.idHint + : cacheGroupSource.key, + reuseExistingChunk: cacheGroupSource.reuseExistingChunk || false, + _validateSize: hasNonZeroSizes(minSize), + _validateRemainingSize: hasNonZeroSizes(minRemainingSize), + _minSizeForMaxSize: mergeSizes( + cacheGroupSource.minSize, + this.options.minSize + ), + _conditionalEnforce: hasNonZeroSizes(enforceSizeThreshold) + }; + this._cacheGroupCache.set(cacheGroupSource, cacheGroup); + return cacheGroup; } /** - * @returns {string} runtime code + * Apply the plugin + * @param {Compiler} compiler the compiler instance + * @returns {void} */ - generate() { - const { global, filename, compilation, chunk } = this; - const { runtimeTemplate } = compilation; - const url = compilation.getPath(JSON.stringify(filename), { - hash: `" + ${RuntimeGlobals.getFullHash}() + "`, - hashWithLength: length => - `" + ${RuntimeGlobals.getFullHash}().slice(0, ${length}) + "`, - chunk, - runtime: chunk.runtime - }); - return Template.asString([ - `${global} = ${runtimeTemplate.returningFunction(url)};` - ]); - } -} + apply(compiler) { + const cachedMakePathsRelative = makePathsRelative.bindContextCache( + compiler.context, + compiler.root + ); + compiler.hooks.thisCompilation.tap("SplitChunksPlugin", compilation => { + const logger = compilation.getLogger("webpack.SplitChunksPlugin"); + let alreadyOptimized = false; + compilation.hooks.unseal.tap("SplitChunksPlugin", () => { + alreadyOptimized = false; + }); + compilation.hooks.optimizeChunks.tap( + { + name: "SplitChunksPlugin", + stage: STAGE_ADVANCED + }, + chunks => { + if (alreadyOptimized) return; + alreadyOptimized = true; + logger.time("prepare"); + const chunkGraph = compilation.chunkGraph; + const moduleGraph = compilation.moduleGraph; + // Give each selected chunk an index (to create strings from chunks) + /** @type {Map} */ + const chunkIndexMap = new Map(); + const ZERO = BigInt("0"); + const ONE = BigInt("1"); + const START = ONE << BigInt("31"); + let index = START; + for (const chunk of chunks) { + chunkIndexMap.set( + chunk, + index | BigInt((Math.random() * 0x7fffffff) | 0) + ); + index = index << ONE; + } + /** + * @param {Iterable} chunks list of chunks + * @returns {bigint | Chunk} key of the chunks + */ + const getKey = chunks => { + const iterator = chunks[Symbol.iterator](); + let result = iterator.next(); + if (result.done) return ZERO; + const first = result.value; + result = iterator.next(); + if (result.done) return first; + let key = + chunkIndexMap.get(first) | chunkIndexMap.get(result.value); + while (!(result = iterator.next()).done) { + const raw = chunkIndexMap.get(result.value); + key = key ^ raw; + } + return key; + }; + const keyToString = key => { + if (typeof key === "bigint") return key.toString(16); + return chunkIndexMap.get(key).toString(16); + }; + + const getChunkSetsInGraph = memoize(() => { + /** @type {Map>} */ + const chunkSetsInGraph = new Map(); + /** @type {Set} */ + const singleChunkSets = new Set(); + for (const module of compilation.modules) { + const chunks = chunkGraph.getModuleChunksIterable(module); + const chunksKey = getKey(chunks); + if (typeof chunksKey === "bigint") { + if (!chunkSetsInGraph.has(chunksKey)) { + chunkSetsInGraph.set(chunksKey, new Set(chunks)); + } + } else { + singleChunkSets.add(chunksKey); + } + } + return { chunkSetsInGraph, singleChunkSets }; + }); + + /** + * @param {Module} module the module + * @returns {Iterable} groups of chunks with equal exports + */ + const groupChunksByExports = module => { + const exportsInfo = moduleGraph.getExportsInfo(module); + const groupedByUsedExports = new Map(); + for (const chunk of chunkGraph.getModuleChunksIterable(module)) { + const key = exportsInfo.getUsageKey(chunk.runtime); + const list = groupedByUsedExports.get(key); + if (list !== undefined) { + list.push(chunk); + } else { + groupedByUsedExports.set(key, [chunk]); + } + } + return groupedByUsedExports.values(); + }; -module.exports = GetMainFilenameRuntimeModule; + /** @type {Map>} */ + const groupedByExportsMap = new Map(); + const getExportsChunkSetsInGraph = memoize(() => { + /** @type {Map>} */ + const chunkSetsInGraph = new Map(); + /** @type {Set} */ + const singleChunkSets = new Set(); + for (const module of compilation.modules) { + const groupedChunks = Array.from(groupChunksByExports(module)); + groupedByExportsMap.set(module, groupedChunks); + for (const chunks of groupedChunks) { + if (chunks.length === 1) { + singleChunkSets.add(chunks[0]); + } else { + const chunksKey = /** @type {bigint} */ (getKey(chunks)); + if (!chunkSetsInGraph.has(chunksKey)) { + chunkSetsInGraph.set(chunksKey, new Set(chunks)); + } + } + } + } + return { chunkSetsInGraph, singleChunkSets }; + }); -/***/ }), + // group these set of chunks by count + // to allow to check less sets via isSubset + // (only smaller sets can be subset) + const groupChunkSetsByCount = chunkSets => { + /** @type {Map>>} */ + const chunkSetsByCount = new Map(); + for (const chunksSet of chunkSets) { + const count = chunksSet.size; + let array = chunkSetsByCount.get(count); + if (array === undefined) { + array = []; + chunkSetsByCount.set(count, array); + } + array.push(chunksSet); + } + return chunkSetsByCount; + }; + const getChunkSetsByCount = memoize(() => + groupChunkSetsByCount( + getChunkSetsInGraph().chunkSetsInGraph.values() + ) + ); + const getExportsChunkSetsByCount = memoize(() => + groupChunkSetsByCount( + getExportsChunkSetsInGraph().chunkSetsInGraph.values() + ) + ); -/***/ 89651: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + // Create a list of possible combinations + const createGetCombinations = ( + chunkSets, + singleChunkSets, + chunkSetsByCount + ) => { + /** @type {Map | Chunk)[]>} */ + const combinationsCache = new Map(); -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php -*/ + return key => { + const cacheEntry = combinationsCache.get(key); + if (cacheEntry !== undefined) return cacheEntry; + if (key instanceof Chunk) { + const result = [key]; + combinationsCache.set(key, result); + return result; + } + const chunksSet = chunkSets.get(key); + /** @type {(Set | Chunk)[]} */ + const array = [chunksSet]; + for (const [count, setArray] of chunkSetsByCount) { + // "equal" is not needed because they would have been merge in the first step + if (count < chunksSet.size) { + for (const set of setArray) { + if (isSubset(chunksSet, set)) { + array.push(set); + } + } + } + } + for (const chunk of singleChunkSets) { + if (chunksSet.has(chunk)) { + array.push(chunk); + } + } + combinationsCache.set(key, array); + return array; + }; + }; + const getCombinationsFactory = memoize(() => { + const { chunkSetsInGraph, singleChunkSets } = getChunkSetsInGraph(); + return createGetCombinations( + chunkSetsInGraph, + singleChunkSets, + getChunkSetsByCount() + ); + }); + const getCombinations = key => getCombinationsFactory()(key); + const getExportsCombinationsFactory = memoize(() => { + const { chunkSetsInGraph, singleChunkSets } = + getExportsChunkSetsInGraph(); + return createGetCombinations( + chunkSetsInGraph, + singleChunkSets, + getExportsChunkSetsByCount() + ); + }); + const getExportsCombinations = key => + getExportsCombinationsFactory()(key); -const RuntimeGlobals = __webpack_require__(49404); -const RuntimeModule = __webpack_require__(61439); -const Template = __webpack_require__(92066); + /** + * @typedef {Object} SelectedChunksResult + * @property {Chunk[]} chunks the list of chunks + * @property {bigint | Chunk} key a key of the list + */ -class GlobalRuntimeModule extends RuntimeModule { - constructor() { - super("global"); - } + /** @type {WeakMap | Chunk, WeakMap>} */ + const selectedChunksCacheByChunksSet = new WeakMap(); - /** - * @returns {string} runtime code - */ - generate() { - return Template.asString([ - `${RuntimeGlobals.global} = (function() {`, - Template.indent([ - "if (typeof globalThis === 'object') return globalThis;", - "try {", - Template.indent( - // This works in non-strict mode - // or - // This works if eval is allowed (see CSP) - "return this || new Function('return this')();" - ), - "} catch (e) {", - Template.indent( - // This works if the window reference is available - "if (typeof window === 'object') return window;" - ), - "}" - // It can still be `undefined`, but nothing to do about it... - // We return `undefined`, instead of nothing here, so it's - // easier to handle this case: - // if (!global) { … } - ]), - "})();" - ]); - } -} + /** + * get list and key by applying the filter function to the list + * It is cached for performance reasons + * @param {Set | Chunk} chunks list of chunks + * @param {ChunkFilterFunction} chunkFilter filter function for chunks + * @returns {SelectedChunksResult} list and key + */ + const getSelectedChunks = (chunks, chunkFilter) => { + let entry = selectedChunksCacheByChunksSet.get(chunks); + if (entry === undefined) { + entry = new WeakMap(); + selectedChunksCacheByChunksSet.set(chunks, entry); + } + /** @type {SelectedChunksResult} */ + let entry2 = entry.get(chunkFilter); + if (entry2 === undefined) { + /** @type {Chunk[]} */ + const selectedChunks = []; + if (chunks instanceof Chunk) { + if (chunkFilter(chunks)) selectedChunks.push(chunks); + } else { + for (const chunk of chunks) { + if (chunkFilter(chunk)) selectedChunks.push(chunk); + } + } + entry2 = { + chunks: selectedChunks, + key: getKey(selectedChunks) + }; + entry.set(chunkFilter, entry2); + } + return entry2; + }; -module.exports = GlobalRuntimeModule; + /** @type {Map} */ + const alreadyValidatedParents = new Map(); + /** @type {Set} */ + const alreadyReportedErrors = new Set(); + // Map a list of chunks to a list of modules + // For the key the chunk "index" is used, the value is a SortableSet of modules + /** @type {Map} */ + const chunksInfoMap = new Map(); -/***/ }), + /** + * @param {CacheGroup} cacheGroup the current cache group + * @param {number} cacheGroupIndex the index of the cache group of ordering + * @param {Chunk[]} selectedChunks chunks selected for this module + * @param {bigint | Chunk} selectedChunksKey a key of selectedChunks + * @param {Module} module the current module + * @returns {void} + */ + const addModuleToChunksInfoMap = ( + cacheGroup, + cacheGroupIndex, + selectedChunks, + selectedChunksKey, + module + ) => { + // Break if minimum number of chunks is not reached + if (selectedChunks.length < cacheGroup.minChunks) return; + // Determine name for split chunk + const name = cacheGroup.getName( + module, + selectedChunks, + cacheGroup.key + ); + // Check if the name is ok + const existingChunk = compilation.namedChunks.get(name); + if (existingChunk) { + const parentValidationKey = `${name}|${ + typeof selectedChunksKey === "bigint" + ? selectedChunksKey + : selectedChunksKey.debugId + }`; + const valid = alreadyValidatedParents.get(parentValidationKey); + if (valid === false) return; + if (valid === undefined) { + // Module can only be moved into the existing chunk if the existing chunk + // is a parent of all selected chunks + let isInAllParents = true; + /** @type {Set} */ + const queue = new Set(); + for (const chunk of selectedChunks) { + for (const group of chunk.groupsIterable) { + queue.add(group); + } + } + for (const group of queue) { + if (existingChunk.isInGroup(group)) continue; + let hasParent = false; + for (const parent of group.parentsIterable) { + hasParent = true; + queue.add(parent); + } + if (!hasParent) { + isInAllParents = false; + } + } + const valid = isInAllParents; + alreadyValidatedParents.set(parentValidationKey, valid); + if (!valid) { + if (!alreadyReportedErrors.has(name)) { + alreadyReportedErrors.add(name); + compilation.errors.push( + new WebpackError( + "SplitChunksPlugin\n" + + `Cache group "${cacheGroup.key}" conflicts with existing chunk.\n` + + `Both have the same name "${name}" and existing chunk is not a parent of the selected modules.\n` + + "Use a different name for the cache group or make sure that the existing chunk is a parent (e. g. via dependOn).\n" + + 'HINT: You can omit "name" to automatically create a name.\n' + + "BREAKING CHANGE: webpack < 5 used to allow to use an entrypoint as splitChunk. " + + "This is no longer allowed when the entrypoint is not a parent of the selected modules.\n" + + "Remove this entrypoint and add modules to cache group's 'test' instead. " + + "If you need modules to be evaluated on startup, add them to the existing entrypoints (make them arrays). " + + "See migration guide of more info." + ) + ); + } + return; + } + } + } + // Create key for maps + // When it has a name we use the name as key + // Otherwise we create the key from chunks and cache group key + // This automatically merges equal names + const key = + cacheGroup.key + + (name + ? ` name:${name}` + : ` chunks:${keyToString(selectedChunksKey)}`); + // Add module to maps + let info = chunksInfoMap.get(key); + if (info === undefined) { + chunksInfoMap.set( + key, + (info = { + modules: new SortableSet( + undefined, + compareModulesByIdentifier + ), + cacheGroup, + cacheGroupIndex, + name, + sizes: {}, + chunks: new Set(), + reuseableChunks: new Set(), + chunksKeys: new Set() + }) + ); + } + const oldSize = info.modules.size; + info.modules.add(module); + if (info.modules.size !== oldSize) { + for (const type of module.getSourceTypes()) { + info.sizes[type] = (info.sizes[type] || 0) + module.size(type); + } + } + const oldChunksKeysSize = info.chunksKeys.size; + info.chunksKeys.add(selectedChunksKey); + if (oldChunksKeysSize !== info.chunksKeys.size) { + for (const chunk of selectedChunks) { + info.chunks.add(chunk); + } + } + }; -/***/ 39399: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + const context = { + moduleGraph, + chunkGraph + }; -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Sergey Melyukov @smelukov -*/ + logger.timeEnd("prepare"); + logger.time("modules"); + // Walk through all modules + for (const module of compilation.modules) { + // Get cache group + let cacheGroups = this.options.getCacheGroups(module, context); + if (!Array.isArray(cacheGroups) || cacheGroups.length === 0) { + continue; + } -const RuntimeGlobals = __webpack_require__(49404); -const RuntimeModule = __webpack_require__(61439); -const Template = __webpack_require__(92066); + // Prepare some values (usedExports = false) + const getCombs = memoize(() => { + const chunks = chunkGraph.getModuleChunksIterable(module); + const chunksKey = getKey(chunks); + return getCombinations(chunksKey); + }); -class HasOwnPropertyRuntimeModule extends RuntimeModule { - constructor() { - super("hasOwnProperty shorthand"); - } + // Prepare some values (usedExports = true) + const getCombsByUsedExports = memoize(() => { + // fill the groupedByExportsMap + getExportsChunkSetsInGraph(); + /** @type {Set | Chunk>} */ + const set = new Set(); + const groupedByUsedExports = groupedByExportsMap.get(module); + for (const chunks of groupedByUsedExports) { + const chunksKey = getKey(chunks); + for (const comb of getExportsCombinations(chunksKey)) + set.add(comb); + } + return set; + }); - /** - * @returns {string} runtime code - */ - generate() { - const { runtimeTemplate } = this.compilation; + let cacheGroupIndex = 0; + for (const cacheGroupSource of cacheGroups) { + const cacheGroup = this._getCacheGroup(cacheGroupSource); - return Template.asString([ - `${RuntimeGlobals.hasOwnProperty} = ${runtimeTemplate.returningFunction( - "Object.prototype.hasOwnProperty.call(obj, prop)", - "obj, prop" - )}` - ]); - } -} + const combs = cacheGroup.usedExports + ? getCombsByUsedExports() + : getCombs(); + // For all combination of chunk selection + for (const chunkCombination of combs) { + // Break if minimum number of chunks is not reached + const count = + chunkCombination instanceof Chunk ? 1 : chunkCombination.size; + if (count < cacheGroup.minChunks) continue; + // Select chunks by configuration + const { chunks: selectedChunks, key: selectedChunksKey } = + getSelectedChunks(chunkCombination, cacheGroup.chunksFilter); -module.exports = HasOwnPropertyRuntimeModule; + addModuleToChunksInfoMap( + cacheGroup, + cacheGroupIndex, + selectedChunks, + selectedChunksKey, + module + ); + } + cacheGroupIndex++; + } + } + logger.timeEnd("modules"); -/***/ }), + logger.time("queue"); -/***/ 22970: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + /** + * @param {ChunksInfoItem} info entry + * @param {string[]} sourceTypes source types to be removed + */ + const removeModulesWithSourceType = (info, sourceTypes) => { + for (const module of info.modules) { + const types = module.getSourceTypes(); + if (sourceTypes.some(type => types.has(type))) { + info.modules.delete(module); + for (const type of types) { + info.sizes[type] -= module.size(type); + } + } + } + }; -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php -*/ + /** + * @param {ChunksInfoItem} info entry + * @returns {boolean} true, if entry become empty + */ + const removeMinSizeViolatingModules = info => { + if (!info.cacheGroup._validateSize) return false; + const violatingSizes = getViolatingMinSizes( + info.sizes, + info.cacheGroup.minSize + ); + if (violatingSizes === undefined) return false; + removeModulesWithSourceType(info, violatingSizes); + return info.modules.size === 0; + }; + // Filter items were size < minSize + for (const [key, info] of chunksInfoMap) { + if (removeMinSizeViolatingModules(info)) { + chunksInfoMap.delete(key); + } else if ( + !checkMinSizeReduction( + info.sizes, + info.cacheGroup.minSizeReduction, + info.chunks.size + ) + ) { + chunksInfoMap.delete(key); + } + } + /** + * @typedef {Object} MaxSizeQueueItem + * @property {SplitChunksSizes} minSize + * @property {SplitChunksSizes} maxAsyncSize + * @property {SplitChunksSizes} maxInitialSize + * @property {string} automaticNameDelimiter + * @property {string[]} keys + */ -const RuntimeModule = __webpack_require__(61439); + /** @type {Map} */ + const maxSizeQueueMap = new Map(); -class HelperRuntimeModule extends RuntimeModule { - /** - * @param {string} name a readable name - */ - constructor(name) { - super(name); - } -} + while (chunksInfoMap.size > 0) { + // Find best matching entry + let bestEntryKey; + let bestEntry; + for (const pair of chunksInfoMap) { + const key = pair[0]; + const info = pair[1]; + if ( + bestEntry === undefined || + compareEntries(bestEntry, info) < 0 + ) { + bestEntry = info; + bestEntryKey = key; + } + } -module.exports = HelperRuntimeModule; + const item = bestEntry; + chunksInfoMap.delete(bestEntryKey); + let chunkName = item.name; + // Variable for the new chunk (lazy created) + /** @type {Chunk} */ + let newChunk; + // When no chunk name, check if we can reuse a chunk instead of creating a new one + let isExistingChunk = false; + let isReusedWithAllModules = false; + if (chunkName) { + const chunkByName = compilation.namedChunks.get(chunkName); + if (chunkByName !== undefined) { + newChunk = chunkByName; + const oldSize = item.chunks.size; + item.chunks.delete(newChunk); + isExistingChunk = item.chunks.size !== oldSize; + } + } else if (item.cacheGroup.reuseExistingChunk) { + outer: for (const chunk of item.chunks) { + if ( + chunkGraph.getNumberOfChunkModules(chunk) !== + item.modules.size + ) { + continue; + } + if ( + item.chunks.size > 1 && + chunkGraph.getNumberOfEntryModules(chunk) > 0 + ) { + continue; + } + for (const module of item.modules) { + if (!chunkGraph.isModuleInChunk(module, chunk)) { + continue outer; + } + } + if (!newChunk || !newChunk.name) { + newChunk = chunk; + } else if ( + chunk.name && + chunk.name.length < newChunk.name.length + ) { + newChunk = chunk; + } else if ( + chunk.name && + chunk.name.length === newChunk.name.length && + chunk.name < newChunk.name + ) { + newChunk = chunk; + } + } + if (newChunk) { + item.chunks.delete(newChunk); + chunkName = undefined; + isExistingChunk = true; + isReusedWithAllModules = true; + } + } -/***/ }), + const enforced = + item.cacheGroup._conditionalEnforce && + checkMinSize(item.sizes, item.cacheGroup.enforceSizeThreshold); -/***/ 80647: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + const usedChunks = new Set(item.chunks); -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php -*/ + // Check if maxRequests condition can be fulfilled + if ( + !enforced && + (Number.isFinite(item.cacheGroup.maxInitialRequests) || + Number.isFinite(item.cacheGroup.maxAsyncRequests)) + ) { + for (const chunk of usedChunks) { + // respect max requests + const maxRequests = chunk.isOnlyInitial() + ? item.cacheGroup.maxInitialRequests + : chunk.canBeInitial() + ? Math.min( + item.cacheGroup.maxInitialRequests, + item.cacheGroup.maxAsyncRequests + ) + : item.cacheGroup.maxAsyncRequests; + if ( + isFinite(maxRequests) && + getRequests(chunk) >= maxRequests + ) { + usedChunks.delete(chunk); + } + } + } + outer: for (const chunk of usedChunks) { + for (const module of item.modules) { + if (chunkGraph.isModuleInChunk(module, chunk)) continue outer; + } + usedChunks.delete(chunk); + } + // Were some (invalid) chunks removed from usedChunks? + // => readd all modules to the queue, as things could have been changed + if (usedChunks.size < item.chunks.size) { + if (isExistingChunk) usedChunks.add(newChunk); + if (usedChunks.size >= item.cacheGroup.minChunks) { + const chunksArr = Array.from(usedChunks); + for (const module of item.modules) { + addModuleToChunksInfoMap( + item.cacheGroup, + item.cacheGroupIndex, + chunksArr, + getKey(usedChunks), + module + ); + } + } + continue; + } -const { SyncWaterfallHook } = __webpack_require__(34718); -const Compilation = __webpack_require__(59622); -const RuntimeGlobals = __webpack_require__(49404); -const Template = __webpack_require__(92066); -const HelperRuntimeModule = __webpack_require__(22970); + // Validate minRemainingSize constraint when a single chunk is left over + if ( + !enforced && + item.cacheGroup._validateRemainingSize && + usedChunks.size === 1 + ) { + const [chunk] = usedChunks; + let chunkSizes = Object.create(null); + for (const module of chunkGraph.getChunkModulesIterable(chunk)) { + if (!item.modules.has(module)) { + for (const type of module.getSourceTypes()) { + chunkSizes[type] = + (chunkSizes[type] || 0) + module.size(type); + } + } + } + const violatingSizes = getViolatingMinSizes( + chunkSizes, + item.cacheGroup.minRemainingSize + ); + if (violatingSizes !== undefined) { + const oldModulesSize = item.modules.size; + removeModulesWithSourceType(item, violatingSizes); + if ( + item.modules.size > 0 && + item.modules.size !== oldModulesSize + ) { + // queue this item again to be processed again + // without violating modules + chunksInfoMap.set(bestEntryKey, item); + } + continue; + } + } -/** @typedef {import("../Chunk")} Chunk */ -/** @typedef {import("../Compiler")} Compiler */ + // Create the new chunk if not reusing one + if (newChunk === undefined) { + newChunk = compilation.addChunk(chunkName); + } + // Walk through all chunks + for (const chunk of usedChunks) { + // Add graph connections for splitted chunk + chunk.split(newChunk); + } -/** - * @typedef {Object} LoadScriptCompilationHooks - * @property {SyncWaterfallHook<[string, Chunk]>} createScript - */ + // Add a note to the chunk + newChunk.chunkReason = + (newChunk.chunkReason ? newChunk.chunkReason + ", " : "") + + (isReusedWithAllModules + ? "reused as split chunk" + : "split chunk"); + if (item.cacheGroup.key) { + newChunk.chunkReason += ` (cache group: ${item.cacheGroup.key})`; + } + if (chunkName) { + newChunk.chunkReason += ` (name: ${chunkName})`; + } + if (item.cacheGroup.filename) { + newChunk.filenameTemplate = item.cacheGroup.filename; + } + if (item.cacheGroup.idHint) { + newChunk.idNameHints.add(item.cacheGroup.idHint); + } + if (!isReusedWithAllModules) { + // Add all modules to the new chunk + for (const module of item.modules) { + if (!module.chunkCondition(newChunk, compilation)) continue; + // Add module to new chunk + chunkGraph.connectChunkAndModule(newChunk, module); + // Remove module from used chunks + for (const chunk of usedChunks) { + chunkGraph.disconnectChunkAndModule(chunk, module); + } + } + } else { + // Remove all modules from used chunks + for (const module of item.modules) { + for (const chunk of usedChunks) { + chunkGraph.disconnectChunkAndModule(chunk, module); + } + } + } -/** @type {WeakMap} */ -const compilationHooksMap = new WeakMap(); + if ( + Object.keys(item.cacheGroup.maxAsyncSize).length > 0 || + Object.keys(item.cacheGroup.maxInitialSize).length > 0 + ) { + const oldMaxSizeSettings = maxSizeQueueMap.get(newChunk); + maxSizeQueueMap.set(newChunk, { + minSize: oldMaxSizeSettings + ? combineSizes( + oldMaxSizeSettings.minSize, + item.cacheGroup._minSizeForMaxSize, + Math.max + ) + : item.cacheGroup.minSize, + maxAsyncSize: oldMaxSizeSettings + ? combineSizes( + oldMaxSizeSettings.maxAsyncSize, + item.cacheGroup.maxAsyncSize, + Math.min + ) + : item.cacheGroup.maxAsyncSize, + maxInitialSize: oldMaxSizeSettings + ? combineSizes( + oldMaxSizeSettings.maxInitialSize, + item.cacheGroup.maxInitialSize, + Math.min + ) + : item.cacheGroup.maxInitialSize, + automaticNameDelimiter: item.cacheGroup.automaticNameDelimiter, + keys: oldMaxSizeSettings + ? oldMaxSizeSettings.keys.concat(item.cacheGroup.key) + : [item.cacheGroup.key] + }); + } -class LoadScriptRuntimeModule extends HelperRuntimeModule { - /** - * @param {Compilation} compilation the compilation - * @returns {LoadScriptCompilationHooks} hooks - */ - static getCompilationHooks(compilation) { - if (!(compilation instanceof Compilation)) { - throw new TypeError( - "The 'compilation' argument must be an instance of Compilation" - ); - } - let hooks = compilationHooksMap.get(compilation); - if (hooks === undefined) { - hooks = { - createScript: new SyncWaterfallHook(["source", "chunk"]) - }; - compilationHooksMap.set(compilation, hooks); - } - return hooks; - } + // remove all modules from other entries and update size + for (const [key, info] of chunksInfoMap) { + if (isOverlap(info.chunks, usedChunks)) { + // update modules and total size + // may remove it from the map when < minSize + let updated = false; + for (const module of item.modules) { + if (info.modules.has(module)) { + // remove module + info.modules.delete(module); + // update size + for (const key of module.getSourceTypes()) { + info.sizes[key] -= module.size(key); + } + updated = true; + } + } + if (updated) { + if (info.modules.size === 0) { + chunksInfoMap.delete(key); + continue; + } + if ( + removeMinSizeViolatingModules(info) || + !checkMinSizeReduction( + info.sizes, + info.cacheGroup.minSizeReduction, + info.chunks.size + ) + ) { + chunksInfoMap.delete(key); + continue; + } + } + } + } + } - /** - * @param {boolean=} withCreateScriptUrl use create script url for trusted types - */ - constructor(withCreateScriptUrl) { - super("load script"); - this._withCreateScriptUrl = withCreateScriptUrl; - } + logger.timeEnd("queue"); - /** - * @returns {string} runtime code - */ - generate() { - const { compilation } = this; - const { runtimeTemplate, outputOptions } = compilation; - const { - scriptType, - chunkLoadTimeout: loadTimeout, - crossOriginLoading, - uniqueName, - charset - } = outputOptions; - const fn = RuntimeGlobals.loadScript; + logger.time("maxSize"); - const { createScript } = - LoadScriptRuntimeModule.getCompilationHooks(compilation); + /** @type {Set} */ + const incorrectMinMaxSizeSet = new Set(); - const code = Template.asString([ - "script = document.createElement('script');", - scriptType ? `script.type = ${JSON.stringify(scriptType)};` : "", - charset ? "script.charset = 'utf-8';" : "", - `script.timeout = ${loadTimeout / 1000};`, - `if (${RuntimeGlobals.scriptNonce}) {`, - Template.indent( - `script.setAttribute("nonce", ${RuntimeGlobals.scriptNonce});` - ), - "}", - uniqueName - ? 'script.setAttribute("data-webpack", dataWebpackPrefix + key);' - : "", - `script.src = ${ - this._withCreateScriptUrl - ? `${RuntimeGlobals.createScriptUrl}(url)` - : "url" - };`, - crossOriginLoading - ? Template.asString([ - "if (script.src.indexOf(window.location.origin + '/') !== 0) {", - Template.indent( - `script.crossOrigin = ${JSON.stringify(crossOriginLoading)};` - ), - "}" - ]) - : "" - ]); + const { outputOptions } = compilation; - return Template.asString([ - "var inProgress = {};", - uniqueName - ? `var dataWebpackPrefix = ${JSON.stringify(uniqueName + ":")};` - : "// data-webpack is not used as build has no uniqueName", - "// loadScript function to load a script via script tag", - `${fn} = ${runtimeTemplate.basicFunction("url, done, key, chunkId", [ - "if(inProgress[url]) { inProgress[url].push(done); return; }", - "var script, needAttach;", - "if(key !== undefined) {", - Template.indent([ - 'var scripts = document.getElementsByTagName("script");', - "for(var i = 0; i < scripts.length; i++) {", - Template.indent([ - "var s = scripts[i];", - `if(s.getAttribute("src") == url${ - uniqueName - ? ' || s.getAttribute("data-webpack") == dataWebpackPrefix + key' - : "" - }) { script = s; break; }` - ]), - "}" - ]), - "}", - "if(!script) {", - Template.indent([ - "needAttach = true;", - createScript.call(code, this.chunk) - ]), - "}", - "inProgress[url] = [done];", - "var onScriptComplete = " + - runtimeTemplate.basicFunction( - "prev, event", - Template.asString([ - "// avoid mem leaks in IE.", - "script.onerror = script.onload = null;", - "clearTimeout(timeout);", - "var doneFns = inProgress[url];", - "delete inProgress[url];", - "script.parentNode && script.parentNode.removeChild(script);", - `doneFns && doneFns.forEach(${runtimeTemplate.returningFunction( - "fn(event)", - "fn" - )});`, - "if(prev) return prev(event);" - ]) - ), - ";", - `var timeout = setTimeout(onScriptComplete.bind(null, undefined, { type: 'timeout', target: script }), ${loadTimeout});`, - "script.onerror = onScriptComplete.bind(null, script.onerror);", - "script.onload = onScriptComplete.bind(null, script.onload);", - "needAttach && document.head.appendChild(script);" - ])};` - ]); + // Make sure that maxSize is fulfilled + const { fallbackCacheGroup } = this.options; + for (const chunk of Array.from(compilation.chunks)) { + const chunkConfig = maxSizeQueueMap.get(chunk); + const { + minSize, + maxAsyncSize, + maxInitialSize, + automaticNameDelimiter + } = chunkConfig || fallbackCacheGroup; + if (!chunkConfig && !fallbackCacheGroup.chunksFilter(chunk)) + continue; + /** @type {SplitChunksSizes} */ + let maxSize; + if (chunk.isOnlyInitial()) { + maxSize = maxInitialSize; + } else if (chunk.canBeInitial()) { + maxSize = combineSizes(maxAsyncSize, maxInitialSize, Math.min); + } else { + maxSize = maxAsyncSize; + } + if (Object.keys(maxSize).length === 0) { + continue; + } + for (const key of Object.keys(maxSize)) { + const maxSizeValue = maxSize[key]; + const minSizeValue = minSize[key]; + if ( + typeof minSizeValue === "number" && + minSizeValue > maxSizeValue + ) { + const keys = chunkConfig && chunkConfig.keys; + const warningKey = `${ + keys && keys.join() + } ${minSizeValue} ${maxSizeValue}`; + if (!incorrectMinMaxSizeSet.has(warningKey)) { + incorrectMinMaxSizeSet.add(warningKey); + compilation.warnings.push( + new MinMaxSizeWarning(keys, minSizeValue, maxSizeValue) + ); + } + } + } + const results = deterministicGroupingForModules({ + minSize, + maxSize: mapObject(maxSize, (value, key) => { + const minSizeValue = minSize[key]; + return typeof minSizeValue === "number" + ? Math.max(value, minSizeValue) + : value; + }), + items: chunkGraph.getChunkModulesIterable(chunk), + getKey(module) { + const cache = getKeyCache.get(module); + if (cache !== undefined) return cache; + const ident = cachedMakePathsRelative(module.identifier()); + const nameForCondition = + module.nameForCondition && module.nameForCondition(); + const name = nameForCondition + ? cachedMakePathsRelative(nameForCondition) + : ident.replace(/^.*!|\?[^?!]*$/g, ""); + const fullKey = + name + + automaticNameDelimiter + + hashFilename(ident, outputOptions); + const key = requestToId(fullKey); + getKeyCache.set(module, key); + return key; + }, + getSize(module) { + const size = Object.create(null); + for (const key of module.getSourceTypes()) { + size[key] = module.size(key); + } + return size; + } + }); + if (results.length <= 1) { + continue; + } + for (let i = 0; i < results.length; i++) { + const group = results[i]; + const key = this.options.hidePathInfo + ? hashFilename(group.key, outputOptions) + : group.key; + let name = chunk.name + ? chunk.name + automaticNameDelimiter + key + : null; + if (name && name.length > 100) { + name = + name.slice(0, 100) + + automaticNameDelimiter + + hashFilename(name, outputOptions); + } + if (i !== results.length - 1) { + const newPart = compilation.addChunk(name); + chunk.split(newPart); + newPart.chunkReason = chunk.chunkReason; + // Add all modules to the new chunk + for (const module of group.items) { + if (!module.chunkCondition(newPart, compilation)) { + continue; + } + // Add module to new chunk + chunkGraph.connectChunkAndModule(newPart, module); + // Remove module from used chunks + chunkGraph.disconnectChunkAndModule(chunk, module); + } + } else { + // change the chunk to be a part + chunk.name = name; + } + } + } + logger.timeEnd("maxSize"); + } + ); + }); } -} - -module.exports = LoadScriptRuntimeModule; +}; /***/ }), -/***/ 62962: +/***/ 60139: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; /* MIT License http://www.opensource.org/licenses/mit-license.php + Author Sean Larkin @thelarkinn */ -const RuntimeGlobals = __webpack_require__(49404); -const Template = __webpack_require__(92066); -const HelperRuntimeModule = __webpack_require__(22970); +const { formatSize } = __webpack_require__(15979); +const WebpackError = __webpack_require__(68422); -class MakeNamespaceObjectRuntimeModule extends HelperRuntimeModule { - constructor() { - super("make namespace object"); - } +/** @typedef {import("./SizeLimitsPlugin").AssetDetails} AssetDetails */ +module.exports = class AssetsOverSizeLimitWarning extends WebpackError { /** - * @returns {string} runtime code + * @param {AssetDetails[]} assetsOverSizeLimit the assets + * @param {number} assetLimit the size limit */ - generate() { - const { runtimeTemplate } = this.compilation; - const fn = RuntimeGlobals.makeNamespaceObject; - return Template.asString([ - "// define __esModule on exports", - `${fn} = ${runtimeTemplate.basicFunction("exports", [ - "if(typeof Symbol !== 'undefined' && Symbol.toStringTag) {", - Template.indent([ - "Object.defineProperty(exports, Symbol.toStringTag, { value: 'Module' });" - ]), - "}", - "Object.defineProperty(exports, '__esModule', { value: true });" - ])};` - ]); - } -} + constructor(assetsOverSizeLimit, assetLimit) { + const assetLists = assetsOverSizeLimit + .map(asset => `\n ${asset.name} (${formatSize(asset.size)})`) + .join(""); -module.exports = MakeNamespaceObjectRuntimeModule; + super(`asset size limit: The following asset(s) exceed the recommended size limit (${formatSize( + assetLimit + )}). +This can impact web performance. +Assets: ${assetLists}`); + + this.name = "AssetsOverSizeLimitWarning"; + this.assets = assetsOverSizeLimit; + } +}; /***/ }), -/***/ 92794: +/***/ 87216: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; /* MIT License http://www.opensource.org/licenses/mit-license.php + Author Sean Larkin @thelarkinn */ -const RuntimeGlobals = __webpack_require__(49404); -const RuntimeModule = __webpack_require__(61439); -const Template = __webpack_require__(92066); +const { formatSize } = __webpack_require__(15979); +const WebpackError = __webpack_require__(68422); -class OnChunksLoadedRuntimeModule extends RuntimeModule { - constructor() { - super("chunk loaded"); - } +/** @typedef {import("./SizeLimitsPlugin").EntrypointDetails} EntrypointDetails */ +module.exports = class EntrypointsOverSizeLimitWarning extends WebpackError { /** - * @returns {string} runtime code + * @param {EntrypointDetails[]} entrypoints the entrypoints + * @param {number} entrypointLimit the size limit */ - generate() { - const { compilation } = this; - const { runtimeTemplate } = compilation; - return Template.asString([ - "var deferred = [];", - `${RuntimeGlobals.onChunksLoaded} = ${runtimeTemplate.basicFunction( - "result, chunkIds, fn, priority", - [ - "if(chunkIds) {", - Template.indent([ - "priority = priority || 0;", - "for(var i = deferred.length; i > 0 && deferred[i - 1][2] > priority; i--) deferred[i] = deferred[i - 1];", - "deferred[i] = [chunkIds, fn, priority];", - "return;" - ]), - "}", - "var notFulfilled = Infinity;", - "for (var i = 0; i < deferred.length; i++) {", - Template.indent([ - runtimeTemplate.destructureArray( - ["chunkIds", "fn", "priority"], - "deferred[i]" - ), - "var fulfilled = true;", - "for (var j = 0; j < chunkIds.length; j++) {", - Template.indent([ - `if ((priority & 1 === 0 || notFulfilled >= priority) && Object.keys(${ - RuntimeGlobals.onChunksLoaded - }).every(${runtimeTemplate.returningFunction( - `${RuntimeGlobals.onChunksLoaded}[key](chunkIds[j])`, - "key" - )})) {`, - Template.indent(["chunkIds.splice(j--, 1);"]), - "} else {", - Template.indent([ - "fulfilled = false;", - "if(priority < notFulfilled) notFulfilled = priority;" - ]), - "}" - ]), - "}", - "if(fulfilled) {", - Template.indent([ - "deferred.splice(i--, 1)", - "var r = fn();", - "if (r !== undefined) result = r;" - ]), - "}" - ]), - "}", - "return result;" - ] - )};` - ]); - } -} + constructor(entrypoints, entrypointLimit) { + const entrypointList = entrypoints + .map( + entrypoint => + `\n ${entrypoint.name} (${formatSize( + entrypoint.size + )})\n${entrypoint.files.map(asset => ` ${asset}`).join("\n")}` + ) + .join(""); + super(`entrypoint size limit: The following entrypoint(s) combined asset size exceeds the recommended limit (${formatSize( + entrypointLimit + )}). This can impact web performance. +Entrypoints:${entrypointList}\n`); -module.exports = OnChunksLoadedRuntimeModule; + this.name = "EntrypointsOverSizeLimitWarning"; + this.entrypoints = entrypoints; + } +}; /***/ }), -/***/ 10569: +/***/ 80882: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; /* MIT License http://www.opensource.org/licenses/mit-license.php + Author Sean Larkin @thelarkinn */ -const RuntimeGlobals = __webpack_require__(49404); -const RuntimeModule = __webpack_require__(61439); - -class PublicPathRuntimeModule extends RuntimeModule { - constructor(publicPath) { - super("publicPath", RuntimeModule.STAGE_BASIC); - this.publicPath = publicPath; - } +const WebpackError = __webpack_require__(68422); - /** - * @returns {string} runtime code - */ - generate() { - const { compilation, publicPath } = this; +module.exports = class NoAsyncChunksWarning extends WebpackError { + constructor() { + super( + "webpack performance recommendations: \n" + + "You can limit the size of your bundles by using import() or require.ensure to lazy load some parts of your application.\n" + + "For more info visit https://webpack.js.org/guides/code-splitting/" + ); - return `${RuntimeGlobals.publicPath} = ${JSON.stringify( - compilation.getPath(publicPath || "", { - hash: compilation.hash || "XXXX" - }) - )};`; + this.name = "NoAsyncChunksWarning"; } -} - -module.exports = PublicPathRuntimeModule; +}; /***/ }), -/***/ 68642: +/***/ 64025: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; /* MIT License http://www.opensource.org/licenses/mit-license.php + Author Sean Larkin @thelarkinn */ -const RuntimeGlobals = __webpack_require__(49404); -const Template = __webpack_require__(92066); -const HelperRuntimeModule = __webpack_require__(22970); +const { find } = __webpack_require__(34715); +const AssetsOverSizeLimitWarning = __webpack_require__(60139); +const EntrypointsOverSizeLimitWarning = __webpack_require__(87216); +const NoAsyncChunksWarning = __webpack_require__(80882); -class RelativeUrlRuntimeModule extends HelperRuntimeModule { - constructor() { - super("relative url"); +/** @typedef {import("webpack-sources").Source} Source */ +/** @typedef {import("../../declarations/WebpackOptions").PerformanceOptions} PerformanceOptions */ +/** @typedef {import("../ChunkGroup")} ChunkGroup */ +/** @typedef {import("../Compiler")} Compiler */ +/** @typedef {import("../Entrypoint")} Entrypoint */ +/** @typedef {import("../WebpackError")} WebpackError */ + +/** + * @typedef {Object} AssetDetails + * @property {string} name + * @property {number} size + */ + +/** + * @typedef {Object} EntrypointDetails + * @property {string} name + * @property {number} size + * @property {string[]} files + */ + +const isOverSizeLimitSet = new WeakSet(); + +const excludeSourceMap = (name, source, info) => !info.development; + +module.exports = class SizeLimitsPlugin { + /** + * @param {PerformanceOptions} options the plugin options + */ + constructor(options) { + this.hints = options.hints; + this.maxAssetSize = options.maxAssetSize; + this.maxEntrypointSize = options.maxEntrypointSize; + this.assetFilter = options.assetFilter; } /** - * @returns {string} runtime code + * @param {ChunkGroup | Source} thing the resource to test + * @returns {boolean} true if over the limit */ - generate() { - const { runtimeTemplate } = this.compilation; - return Template.asString([ - `${RuntimeGlobals.relativeUrl} = function RelativeURL(url) {`, - Template.indent([ - 'var realUrl = new URL(url, "x:/");', - "var values = {};", - "for (var key in realUrl) values[key] = realUrl[key];", - "values.href = url;", - 'values.pathname = url.replace(/[?#].*/, "");', - 'values.origin = values.protocol = "";', - `values.toString = values.toJSON = ${runtimeTemplate.returningFunction( - "url" - )};`, - "for (var key in values) Object.defineProperty(this, key, { enumerable: true, configurable: true, value: values[key] });" - ]), - "};", - `${RuntimeGlobals.relativeUrl}.prototype = URL.prototype;` - ]); + static isOverSizeLimit(thing) { + return isOverSizeLimitSet.has(thing); } -} -module.exports = RelativeUrlRuntimeModule; + /** + * Apply the plugin + * @param {Compiler} compiler the compiler instance + * @returns {void} + */ + apply(compiler) { + const entrypointSizeLimit = this.maxEntrypointSize; + const assetSizeLimit = this.maxAssetSize; + const hints = this.hints; + const assetFilter = this.assetFilter || excludeSourceMap; + + compiler.hooks.afterEmit.tap("SizeLimitsPlugin", compilation => { + /** @type {WebpackError[]} */ + const warnings = []; + + /** + * @param {Entrypoint} entrypoint an entrypoint + * @returns {number} the size of the entrypoint + */ + const getEntrypointSize = entrypoint => { + let size = 0; + for (const file of entrypoint.getFiles()) { + const asset = compilation.getAsset(file); + if ( + asset && + assetFilter(asset.name, asset.source, asset.info) && + asset.source + ) { + size += asset.info.size || asset.source.size(); + } + } + return size; + }; + + /** @type {AssetDetails[]} */ + const assetsOverSizeLimit = []; + for (const { name, source, info } of compilation.getAssets()) { + if (!assetFilter(name, source, info) || !source) { + continue; + } + + const size = info.size || source.size(); + if (size > assetSizeLimit) { + assetsOverSizeLimit.push({ + name, + size + }); + isOverSizeLimitSet.add(source); + } + } + + const fileFilter = name => { + const asset = compilation.getAsset(name); + return asset && assetFilter(asset.name, asset.source, asset.info); + }; + + /** @type {EntrypointDetails[]} */ + const entrypointsOverLimit = []; + for (const [name, entry] of compilation.entrypoints) { + const size = getEntrypointSize(entry); + + if (size > entrypointSizeLimit) { + entrypointsOverLimit.push({ + name: name, + size: size, + files: entry.getFiles().filter(fileFilter) + }); + isOverSizeLimitSet.add(entry); + } + } + + if (hints) { + // 1. Individual Chunk: Size < 250kb + // 2. Collective Initial Chunks [entrypoint] (Each Set?): Size < 250kb + // 3. No Async Chunks + // if !1, then 2, if !2 return + if (assetsOverSizeLimit.length > 0) { + warnings.push( + new AssetsOverSizeLimitWarning(assetsOverSizeLimit, assetSizeLimit) + ); + } + if (entrypointsOverLimit.length > 0) { + warnings.push( + new EntrypointsOverSizeLimitWarning( + entrypointsOverLimit, + entrypointSizeLimit + ) + ); + } + + if (warnings.length > 0) { + const someAsyncChunk = find( + compilation.chunks, + chunk => !chunk.canBeInitial() + ); + + if (!someAsyncChunk) { + warnings.push(new NoAsyncChunksWarning()); + } + + if (hints === "error") { + compilation.errors.push(...warnings); + } else { + compilation.warnings.push(...warnings); + } + } + } + }); + } +}; /***/ }), -/***/ 90984: +/***/ 18315: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; @@ -111369,121 +110618,157 @@ module.exports = RelativeUrlRuntimeModule; -const RuntimeGlobals = __webpack_require__(49404); const RuntimeModule = __webpack_require__(61439); +const Template = __webpack_require__(92066); -class RuntimeIdRuntimeModule extends RuntimeModule { - constructor() { - super("runtimeId"); +/** @typedef {import("../RuntimeTemplate")} RuntimeTemplate */ + +class ChunkPrefetchFunctionRuntimeModule extends RuntimeModule { + /** + * @param {string} childType TODO + * @param {string} runtimeFunction TODO + * @param {string} runtimeHandlers TODO + */ + constructor(childType, runtimeFunction, runtimeHandlers) { + super(`chunk ${childType} function`); + this.childType = childType; + this.runtimeFunction = runtimeFunction; + this.runtimeHandlers = runtimeHandlers; } /** * @returns {string} runtime code */ generate() { - const { chunkGraph, chunk } = this; - const runtime = chunk.runtime; - if (typeof runtime !== "string") - throw new Error("RuntimeIdRuntimeModule must be in a single runtime"); - const id = chunkGraph.getRuntimeId(runtime); - return `${RuntimeGlobals.runtimeId} = ${JSON.stringify(id)};`; + const { runtimeFunction, runtimeHandlers } = this; + const { runtimeTemplate } = this.compilation; + return Template.asString([ + `${runtimeHandlers} = {};`, + `${runtimeFunction} = ${runtimeTemplate.basicFunction("chunkId", [ + // map is shorter than forEach + `Object.keys(${runtimeHandlers}).map(${runtimeTemplate.basicFunction( + "key", + `${runtimeHandlers}[key](chunkId);` + )});` + ])}` + ]); } } -module.exports = RuntimeIdRuntimeModule; +module.exports = ChunkPrefetchFunctionRuntimeModule; /***/ }), -/***/ 23613: +/***/ 17839: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; /* MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra */ const RuntimeGlobals = __webpack_require__(49404); -const StartupChunkDependenciesRuntimeModule = __webpack_require__(7902); -const StartupEntrypointRuntimeModule = __webpack_require__(53372); +const ChunkPrefetchFunctionRuntimeModule = __webpack_require__(18315); +const ChunkPrefetchStartupRuntimeModule = __webpack_require__(79985); +const ChunkPrefetchTriggerRuntimeModule = __webpack_require__(32123); +const ChunkPreloadTriggerRuntimeModule = __webpack_require__(58929); /** @typedef {import("../Compiler")} Compiler */ -class StartupChunkDependenciesPlugin { - constructor(options) { - this.chunkLoading = options.chunkLoading; - this.asyncChunkLoading = - typeof options.asyncChunkLoading === "boolean" - ? options.asyncChunkLoading - : true; - } - +class ChunkPrefetchPreloadPlugin { /** - * Apply the plugin - * @param {Compiler} compiler the compiler instance + * @param {Compiler} compiler the compiler * @returns {void} */ apply(compiler) { - compiler.hooks.thisCompilation.tap( - "StartupChunkDependenciesPlugin", + compiler.hooks.compilation.tap( + "ChunkPrefetchPreloadPlugin", compilation => { - const globalChunkLoading = compilation.outputOptions.chunkLoading; - const isEnabledForChunk = chunk => { - const options = chunk.getEntryOptions(); - const chunkLoading = - options && options.chunkLoading !== undefined - ? options.chunkLoading - : globalChunkLoading; - return chunkLoading === this.chunkLoading; - }; + compilation.hooks.additionalChunkRuntimeRequirements.tap( + "ChunkPrefetchPreloadPlugin", + (chunk, set, { chunkGraph }) => { + if (chunkGraph.getNumberOfEntryModules(chunk) === 0) return; + const startupChildChunks = chunk.getChildrenOfTypeInOrder( + chunkGraph, + "prefetchOrder" + ); + if (startupChildChunks) { + set.add(RuntimeGlobals.prefetchChunk); + set.add(RuntimeGlobals.onChunksLoaded); + compilation.addRuntimeModule( + chunk, + new ChunkPrefetchStartupRuntimeModule(startupChildChunks) + ); + } + } + ); compilation.hooks.additionalTreeRuntimeRequirements.tap( - "StartupChunkDependenciesPlugin", + "ChunkPrefetchPreloadPlugin", (chunk, set, { chunkGraph }) => { - if (!isEnabledForChunk(chunk)) return; - if (chunkGraph.hasChunkEntryDependentChunks(chunk)) { - set.add(RuntimeGlobals.startup); - set.add(RuntimeGlobals.ensureChunk); - set.add(RuntimeGlobals.ensureChunkIncludeEntries); + const chunkMap = chunk.getChildIdsByOrdersMap(chunkGraph, false); + + if (chunkMap.prefetch) { + set.add(RuntimeGlobals.prefetchChunk); compilation.addRuntimeModule( chunk, - new StartupChunkDependenciesRuntimeModule( - this.asyncChunkLoading - ) + new ChunkPrefetchTriggerRuntimeModule(chunkMap.prefetch) + ); + } + if (chunkMap.preload) { + set.add(RuntimeGlobals.preloadChunk); + compilation.addRuntimeModule( + chunk, + new ChunkPreloadTriggerRuntimeModule(chunkMap.preload) ); } } ); compilation.hooks.runtimeRequirementInTree - .for(RuntimeGlobals.startupEntrypoint) - .tap("StartupChunkDependenciesPlugin", (chunk, set) => { - if (!isEnabledForChunk(chunk)) return; - set.add(RuntimeGlobals.require); - set.add(RuntimeGlobals.ensureChunk); - set.add(RuntimeGlobals.ensureChunkIncludeEntries); + .for(RuntimeGlobals.prefetchChunk) + .tap("ChunkPrefetchPreloadPlugin", (chunk, set) => { + compilation.addRuntimeModule( + chunk, + new ChunkPrefetchFunctionRuntimeModule( + "prefetch", + RuntimeGlobals.prefetchChunk, + RuntimeGlobals.prefetchChunkHandlers + ) + ); + set.add(RuntimeGlobals.prefetchChunkHandlers); + }); + compilation.hooks.runtimeRequirementInTree + .for(RuntimeGlobals.preloadChunk) + .tap("ChunkPrefetchPreloadPlugin", (chunk, set) => { compilation.addRuntimeModule( chunk, - new StartupEntrypointRuntimeModule(this.asyncChunkLoading) + new ChunkPrefetchFunctionRuntimeModule( + "preload", + RuntimeGlobals.preloadChunk, + RuntimeGlobals.preloadChunkHandlers + ) ); + set.add(RuntimeGlobals.preloadChunkHandlers); }); } ); } } -module.exports = StartupChunkDependenciesPlugin; +module.exports = ChunkPrefetchPreloadPlugin; /***/ }), -/***/ 7902: +/***/ 79985: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; /* MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra */ @@ -111492,67 +110777,53 @@ const RuntimeGlobals = __webpack_require__(49404); const RuntimeModule = __webpack_require__(61439); const Template = __webpack_require__(92066); -class StartupChunkDependenciesRuntimeModule extends RuntimeModule { - constructor(asyncChunkLoading) { - super("startup chunk dependencies", RuntimeModule.STAGE_TRIGGER); - this.asyncChunkLoading = asyncChunkLoading; +/** @typedef {import("../Chunk")} Chunk */ +/** @typedef {import("../RuntimeTemplate")} RuntimeTemplate */ + +class ChunkPrefetchStartupRuntimeModule extends RuntimeModule { + /** + * @param {{ onChunks: Chunk[], chunks: Set }[]} startupChunks chunk ids to trigger when chunks are loaded + */ + constructor(startupChunks) { + super("startup prefetch", RuntimeModule.STAGE_TRIGGER); + this.startupChunks = startupChunks; } /** * @returns {string} runtime code */ generate() { - const { chunkGraph, chunk, compilation } = this; - const { runtimeTemplate } = compilation; - const chunkIds = Array.from( - chunkGraph.getChunkEntryDependentChunksIterable(chunk) - ).map(chunk => { - return chunk.id; - }); - return Template.asString([ - `var next = ${RuntimeGlobals.startup};`, - `${RuntimeGlobals.startup} = ${runtimeTemplate.basicFunction( - "", - !this.asyncChunkLoading - ? chunkIds - .map( - id => `${RuntimeGlobals.ensureChunk}(${JSON.stringify(id)});` - ) - .concat("return next();") - : chunkIds.length === 1 - ? `return ${RuntimeGlobals.ensureChunk}(${JSON.stringify( - chunkIds[0] - )}).then(next);` - : chunkIds.length > 2 - ? [ - // using map is shorter for 3 or more chunks - `return Promise.all(${JSON.stringify(chunkIds)}.map(${ - RuntimeGlobals.ensureChunk - }, __webpack_require__)).then(next);` - ] - : [ - // calling ensureChunk directly is shorter for 0 - 2 chunks - "return Promise.all([", - Template.indent( - chunkIds - .map( - id => `${RuntimeGlobals.ensureChunk}(${JSON.stringify(id)})` - ) - .join(",\n") - ), - "]).then(next);" - ] - )};` - ]); + const { startupChunks, chunk } = this; + const { runtimeTemplate } = this.compilation; + return Template.asString( + startupChunks.map( + ({ onChunks, chunks }) => + `${RuntimeGlobals.onChunksLoaded}(0, ${JSON.stringify( + // This need to include itself to delay execution after this chunk has been fully loaded + onChunks.filter(c => c === chunk).map(c => c.id) + )}, ${runtimeTemplate.basicFunction( + "", + chunks.size < 3 + ? Array.from( + chunks, + c => + `${RuntimeGlobals.prefetchChunk}(${JSON.stringify(c.id)});` + ) + : `${JSON.stringify(Array.from(chunks, c => c.id))}.map(${ + RuntimeGlobals.prefetchChunk + });` + )}, 5);` + ) + ); } } -module.exports = StartupChunkDependenciesRuntimeModule; +module.exports = ChunkPrefetchStartupRuntimeModule; /***/ }), -/***/ 53372: +/***/ 32123: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; @@ -111564,53 +110835,52 @@ module.exports = StartupChunkDependenciesRuntimeModule; const RuntimeGlobals = __webpack_require__(49404); const RuntimeModule = __webpack_require__(61439); +const Template = __webpack_require__(92066); -/** @typedef {import("../MainTemplate")} MainTemplate */ +/** @typedef {import("../RuntimeTemplate")} RuntimeTemplate */ -class StartupEntrypointRuntimeModule extends RuntimeModule { - constructor(asyncChunkLoading) { - super("startup entrypoint"); - this.asyncChunkLoading = asyncChunkLoading; +class ChunkPrefetchTriggerRuntimeModule extends RuntimeModule { + /** + * @param {Record} chunkMap map from chunk to + */ + constructor(chunkMap) { + super(`chunk prefetch trigger`, RuntimeModule.STAGE_TRIGGER); + this.chunkMap = chunkMap; } /** * @returns {string} runtime code */ generate() { - const { compilation } = this; - const { runtimeTemplate } = compilation; - return `${ - RuntimeGlobals.startupEntrypoint - } = ${runtimeTemplate.basicFunction("result, chunkIds, fn", [ - "// arguments: chunkIds, moduleId are deprecated", - "var moduleId = chunkIds;", - `if(!fn) chunkIds = result, fn = ${runtimeTemplate.returningFunction( - `__webpack_require__(${RuntimeGlobals.entryModuleId} = moduleId)` - )};`, - ...(this.asyncChunkLoading - ? [ - `return Promise.all(chunkIds.map(${ - RuntimeGlobals.ensureChunk - }, __webpack_require__)).then(${runtimeTemplate.basicFunction("", [ - "var r = fn();", - "return r === undefined ? result : r;" - ])})` - ] - : [ - `chunkIds.map(${RuntimeGlobals.ensureChunk}, __webpack_require__)`, - "var r = fn();", - "return r === undefined ? result : r;" - ]) - ])}`; + const { chunkMap } = this; + const { runtimeTemplate } = this.compilation; + const body = [ + "var chunks = chunkToChildrenMap[chunkId];", + `Array.isArray(chunks) && chunks.map(${RuntimeGlobals.prefetchChunk});` + ]; + return Template.asString([ + Template.asString([ + `var chunkToChildrenMap = ${JSON.stringify(chunkMap, null, "\t")};`, + `${ + RuntimeGlobals.ensureChunkHandlers + }.prefetch = ${runtimeTemplate.expressionFunction( + `Promise.all(promises).then(${runtimeTemplate.basicFunction( + "", + body + )})`, + "chunkId, promises" + )};` + ]) + ]); } } -module.exports = StartupEntrypointRuntimeModule; +module.exports = ChunkPrefetchTriggerRuntimeModule; /***/ }), -/***/ 33248: +/***/ 58929: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; @@ -111622,29 +110892,47 @@ module.exports = StartupEntrypointRuntimeModule; const RuntimeGlobals = __webpack_require__(49404); const RuntimeModule = __webpack_require__(61439); +const Template = __webpack_require__(92066); -/** @typedef {import("../Compilation")} Compilation */ +/** @typedef {import("../RuntimeTemplate")} RuntimeTemplate */ -class SystemContextRuntimeModule extends RuntimeModule { - constructor() { - super("__system_context__"); +class ChunkPreloadTriggerRuntimeModule extends RuntimeModule { + /** + * @param {Record} chunkMap map from chunk to chunks + */ + constructor(chunkMap) { + super(`chunk preload trigger`, RuntimeModule.STAGE_TRIGGER); + this.chunkMap = chunkMap; } /** * @returns {string} runtime code */ generate() { - return `${RuntimeGlobals.systemContext} = __system_context__;`; + const { chunkMap } = this; + const { runtimeTemplate } = this.compilation; + const body = [ + "var chunks = chunkToChildrenMap[chunkId];", + `Array.isArray(chunks) && chunks.map(${RuntimeGlobals.preloadChunk});` + ]; + return Template.asString([ + Template.asString([ + `var chunkToChildrenMap = ${JSON.stringify(chunkMap, null, "\t")};`, + `${ + RuntimeGlobals.ensureChunkHandlers + }.preload = ${runtimeTemplate.basicFunction("chunkId", body)};` + ]) + ]); } } -module.exports = SystemContextRuntimeModule; +module.exports = ChunkPreloadTriggerRuntimeModule; /***/ }), -/***/ 71276: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { +/***/ 70119: +/***/ (function(module) { "use strict"; /* @@ -111654,61 +110942,44 @@ module.exports = SystemContextRuntimeModule; -const NormalModule = __webpack_require__(11026); - -/** @typedef {import("../Compiler")} Compiler */ - -// data URL scheme: "data:text/javascript;charset=utf-8;base64,some-string" -// http://www.ietf.org/rfc/rfc2397.txt -const URIRegEx = /^data:([^;,]+)?((?:;[^;,]+)*?)(?:;(base64))?,(.*)$/i; - -const decodeDataURI = uri => { - const match = URIRegEx.exec(uri); - if (!match) return null; +/** @typedef {import("./RuleSetCompiler")} RuleSetCompiler */ - const isBase64 = match[3]; - const body = match[4]; - return isBase64 - ? Buffer.from(body, "base64") - : Buffer.from(decodeURIComponent(body), "ascii"); -}; +class BasicEffectRulePlugin { + constructor(ruleProperty, effectType) { + this.ruleProperty = ruleProperty; + this.effectType = effectType || ruleProperty; + } -class DataUriPlugin { /** - * Apply the plugin - * @param {Compiler} compiler the compiler instance + * @param {RuleSetCompiler} ruleSetCompiler the rule set compiler * @returns {void} */ - apply(compiler) { - compiler.hooks.compilation.tap( - "DataUriPlugin", - (compilation, { normalModuleFactory }) => { - normalModuleFactory.hooks.resolveForScheme - .for("data") - .tap("DataUriPlugin", resourceData => { - const match = URIRegEx.exec(resourceData.resource); - if (match) { - resourceData.data.mimetype = match[1] || ""; - resourceData.data.parameters = match[2] || ""; - resourceData.data.encoding = match[3] || false; - resourceData.data.encodedContent = match[4] || ""; - } + apply(ruleSetCompiler) { + ruleSetCompiler.hooks.rule.tap( + "BasicEffectRulePlugin", + (path, rule, unhandledProperties, result, references) => { + if (unhandledProperties.has(this.ruleProperty)) { + unhandledProperties.delete(this.ruleProperty); + + const value = rule[this.ruleProperty]; + + result.effects.push({ + type: this.effectType, + value }); - NormalModule.getCompilationHooks(compilation) - .readResourceForScheme.for("data") - .tap("DataUriPlugin", resource => decodeDataURI(resource)); + } } ); } } -module.exports = DataUriPlugin; +module.exports = BasicEffectRulePlugin; /***/ }), -/***/ 75275: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { +/***/ 99083: +/***/ (function(module) { "use strict"; /* @@ -111718,54 +110989,52 @@ module.exports = DataUriPlugin; -const { URL, fileURLToPath } = __webpack_require__(78835); -const { NormalModule } = __webpack_require__(48169); +/** @typedef {import("./RuleSetCompiler")} RuleSetCompiler */ +/** @typedef {import("./RuleSetCompiler").RuleCondition} RuleCondition */ -/** @typedef {import("../Compiler")} Compiler */ +class BasicMatcherRulePlugin { + constructor(ruleProperty, dataProperty, invert) { + this.ruleProperty = ruleProperty; + this.dataProperty = dataProperty || ruleProperty; + this.invert = invert || false; + } -class FileUriPlugin { /** - * Apply the plugin - * @param {Compiler} compiler the compiler instance + * @param {RuleSetCompiler} ruleSetCompiler the rule set compiler * @returns {void} */ - apply(compiler) { - compiler.hooks.compilation.tap( - "FileUriPlugin", - (compilation, { normalModuleFactory }) => { - normalModuleFactory.hooks.resolveForScheme - .for("file") - .tap("FileUriPlugin", resourceData => { - const url = new URL(resourceData.resource); - const path = fileURLToPath(url); - const query = url.search; - const fragment = url.hash; - resourceData.path = path; - resourceData.query = query; - resourceData.fragment = fragment; - resourceData.resource = path + query + fragment; - return true; - }); - const hooks = NormalModule.getCompilationHooks(compilation); - hooks.readResource - .for(undefined) - .tapAsync("FileUriPlugin", (loaderContext, callback) => { - const { resourcePath } = loaderContext; - loaderContext.addDependency(resourcePath); - loaderContext.fs.readFile(resourcePath, callback); + apply(ruleSetCompiler) { + ruleSetCompiler.hooks.rule.tap( + "BasicMatcherRulePlugin", + (path, rule, unhandledProperties, result) => { + if (unhandledProperties.has(this.ruleProperty)) { + unhandledProperties.delete(this.ruleProperty); + const value = rule[this.ruleProperty]; + const condition = ruleSetCompiler.compileCondition( + `${path}.${this.ruleProperty}`, + value + ); + const fn = condition.fn; + result.conditions.push({ + property: this.dataProperty, + matchWhenEmpty: this.invert + ? !condition.matchWhenEmpty + : condition.matchWhenEmpty, + fn: this.invert ? v => !fn(v) : fn }); + } } ); } } -module.exports = FileUriPlugin; +module.exports = BasicMatcherRulePlugin; /***/ }), -/***/ 34747: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { +/***/ 61166: +/***/ (function(module) { "use strict"; /* @@ -111775,1061 +111044,872 @@ module.exports = FileUriPlugin; -const { extname, basename } = __webpack_require__(85622); -const { URL } = __webpack_require__(78835); -const { createGunzip, createBrotliDecompress, createInflate } = __webpack_require__(78761); -const NormalModule = __webpack_require__(11026); -const createSchemaValidation = __webpack_require__(77695); -const createHash = __webpack_require__(24123); -const { mkdirp, dirname, join } = __webpack_require__(93204); -const memoize = __webpack_require__(84297); - -/** @typedef {import("../../declarations/plugins/schemes/HttpUriPlugin").HttpUriPluginOptions} HttpUriPluginOptions */ -/** @typedef {import("../Compiler")} Compiler */ - -const getHttp = memoize(() => __webpack_require__(98605)); -const getHttps = memoize(() => __webpack_require__(57211)); - -/** @type {(() => void)[] | undefined} */ -let inProgressWrite = undefined; +/** @typedef {import("./RuleSetCompiler")} RuleSetCompiler */ +/** @typedef {import("./RuleSetCompiler").RuleCondition} RuleCondition */ -const validate = createSchemaValidation( - __webpack_require__(87387), - () => __webpack_require__(75110), - { - name: "Http Uri Plugin", - baseDataPath: "options" +class ObjectMatcherRulePlugin { + constructor(ruleProperty, dataProperty) { + this.ruleProperty = ruleProperty; + this.dataProperty = dataProperty || ruleProperty; } -); - -const toSafePath = str => - str - .replace(/^[^a-zA-Z0-9]+|[^a-zA-Z0-9]+$/g, "") - .replace(/[^a-zA-Z0-9._-]+/g, "_"); - -const computeIntegrity = content => { - const hash = createHash("sha512"); - hash.update(content); - const integrity = "sha512-" + hash.digest("base64"); - return integrity; -}; - -const verifyIntegrity = (content, integrity) => { - if (integrity === "ignore") return true; - return computeIntegrity(content) === integrity; -}; -/** - * @param {string} str input - * @returns {Record} parsed - */ -const parseKeyValuePairs = str => { - /** @type {Record} */ - const result = {}; - for (const item of str.split(",")) { - const i = item.indexOf("="); - if (i >= 0) { - const key = item.slice(0, i).trim(); - const value = item.slice(i + 1).trim(); - result[key] = value; - } else { - const key = item.trim(); - if (!key) continue; - result[key] = key; - } + /** + * @param {RuleSetCompiler} ruleSetCompiler the rule set compiler + * @returns {void} + */ + apply(ruleSetCompiler) { + const { ruleProperty, dataProperty } = this; + ruleSetCompiler.hooks.rule.tap( + "ObjectMatcherRulePlugin", + (path, rule, unhandledProperties, result) => { + if (unhandledProperties.has(ruleProperty)) { + unhandledProperties.delete(ruleProperty); + const value = rule[ruleProperty]; + for (const property of Object.keys(value)) { + const nestedDataProperties = property.split("."); + const condition = ruleSetCompiler.compileCondition( + `${path}.${ruleProperty}.${property}`, + value[property] + ); + result.conditions.push({ + property: [dataProperty, ...nestedDataProperties], + matchWhenEmpty: condition.matchWhenEmpty, + fn: condition.fn + }); + } + } + } + ); } - return result; -}; +} -const parseCacheControl = (cacheControl, requestTime) => { - // When false resource is not stored in cache - let storeCache = true; - // When false resource is not stored in lockfile cache - let storeLock = true; - // Resource is only revalidated, after that timestamp and when upgrade is chosen - let validUntil = 0; - if (cacheControl) { - const parsed = parseKeyValuePairs(cacheControl); - if (parsed["no-cache"]) storeCache = storeLock = false; - if (parsed["max-age"] && !isNaN(+parsed["max-age"])) { - validUntil = requestTime + +parsed["max-age"] * 1000; - } - if (parsed["must-revalidate"]) validUntil = 0; - } - return { - storeLock, - storeCache, - validUntil - }; -}; +module.exports = ObjectMatcherRulePlugin; -/** - * @typedef {Object} LockfileEntry - * @property {string} resolved - * @property {string} integrity - * @property {string} contentType - */ -const areLockfileEntriesEqual = (a, b) => { - return ( - a.resolved === b.resolved && - a.integrity === b.integrity && - a.contentType === b.contentType - ); -}; +/***/ }), -const entryToString = entry => { - return `resolved: ${entry.resolved}, integrity: ${entry.integrity}, contentType: ${entry.contentType}`; -}; +/***/ 23246: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { -class Lockfile { - constructor() { - this.version = 1; - /** @type {Map} */ - this.entries = new Map(); - } +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ - static parse(content) { - // TODO handle merge conflicts - const data = JSON.parse(content); - if (data.version !== 1) - throw new Error(`Unsupported lockfile version ${data.version}`); - const lockfile = new Lockfile(); - for (const key of Object.keys(data)) { - if (key === "version") continue; - const entry = data[key]; - lockfile.entries.set( - key, - typeof entry === "string" - ? entry - : { - resolved: key, - ...entry - } - ); - } - return lockfile; - } - toString() { - let str = "{\n"; - const entries = Array.from(this.entries).sort(([a], [b]) => - a < b ? -1 : 1 - ); - for (const [key, entry] of entries) { - if (typeof entry === "string") { - str += ` ${JSON.stringify(key)}: ${JSON.stringify(entry)},\n`; - } else { - str += ` ${JSON.stringify(key)}: { `; - if (entry.resolved !== key) - str += `"resolved": ${JSON.stringify(entry.resolved)}, `; - str += `"integrity": ${JSON.stringify( - entry.integrity - )}, "contentType": ${JSON.stringify(entry.contentType)} },\n`; - } - } - str += ` "version": ${this.version}\n}\n`; - return str; - } -} + +const { SyncHook } = __webpack_require__(34718); /** - * @template R - * @param {function(function(Error=, R=): void): void} fn function - * @returns {function(function(Error=, R=): void): void} cached function + * @typedef {Object} RuleCondition + * @property {string | string[]} property + * @property {boolean} matchWhenEmpty + * @property {function(string): boolean} fn */ -const cachedWithoutKey = fn => { - let inFlight = false; - /** @type {Error | undefined} */ - let cachedError = undefined; - /** @type {R | undefined} */ - let cachedResult = undefined; - /** @type {(function(Error=, R=): void)[] | undefined} */ - let cachedCallbacks = undefined; - return callback => { - if (inFlight) { - if (cachedResult !== undefined) return callback(null, cachedResult); - if (cachedError !== undefined) return callback(cachedError); - if (cachedCallbacks === undefined) cachedCallbacks = [callback]; - else cachedCallbacks.push(callback); - return; - } - inFlight = true; - fn((err, result) => { - if (err) cachedError = err; - else cachedResult = result; - const callbacks = cachedCallbacks; - cachedCallbacks = undefined; - callback(err, result); - if (callbacks !== undefined) for (const cb of callbacks) cb(err, result); - }); - }; -}; /** - * @template T - * @template R - * @param {function(T, function(Error=, R=): void): void} fn function - * @param {function(T, function(Error=, R=): void): void=} forceFn function for the second try - * @returns {(function(T, function(Error=, R=): void): void) & { force: function(T, function(Error=, R=): void): void }} cached function + * @typedef {Object} Condition + * @property {boolean} matchWhenEmpty + * @property {function(string): boolean} fn */ -const cachedWithKey = (fn, forceFn = fn) => { - /** @typedef {{ result?: R, error?: Error, callbacks?: (function(Error=, R=): void)[], force?: true }} CacheEntry */ - /** @type {Map} */ - const cache = new Map(); - const resultFn = (arg, callback) => { - const cacheEntry = cache.get(arg); - if (cacheEntry !== undefined) { - if (cacheEntry.result !== undefined) - return callback(null, cacheEntry.result); - if (cacheEntry.error !== undefined) return callback(cacheEntry.error); - if (cacheEntry.callbacks === undefined) cacheEntry.callbacks = [callback]; - else cacheEntry.callbacks.push(callback); - return; - } - /** @type {CacheEntry} */ - const newCacheEntry = { - result: undefined, - error: undefined, - callbacks: undefined - }; - cache.set(arg, newCacheEntry); - fn(arg, (err, result) => { - if (err) newCacheEntry.error = err; - else newCacheEntry.result = result; - const callbacks = newCacheEntry.callbacks; - newCacheEntry.callbacks = undefined; - callback(err, result); - if (callbacks !== undefined) for (const cb of callbacks) cb(err, result); + +/** + * @typedef {Object} CompiledRule + * @property {RuleCondition[]} conditions + * @property {(Effect|function(object): Effect[])[]} effects + * @property {CompiledRule[]=} rules + * @property {CompiledRule[]=} oneOf + */ + +/** + * @typedef {Object} Effect + * @property {string} type + * @property {any} value + */ + +/** + * @typedef {Object} RuleSet + * @property {Map} references map of references in the rule set (may grow over time) + * @property {function(object): Effect[]} exec execute the rule set + */ + +class RuleSetCompiler { + constructor(plugins) { + this.hooks = Object.freeze({ + /** @type {SyncHook<[string, object, Set, CompiledRule, Map]>} */ + rule: new SyncHook([ + "path", + "rule", + "unhandledProperties", + "compiledRule", + "references" + ]) }); - }; - resultFn.force = (arg, callback) => { - const cacheEntry = cache.get(arg); - if (cacheEntry !== undefined && cacheEntry.force) { - if (cacheEntry.result !== undefined) - return callback(null, cacheEntry.result); - if (cacheEntry.error !== undefined) return callback(cacheEntry.error); - if (cacheEntry.callbacks === undefined) cacheEntry.callbacks = [callback]; - else cacheEntry.callbacks.push(callback); - return; + if (plugins) { + for (const plugin of plugins) { + plugin.apply(this); + } } - /** @type {CacheEntry} */ - const newCacheEntry = { - result: undefined, - error: undefined, - callbacks: undefined, - force: true - }; - cache.set(arg, newCacheEntry); - forceFn(arg, (err, result) => { - if (err) newCacheEntry.error = err; - else newCacheEntry.result = result; - const callbacks = newCacheEntry.callbacks; - newCacheEntry.callbacks = undefined; - callback(err, result); - if (callbacks !== undefined) for (const cb of callbacks) cb(err, result); - }); - }; - return resultFn; -}; - -class HttpUriPlugin { - /** - * @param {HttpUriPluginOptions} options options - */ - constructor(options) { - validate(options); - this._lockfileLocation = options.lockfileLocation; - this._cacheLocation = options.cacheLocation; - this._upgrade = options.upgrade; - this._frozen = options.frozen; - this._allowedUris = options.allowedUris; } /** - * Apply the plugin - * @param {Compiler} compiler the compiler instance - * @returns {void} + * @param {object[]} ruleSet raw user provided rules + * @returns {RuleSet} compiled RuleSet */ - apply(compiler) { - const schemes = [ - { - scheme: "http", - fetch: (url, options, callback) => getHttp().get(url, options, callback) - }, - { - scheme: "https", - fetch: (url, options, callback) => - getHttps().get(url, options, callback) - } - ]; - let lockfileCache; - compiler.hooks.compilation.tap( - "HttpUriPlugin", - (compilation, { normalModuleFactory }) => { - const intermediateFs = compiler.intermediateFileSystem; - const fs = compilation.inputFileSystem; - const cache = compilation.getCache("webpack.HttpUriPlugin"); - const logger = compilation.getLogger("webpack.HttpUriPlugin"); - const lockfileLocation = - this._lockfileLocation || - join( - intermediateFs, - compiler.context, - compiler.name - ? `${toSafePath(compiler.name)}.webpack.lock` - : "webpack.lock" - ); - const cacheLocation = - this._cacheLocation !== undefined - ? this._cacheLocation - : lockfileLocation + ".data"; - const upgrade = this._upgrade || false; - const frozen = this._frozen || false; - const hashFunction = "sha512"; - const hashDigest = "hex"; - const hashDigestLength = 20; - const allowedUris = this._allowedUris; - - let warnedAboutEol = false; - - const cacheKeyCache = new Map(); - /** - * @param {string} url the url - * @returns {string} the key - */ - const getCacheKey = url => { - const cachedResult = cacheKeyCache.get(url); - if (cachedResult !== undefined) return cachedResult; - const result = _getCacheKey(url); - cacheKeyCache.set(url, result); - return result; - }; - - /** - * @param {string} url the url - * @returns {string} the key - */ - const _getCacheKey = url => { - const parsedUrl = new URL(url); - const folder = toSafePath(parsedUrl.origin); - const name = toSafePath(parsedUrl.pathname); - const query = toSafePath(parsedUrl.search); - let ext = extname(name); - if (ext.length > 20) ext = ""; - const basename = ext ? name.slice(0, -ext.length) : name; - const hash = createHash(hashFunction); - hash.update(url); - const digest = hash.digest(hashDigest).slice(0, hashDigestLength); - return `${folder.slice(-50)}/${`${basename}${ - query ? `_${query}` : "" - }`.slice(0, 150)}_${digest}${ext}`; - }; + compile(ruleSet) { + const refs = new Map(); + const rules = this.compileRules("ruleSet", ruleSet, refs); - const getLockfile = cachedWithoutKey( - /** - * @param {function(Error=, Lockfile=): void} callback callback - * @returns {void} - */ - callback => { - const readLockfile = () => { - intermediateFs.readFile(lockfileLocation, (err, buffer) => { - if (err && err.code !== "ENOENT") { - compilation.missingDependencies.add(lockfileLocation); - return callback(err); - } - compilation.fileDependencies.add(lockfileLocation); - compilation.fileSystemInfo.createSnapshot( - compiler.fsStartTime, - buffer ? [lockfileLocation] : [], - [], - buffer ? [] : [lockfileLocation], - { timestamp: true }, - (err, snapshot) => { - if (err) return callback(err); - const lockfile = buffer - ? Lockfile.parse(buffer.toString("utf-8")) - : new Lockfile(); - lockfileCache = { - lockfile, - snapshot - }; - callback(null, lockfile); - } - ); - }); - }; - if (lockfileCache) { - compilation.fileSystemInfo.checkSnapshotValid( - lockfileCache.snapshot, - (err, valid) => { - if (err) return callback(err); - if (!valid) return readLockfile(); - callback(null, lockfileCache.lockfile); - } - ); + /** + * @param {object} data data passed in + * @param {CompiledRule} rule the compiled rule + * @param {Effect[]} effects an array where effects are pushed to + * @returns {boolean} true, if the rule has matched + */ + const execRule = (data, rule, effects) => { + for (const condition of rule.conditions) { + const p = condition.property; + if (Array.isArray(p)) { + let current = data; + for (const subProperty of p) { + if ( + current && + typeof current === "object" && + Object.prototype.hasOwnProperty.call(current, subProperty) + ) { + current = current[subProperty]; } else { - readLockfile(); + current = undefined; + break; } } - ); - - /** @type {Map | undefined} */ - let lockfileUpdates = undefined; - const storeLockEntry = (lockfile, url, entry) => { - const oldEntry = lockfile.entries.get(url); - if (lockfileUpdates === undefined) lockfileUpdates = new Map(); - lockfileUpdates.set(url, entry); - lockfile.entries.set(url, entry); - if (!oldEntry) { - logger.log(`${url} added to lockfile`); - } else if (typeof oldEntry === "string") { - if (typeof entry === "string") { - logger.log(`${url} updated in lockfile: ${oldEntry} -> ${entry}`); - } else { - logger.log( - `${url} updated in lockfile: ${oldEntry} -> ${entry.resolved}` - ); - } - } else if (typeof entry === "string") { - logger.log( - `${url} updated in lockfile: ${oldEntry.resolved} -> ${entry}` - ); - } else if (oldEntry.resolved !== entry.resolved) { - logger.log( - `${url} updated in lockfile: ${oldEntry.resolved} -> ${entry.resolved}` - ); - } else if (oldEntry.integrity !== entry.integrity) { - logger.log(`${url} updated in lockfile: content changed`); - } else if (oldEntry.contentType !== entry.contentType) { - logger.log( - `${url} updated in lockfile: ${oldEntry.contentType} -> ${entry.contentType}` - ); - } else { - logger.log(`${url} updated in lockfile`); + if (current !== undefined) { + if (!condition.fn(current)) return false; + continue; } - }; - - const storeResult = (lockfile, url, result, callback) => { - if (result.storeLock) { - storeLockEntry(lockfile, url, result.entry); - if (!cacheLocation || !result.content) - return callback(null, result); - const key = getCacheKey(result.entry.resolved); - const filePath = join(intermediateFs, cacheLocation, key); - mkdirp(intermediateFs, dirname(intermediateFs, filePath), err => { - if (err) return callback(err); - intermediateFs.writeFile(filePath, result.content, err => { - if (err) return callback(err); - callback(null, result); - }); - }); - } else { - storeLockEntry(lockfile, url, "no-cache"); - callback(null, result); + } else if (p in data) { + const value = data[p]; + if (value !== undefined) { + if (!condition.fn(value)) return false; + continue; } - }; - - for (const { scheme, fetch } of schemes) { - /** - * - * @param {string} url URL - * @param {string} integrity integrity - * @param {function(Error=, { entry: LockfileEntry, content: Buffer, storeLock: boolean }=): void} callback callback - */ - const resolveContent = (url, integrity, callback) => { - const handleResult = (err, result) => { - if (err) return callback(err); - if ("location" in result) { - return resolveContent( - result.location, - integrity, - (err, innerResult) => { - if (err) return callback(err); - callback(null, { - entry: innerResult.entry, - content: innerResult.content, - storeLock: innerResult.storeLock && result.storeLock - }); - } - ); - } else { - if ( - !result.fresh && - integrity && - result.entry.integrity !== integrity && - !verifyIntegrity(result.content, integrity) - ) { - return fetchContent.force(url, handleResult); - } - return callback(null, { - entry: result.entry, - content: result.content, - storeLock: result.storeLock - }); - } - }; - fetchContent(url, handleResult); - }; - - /** @typedef {{ storeCache: boolean, storeLock: boolean, validUntil: number, etag: string | undefined, fresh: boolean }} FetchResultMeta */ - /** @typedef {FetchResultMeta & { location: string }} RedirectFetchResult */ - /** @typedef {FetchResultMeta & { entry: LockfileEntry, content: Buffer }} ContentFetchResult */ - /** @typedef {RedirectFetchResult | ContentFetchResult} FetchResult */ - - /** - * @param {string} url URL - * @param {FetchResult} cachedResult result from cache - * @param {function(Error=, FetchResult=): void} callback callback - * @returns {void} - */ - const fetchContentRaw = (url, cachedResult, callback) => { - const requestTime = Date.now(); - fetch( - new URL(url), - { - headers: { - "accept-encoding": "gzip, deflate, br", - "user-agent": "webpack", - "if-none-match": cachedResult - ? cachedResult.etag || null - : null - } - }, - res => { - const etag = res.headers["etag"]; - const location = res.headers["location"]; - const cacheControl = res.headers["cache-control"]; - const { storeLock, storeCache, validUntil } = parseCacheControl( - cacheControl, - requestTime - ); - /** - * @param {Partial> & (Pick | Pick)} partialResult result - * @returns {void} - */ - const finishWith = partialResult => { - if ("location" in partialResult) { - logger.debug( - `GET ${url} [${res.statusCode}] -> ${partialResult.location}` - ); - } else { - logger.debug( - `GET ${url} [${res.statusCode}] ${Math.ceil( - partialResult.content.length / 1024 - )} kB${!storeLock ? " no-cache" : ""}` - ); - } - const result = { - ...partialResult, - fresh: true, - storeLock, - storeCache, - validUntil, - etag - }; - if (!storeCache) { - logger.log( - `${url} can't be stored in cache, due to Cache-Control header: ${cacheControl}` - ); - return callback(null, result); - } - cache.store( - url, - null, - { - ...result, - fresh: false - }, - err => { - if (err) { - logger.warn( - `${url} can't be stored in cache: ${err.message}` - ); - logger.debug(err.stack); - } - callback(null, result); - } - ); - }; - if (res.statusCode === 304) { - if ( - cachedResult.validUntil < validUntil || - cachedResult.storeLock !== storeLock || - cachedResult.storeCache !== storeCache || - cachedResult.etag !== etag - ) { - return finishWith(cachedResult); - } else { - logger.debug(`GET ${url} [${res.statusCode}] (unchanged)`); - return callback(null, { - ...cachedResult, - fresh: true - }); - } - } - if ( - location && - res.statusCode >= 301 && - res.statusCode <= 308 - ) { - return finishWith({ - location: new URL(location, url).href - }); - } - const contentType = res.headers["content-type"] || ""; - const bufferArr = []; + } + if (!condition.matchWhenEmpty) { + return false; + } + } + for (const effect of rule.effects) { + if (typeof effect === "function") { + const returnedEffects = effect(data); + for (const effect of returnedEffects) { + effects.push(effect); + } + } else { + effects.push(effect); + } + } + if (rule.rules) { + for (const childRule of rule.rules) { + execRule(data, childRule, effects); + } + } + if (rule.oneOf) { + for (const childRule of rule.oneOf) { + if (execRule(data, childRule, effects)) { + break; + } + } + } + return true; + }; - const contentEncoding = res.headers["content-encoding"]; - let stream = res; - if (contentEncoding === "gzip") { - stream = stream.pipe(createGunzip()); - } else if (contentEncoding === "br") { - stream = stream.pipe(createBrotliDecompress()); - } else if (contentEncoding === "deflate") { - stream = stream.pipe(createInflate()); - } + return { + references: refs, + exec: data => { + /** @type {Effect[]} */ + const effects = []; + for (const rule of rules) { + execRule(data, rule, effects); + } + return effects; + } + }; + } - stream.on("data", chunk => { - bufferArr.push(chunk); - }); + /** + * @param {string} path current path + * @param {object[]} rules the raw rules provided by user + * @param {Map} refs references + * @returns {CompiledRule[]} rules + */ + compileRules(path, rules, refs) { + return rules.map((rule, i) => + this.compileRule(`${path}[${i}]`, rule, refs) + ); + } - stream.on("end", () => { - if (!res.complete) { - logger.log(`GET ${url} [${res.statusCode}] (terminated)`); - return callback(new Error(`${url} request was terminated`)); - } + /** + * @param {string} path current path + * @param {object} rule the raw rule provided by user + * @param {Map} refs references + * @returns {CompiledRule} normalized and compiled rule for processing + */ + compileRule(path, rule, refs) { + const unhandledProperties = new Set( + Object.keys(rule).filter(key => rule[key] !== undefined) + ); - const content = Buffer.concat(bufferArr); + /** @type {CompiledRule} */ + const compiledRule = { + conditions: [], + effects: [], + rules: undefined, + oneOf: undefined + }; - if (res.statusCode !== 200) { - logger.log(`GET ${url} [${res.statusCode}]`); - return callback( - new Error( - `${url} request status code = ${ - res.statusCode - }\n${content.toString("utf-8")}` - ) - ); - } + this.hooks.rule.call(path, rule, unhandledProperties, compiledRule, refs); - const integrity = computeIntegrity(content); - const entry = { resolved: url, integrity, contentType }; + if (unhandledProperties.has("rules")) { + unhandledProperties.delete("rules"); + const rules = rule.rules; + if (!Array.isArray(rules)) + throw this.error(path, rules, "Rule.rules must be an array of rules"); + compiledRule.rules = this.compileRules(`${path}.rules`, rules, refs); + } - finishWith({ - entry, - content - }); - }); - } - ).on("error", err => { - logger.log(`GET ${url} (error)`); - err.message += `\nwhile fetching ${url}`; - callback(err); - }); - }; + if (unhandledProperties.has("oneOf")) { + unhandledProperties.delete("oneOf"); + const oneOf = rule.oneOf; + if (!Array.isArray(oneOf)) + throw this.error(path, oneOf, "Rule.oneOf must be an array of rules"); + compiledRule.oneOf = this.compileRules(`${path}.oneOf`, oneOf, refs); + } - const fetchContent = cachedWithKey( - /** - * @param {string} url URL - * @param {function(Error=, { validUntil: number, etag?: string, entry: LockfileEntry, content: Buffer, fresh: boolean } | { validUntil: number, etag?: string, location: string, fresh: boolean }=): void} callback callback - * @returns {void} - */ (url, callback) => { - cache.get(url, null, (err, cachedResult) => { - if (err) return callback(err); - if (cachedResult) { - const isValid = cachedResult.validUntil >= Date.now(); - if (isValid) return callback(null, cachedResult); - } - fetchContentRaw(url, cachedResult, callback); - }); - }, - (url, callback) => fetchContentRaw(url, undefined, callback) - ); + if (unhandledProperties.size > 0) { + throw this.error( + path, + rule, + `Properties ${Array.from(unhandledProperties).join(", ")} are unknown` + ); + } - const isAllowed = uri => { - for (const allowed of allowedUris) { - if (typeof allowed === "string") { - if (uri.startsWith(allowed)) return true; - } else if (typeof allowed === "function") { - if (allowed(uri)) return true; - } else { - if (allowed.test(uri)) return true; - } - } - return false; - }; + return compiledRule; + } - const getInfo = cachedWithKey( - /** - * @param {string} url the url - * @param {function(Error=, { entry: LockfileEntry, content: Buffer }=): void} callback callback - * @returns {void} - */ - (url, callback) => { - if (!isAllowed(url)) { - return callback( - new Error( - `${url} doesn't match the allowedUris policy. These URIs are allowed:\n${allowedUris - .map(uri => ` - ${uri}`) - .join("\n")}` - ) - ); - } - getLockfile((err, lockfile) => { - if (err) return callback(err); - const entryOrString = lockfile.entries.get(url); - if (!entryOrString) { - if (frozen) { - return callback( - new Error( - `${url} has no lockfile entry and lockfile is frozen` - ) - ); - } - resolveContent(url, null, (err, result) => { - if (err) return callback(err); - storeResult(lockfile, url, result, callback); - }); - return; - } - if (typeof entryOrString === "string") { - const entryTag = entryOrString; - resolveContent(url, null, (err, result) => { - if (err) return callback(err); - if (!result.storeLock || entryTag === "ignore") - return callback(null, result); - if (frozen) { - return callback( - new Error( - `${url} used to have ${entryTag} lockfile entry and has content now, but lockfile is frozen` - ) - ); - } - if (!upgrade) { - return callback( - new Error( - `${url} used to have ${entryTag} lockfile entry and has content now. -This should be reflected in the lockfile, so this lockfile entry must be upgraded, but upgrading is not enabled. -Remove this line from the lockfile to force upgrading.` - ) - ); - } - storeResult(lockfile, url, result, callback); - }); - return; - } - let entry = entryOrString; - const doFetch = lockedContent => { - resolveContent(url, entry.integrity, (err, result) => { - if (err) { - if (lockedContent) { - logger.warn( - `Upgrade request to ${url} failed: ${err.message}` - ); - logger.debug(err.stack); - return callback(null, { - entry, - content: lockedContent - }); - } - return callback(err); - } - if (!result.storeLock) { - // When the lockfile entry should be no-cache - // we need to update the lockfile - if (frozen) { - return callback( - new Error( - `${url} has a lockfile entry and is no-cache now, but lockfile is frozen\nLockfile: ${entryToString( - entry - )}` - ) - ); - } - storeResult(lockfile, url, result, callback); - return; - } - if (!areLockfileEntriesEqual(result.entry, entry)) { - // When the lockfile entry is outdated - // we need to update the lockfile - if (frozen) { - return callback( - new Error( - `${url} has an outdated lockfile entry, but lockfile is frozen\nLockfile: ${entryToString( - entry - )}\nExpected: ${entryToString(result.entry)}` - ) - ); - } - storeResult(lockfile, url, result, callback); - return; - } - if (!lockedContent && cacheLocation) { - // When the lockfile cache content is missing - // we need to update the lockfile - if (frozen) { - return callback( - new Error( - `${url} is missing content in the lockfile cache, but lockfile is frozen\nLockfile: ${entryToString( - entry - )}` - ) - ); - } - storeResult(lockfile, url, result, callback); - return; - } - return callback(null, result); - }); - }; - if (cacheLocation) { - // When there is a lockfile cache - // we read the content from there - const key = getCacheKey(entry.resolved); - const filePath = join(intermediateFs, cacheLocation, key); - fs.readFile(filePath, (err, result) => { - const content = /** @type {Buffer} */ (result); - if (err) { - if (err.code === "ENOENT") return doFetch(); - return callback(err); - } - const continueWithCachedContent = result => { - if (!upgrade) { - // When not in upgrade mode, we accept the result from the lockfile cache - return callback(null, { entry, content }); - } - return doFetch(content); - }; - if (!verifyIntegrity(content, entry.integrity)) { - let contentWithChangedEol; - let isEolChanged = false; - try { - contentWithChangedEol = Buffer.from( - content.toString("utf-8").replace(/\r\n/g, "\n") - ); - isEolChanged = verifyIntegrity( - contentWithChangedEol, - entry.integrity - ); - } catch (e) { - // ignore - } - if (isEolChanged) { - if (!warnedAboutEol) { - const explainer = `Incorrect end of line sequence was detected in the lockfile cache. -The lockfile cache is protected by integrity checks, so any external modification will lead to a corrupted lockfile cache. -When using git make sure to configure .gitattributes correctly for the lockfile cache: - **/*webpack.lock.data/** -text -This will avoid that the end of line sequence is changed by git on Windows.`; - if (frozen) { - logger.error(explainer); - } else { - logger.warn(explainer); - logger.info( - "Lockfile cache will be automatically fixed now, but when lockfile is frozen this would result in an error." - ); - } - warnedAboutEol = true; - } - if (!frozen) { - // "fix" the end of line sequence of the lockfile content - logger.log( - `${filePath} fixed end of line sequence (\\r\\n instead of \\n).` - ); - intermediateFs.writeFile( - filePath, - contentWithChangedEol, - err => { - if (err) return callback(err); - continueWithCachedContent(contentWithChangedEol); - } - ); - return; - } - } - if (frozen) { - return callback( - new Error( - `${ - entry.resolved - } integrity mismatch, expected content with integrity ${ - entry.integrity - } but got ${computeIntegrity(content)}. -Lockfile corrupted (${ - isEolChanged - ? "end of line sequence was unexpectedly changed" - : "incorrectly merged? changed by other tools?" - }). -Run build with un-frozen lockfile to automatically fix lockfile.` - ) - ); - } else { - // "fix" the lockfile entry to the correct integrity - // the content has priority over the integrity value - entry = { - ...entry, - integrity: computeIntegrity(content) - }; - storeLockEntry(lockfile, url, entry); - } - } - continueWithCachedContent(result); - }); - } else { - doFetch(); - } - }); + /** + * @param {string} path current path + * @param {any} condition user provided condition value + * @returns {Condition} compiled condition + */ + compileCondition(path, condition) { + if (condition === "") { + return { + matchWhenEmpty: true, + fn: str => str === "" + }; + } + if (!condition) { + throw this.error( + path, + condition, + "Expected condition but got falsy value" + ); + } + if (typeof condition === "string") { + return { + matchWhenEmpty: condition.length === 0, + fn: str => typeof str === "string" && str.startsWith(condition) + }; + } + if (typeof condition === "function") { + try { + return { + matchWhenEmpty: condition(""), + fn: condition + }; + } catch (err) { + throw this.error( + path, + condition, + "Evaluation of condition function threw error" + ); + } + } + if (condition instanceof RegExp) { + return { + matchWhenEmpty: condition.test(""), + fn: v => typeof v === "string" && condition.test(v) + }; + } + if (Array.isArray(condition)) { + const items = condition.map((c, i) => + this.compileCondition(`${path}[${i}]`, c) + ); + return this.combineConditionsOr(items); + } + + if (typeof condition !== "object") { + throw this.error( + path, + condition, + `Unexpected ${typeof condition} when condition was expected` + ); + } + + const conditions = []; + for (const key of Object.keys(condition)) { + const value = condition[key]; + switch (key) { + case "or": + if (value) { + if (!Array.isArray(value)) { + throw this.error( + `${path}.or`, + condition.and, + "Expected array of conditions" + ); + } + conditions.push(this.compileCondition(`${path}.or`, value)); + } + break; + case "and": + if (value) { + if (!Array.isArray(value)) { + throw this.error( + `${path}.and`, + condition.and, + "Expected array of conditions" + ); + } + let i = 0; + for (const item of value) { + conditions.push(this.compileCondition(`${path}.and[${i}]`, item)); + i++; } + } + break; + case "not": + if (value) { + const matcher = this.compileCondition(`${path}.not`, value); + const fn = matcher.fn; + conditions.push({ + matchWhenEmpty: !matcher.matchWhenEmpty, + fn: v => !fn(v) + }); + } + break; + default: + throw this.error( + `${path}.${key}`, + condition[key], + `Unexpected property ${key} in condition` ); + } + } + if (conditions.length === 0) { + throw this.error( + path, + condition, + "Expected condition, but got empty thing" + ); + } + return this.combineConditionsAnd(conditions); + } + + /** + * @param {Condition[]} conditions some conditions + * @returns {Condition} merged condition + */ + combineConditionsOr(conditions) { + if (conditions.length === 0) { + return { + matchWhenEmpty: false, + fn: () => false + }; + } else if (conditions.length === 1) { + return conditions[0]; + } else { + return { + matchWhenEmpty: conditions.some(c => c.matchWhenEmpty), + fn: v => conditions.some(c => c.fn(v)) + }; + } + } - const respondWithUrlModule = (url, resourceData, callback) => { - getInfo(url.href, (err, result) => { - if (err) return callback(err); - resourceData.resource = url.href; - resourceData.path = url.origin + url.pathname; - resourceData.query = url.search; - resourceData.fragment = url.hash; - resourceData.context = new URL( - ".", - result.entry.resolved - ).href.slice(0, -1); - resourceData.data.mimetype = result.entry.contentType; - callback(null, true); - }); + /** + * @param {Condition[]} conditions some conditions + * @returns {Condition} merged condition + */ + combineConditionsAnd(conditions) { + if (conditions.length === 0) { + return { + matchWhenEmpty: false, + fn: () => false + }; + } else if (conditions.length === 1) { + return conditions[0]; + } else { + return { + matchWhenEmpty: conditions.every(c => c.matchWhenEmpty), + fn: v => conditions.every(c => c.fn(v)) + }; + } + } + + /** + * @param {string} path current path + * @param {any} value value at the error location + * @param {string} message message explaining the problem + * @returns {Error} an error object + */ + error(path, value, message) { + return new Error( + `Compiling RuleSet failed: ${message} (at ${path}: ${value})` + ); + } +} + +module.exports = RuleSetCompiler; + + +/***/ }), + +/***/ 42541: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ + + + +const util = __webpack_require__(31669); + +/** @typedef {import("./RuleSetCompiler")} RuleSetCompiler */ +/** @typedef {import("./RuleSetCompiler").Effect} Effect */ + +class UseEffectRulePlugin { + /** + * @param {RuleSetCompiler} ruleSetCompiler the rule set compiler + * @returns {void} + */ + apply(ruleSetCompiler) { + ruleSetCompiler.hooks.rule.tap( + "UseEffectRulePlugin", + (path, rule, unhandledProperties, result, references) => { + const conflictWith = (property, correctProperty) => { + if (unhandledProperties.has(property)) { + throw ruleSetCompiler.error( + `${path}.${property}`, + rule[property], + `A Rule must not have a '${property}' property when it has a '${correctProperty}' property` + ); + } + }; + + if (unhandledProperties.has("use")) { + unhandledProperties.delete("use"); + unhandledProperties.delete("enforce"); + + conflictWith("loader", "use"); + conflictWith("options", "use"); + + const use = rule.use; + const enforce = rule.enforce; + + const type = enforce ? `use-${enforce}` : "use"; + + /** + * + * @param {string} path options path + * @param {string} defaultIdent default ident when none is provided + * @param {object} item user provided use value + * @returns {Effect|function(any): Effect[]} effect + */ + const useToEffect = (path, defaultIdent, item) => { + if (typeof item === "function") { + return data => useToEffectsWithoutIdent(path, item(data)); + } else { + return useToEffectRaw(path, defaultIdent, item); + } }; - normalModuleFactory.hooks.resolveForScheme - .for(scheme) - .tapAsync( - "HttpUriPlugin", - (resourceData, resolveData, callback) => { - respondWithUrlModule( - new URL(resourceData.resource), - resourceData, - callback - ); + + /** + * + * @param {string} path options path + * @param {string} defaultIdent default ident when none is provided + * @param {object} item user provided use value + * @returns {Effect} effect + */ + const useToEffectRaw = (path, defaultIdent, item) => { + if (typeof item === "string") { + return { + type, + value: { + loader: item, + options: undefined, + ident: undefined + } + }; + } else { + const loader = item.loader; + const options = item.options; + let ident = item.ident; + if (options && typeof options === "object") { + if (!ident) ident = defaultIdent; + references.set(ident, options); } - ); - normalModuleFactory.hooks.resolveInScheme - .for(scheme) - .tapAsync("HttpUriPlugin", (resourceData, data, callback) => { - // Only handle relative urls (./xxx, ../xxx, /xxx, //xxx) - if ( - data.dependencyType !== "url" && - !/^\.{0,2}\//.test(resourceData.resource) - ) { - return callback(); + if (typeof options === "string") { + util.deprecate( + () => {}, + `Using a string as loader options is deprecated (${path}.options)`, + "DEP_WEBPACK_RULE_LOADER_OPTIONS_STRING" + )(); } - respondWithUrlModule( - new URL(resourceData.resource, data.context + "/"), - resourceData, - callback + return { + type: enforce ? `use-${enforce}` : "use", + value: { + loader, + options, + ident + } + }; + } + }; + + /** + * @param {string} path options path + * @param {any} items user provided use value + * @returns {Effect[]} effects + */ + const useToEffectsWithoutIdent = (path, items) => { + if (Array.isArray(items)) { + return items.map((item, idx) => + useToEffectRaw(`${path}[${idx}]`, "[[missing ident]]", item) ); - }); - const hooks = NormalModule.getCompilationHooks(compilation); - hooks.readResourceForScheme - .for(scheme) - .tapAsync("HttpUriPlugin", (resource, module, callback) => { - return getInfo(resource, (err, result) => { - if (err) return callback(err); - module.buildInfo.resourceIntegrity = result.entry.integrity; - callback(null, result.content); + } + return [useToEffectRaw(path, "[[missing ident]]", items)]; + }; + + /** + * @param {string} path current path + * @param {any} items user provided use value + * @returns {(Effect|function(any): Effect[])[]} effects + */ + const useToEffects = (path, items) => { + if (Array.isArray(items)) { + return items.map((item, idx) => { + const subPath = `${path}[${idx}]`; + return useToEffect(subPath, subPath, item); }); - }); - hooks.needBuild.tapAsync( - "HttpUriPlugin", - (module, context, callback) => { - if ( - module.resource && - module.resource.startsWith(`${scheme}://`) - ) { - getInfo(module.resource, (err, result) => { - if (err) return callback(err); - if ( - result.entry.integrity !== - module.buildInfo.resourceIntegrity - ) { - return callback(null, true); - } - callback(); - }); - } else { - return callback(); - } } - ); + return [useToEffect(path, path, items)]; + }; + + if (typeof use === "function") { + result.effects.push(data => + useToEffectsWithoutIdent(`${path}.use`, use(data)) + ); + } else { + for (const effect of useToEffects(`${path}.use`, use)) { + result.effects.push(effect); + } + } } - compilation.hooks.finishModules.tapAsync( - "HttpUriPlugin", - (modules, callback) => { - if (!lockfileUpdates) return callback(); - const ext = extname(lockfileLocation); - const tempFile = join( - intermediateFs, - dirname(intermediateFs, lockfileLocation), - `.${basename(lockfileLocation, ext)}.${ - (Math.random() * 10000) | 0 - }${ext}` + + if (unhandledProperties.has("loader")) { + unhandledProperties.delete("loader"); + unhandledProperties.delete("options"); + unhandledProperties.delete("enforce"); + + const loader = rule.loader; + const options = rule.options; + const enforce = rule.enforce; + + if (loader.includes("!")) { + throw ruleSetCompiler.error( + `${path}.loader`, + loader, + "Exclamation mark separated loader lists has been removed in favor of the 'use' property with arrays" ); + } - const writeDone = () => { - const nextOperation = inProgressWrite.shift(); - if (nextOperation) { - nextOperation(); - } else { - inProgressWrite = undefined; - } - }; - const runWrite = () => { - intermediateFs.readFile(lockfileLocation, (err, buffer) => { - if (err && err.code !== "ENOENT") { - writeDone(); - return callback(err); - } - const lockfile = buffer - ? Lockfile.parse(buffer.toString("utf-8")) - : new Lockfile(); - for (const [key, value] of lockfileUpdates) { - lockfile.entries.set(key, value); - } - intermediateFs.writeFile(tempFile, lockfile.toString(), err => { - if (err) { - writeDone(); - return intermediateFs.unlink(tempFile, () => callback(err)); - } - intermediateFs.rename(tempFile, lockfileLocation, err => { - if (err) { - writeDone(); - return intermediateFs.unlink(tempFile, () => - callback(err) - ); - } - writeDone(); - callback(); - }); - }); - }); - }; - if (inProgressWrite) { - inProgressWrite.push(runWrite); - } else { - inProgressWrite = []; - runWrite(); - } + if (loader.includes("?")) { + throw ruleSetCompiler.error( + `${path}.loader`, + loader, + "Query arguments on 'loader' has been removed in favor of the 'options' property" + ); } - ); + + if (typeof options === "string") { + util.deprecate( + () => {}, + `Using a string as loader options is deprecated (${path}.options)`, + "DEP_WEBPACK_RULE_LOADER_OPTIONS_STRING" + )(); + } + + const ident = + options && typeof options === "object" ? path : undefined; + references.set(ident, options); + result.effects.push({ + type: enforce ? `use-${enforce}` : "use", + value: { + loader, + options, + ident + } + }); + } + } + ); + } + + useItemToEffects(path, item) {} +} + +module.exports = UseEffectRulePlugin; + + +/***/ }), + +/***/ 31372: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php +*/ + + + +const RuntimeGlobals = __webpack_require__(49404); +const Template = __webpack_require__(92066); +const HelperRuntimeModule = __webpack_require__(22970); + +class AsyncModuleRuntimeModule extends HelperRuntimeModule { + constructor() { + super("async module"); + } + + /** + * @returns {string} runtime code + */ + generate() { + const { runtimeTemplate } = this.compilation; + const fn = RuntimeGlobals.asyncModule; + return Template.asString([ + 'var webpackThen = typeof Symbol === "function" ? Symbol("webpack then") : "__webpack_then__";', + 'var webpackExports = typeof Symbol === "function" ? Symbol("webpack exports") : "__webpack_exports__";', + `var completeQueue = ${runtimeTemplate.basicFunction("queue", [ + "if(queue) {", + Template.indent([ + `queue.forEach(${runtimeTemplate.expressionFunction( + "fn.r--", + "fn" + )});`, + `queue.forEach(${runtimeTemplate.expressionFunction( + "fn.r-- ? fn.r++ : fn()", + "fn" + )});` + ]), + "}" + ])}`, + `var completeFunction = ${runtimeTemplate.expressionFunction( + "!--fn.r && fn()", + "fn" + )};`, + `var queueFunction = ${runtimeTemplate.expressionFunction( + "queue ? queue.push(fn) : completeFunction(fn)", + "queue, fn" + )};`, + `var wrapDeps = ${runtimeTemplate.returningFunction( + `deps.map(${runtimeTemplate.basicFunction("dep", [ + 'if(dep !== null && typeof dep === "object") {', + Template.indent([ + "if(dep[webpackThen]) return dep;", + "if(dep.then) {", + Template.indent([ + "var queue = [];", + `dep.then(${runtimeTemplate.basicFunction("r", [ + "obj[webpackExports] = r;", + "completeQueue(queue);", + "queue = 0;" + ])});`, + `var obj = {}; + obj[webpackThen] = ${runtimeTemplate.expressionFunction( + "queueFunction(queue, fn), dep['catch'](reject)", + "fn, reject" + )};`, + "return obj;" + ]), + "}" + ]), + "}", + `var ret = {}; + ret[webpackThen] = ${runtimeTemplate.expressionFunction( + "completeFunction(fn)", + "fn" + )}; + ret[webpackExports] = dep; + return ret;` + ])})`, + "deps" + )};`, + `${fn} = ${runtimeTemplate.basicFunction("module, body, hasAwait", [ + "var queue = hasAwait && [];", + "var exports = module.exports;", + "var currentDeps;", + "var outerResolve;", + "var reject;", + "var isEvaluating = true;", + "var nested = false;", + `var whenAll = ${runtimeTemplate.basicFunction( + "deps, onResolve, onReject", + [ + "if (nested) return;", + "nested = true;", + "onResolve.r += deps.length;", + `deps.map(${runtimeTemplate.expressionFunction( + "dep[webpackThen](onResolve, onReject)", + "dep, i" + )});`, + "nested = false;" + ] + )};`, + `var promise = new Promise(${runtimeTemplate.basicFunction( + "resolve, rej", + [ + "reject = rej;", + `outerResolve = ${runtimeTemplate.expressionFunction( + "resolve(exports), completeQueue(queue), queue = 0" + )};` + ] + )});`, + "promise[webpackExports] = exports;", + `promise[webpackThen] = ${runtimeTemplate.basicFunction( + "fn, rejectFn", + [ + "if (isEvaluating) { return completeFunction(fn); }", + "if (currentDeps) whenAll(currentDeps, fn, rejectFn);", + "queueFunction(queue, fn);", + "promise['catch'](rejectFn);" + ] + )};`, + "module.exports = promise;", + `body(${runtimeTemplate.basicFunction("deps", [ + "if(!deps) return outerResolve();", + "currentDeps = wrapDeps(deps);", + "var fn, result;", + `var promise = new Promise(${runtimeTemplate.basicFunction( + "resolve, reject", + [ + `fn = ${runtimeTemplate.expressionFunction( + `resolve(result = currentDeps.map(${runtimeTemplate.returningFunction( + "d[webpackExports]", + "d" + )}))` + )};`, + "fn.r = 0;", + "whenAll(currentDeps, fn, reject);" + ] + )});`, + "return fn.r ? promise : result;" + ])}).then(outerResolve, reject);`, + "isEvaluating = false;" + ])};` + ]); + } +} + +module.exports = AsyncModuleRuntimeModule; + + +/***/ }), + +/***/ 86150: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php +*/ + + + +const RuntimeGlobals = __webpack_require__(49404); +const RuntimeModule = __webpack_require__(61439); +const Template = __webpack_require__(92066); +const JavascriptModulesPlugin = __webpack_require__(76767); +const { getUndoPath } = __webpack_require__(96236); + +class AutoPublicPathRuntimeModule extends RuntimeModule { + constructor() { + super("publicPath", RuntimeModule.STAGE_BASIC); + } + + /** + * @returns {string} runtime code + */ + generate() { + const { compilation } = this; + const { scriptType, importMetaName, path } = compilation.outputOptions; + const chunkName = compilation.getPath( + JavascriptModulesPlugin.getChunkFilenameTemplate( + this.chunk, + compilation.outputOptions + ), + { + chunk: this.chunk, + contentHashType: "javascript" } ); + const undoPath = getUndoPath(chunkName, path, false); + + return Template.asString([ + "var scriptUrl;", + scriptType === "module" + ? `if (typeof ${importMetaName}.url === "string") scriptUrl = ${importMetaName}.url` + : Template.asString([ + `if (${RuntimeGlobals.global}.importScripts) scriptUrl = ${RuntimeGlobals.global}.location + "";`, + `var document = ${RuntimeGlobals.global}.document;`, + "if (!scriptUrl && document) {", + Template.indent([ + `if (document.currentScript)`, + Template.indent(`scriptUrl = document.currentScript.src`), + "if (!scriptUrl) {", + Template.indent([ + 'var scripts = document.getElementsByTagName("script");', + "if(scripts.length) scriptUrl = scripts[scripts.length - 1].src" + ]), + "}" + ]), + "}" + ]), + "// When supporting browsers where an automatic publicPath is not supported you must specify an output.publicPath manually via configuration", + '// or pass an empty string ("") and set the __webpack_public_path__ variable from your code to use your own logic.', + 'if (!scriptUrl) throw new Error("Automatic publicPath is not supported in this browser");', + 'scriptUrl = scriptUrl.replace(/#.*$/, "").replace(/\\?.*$/, "").replace(/\\/[^\\/]+$/, "/");', + !undoPath + ? `${RuntimeGlobals.publicPath} = scriptUrl;` + : `${RuntimeGlobals.publicPath} = scriptUrl + ${JSON.stringify( + undoPath + )};` + ]); } } -module.exports = HttpUriPlugin; +module.exports = AutoPublicPathRuntimeModule; /***/ }), -/***/ 80573: -/***/ (function(module) { +/***/ 43818: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; /* @@ -112838,27 +111918,163 @@ module.exports = HttpUriPlugin; -class ArraySerializer { - serialize(array, { write }) { - write(array.length); - for (const item of array) write(item); +const RuntimeGlobals = __webpack_require__(49404); +const RuntimeModule = __webpack_require__(61439); + +class ChunkNameRuntimeModule extends RuntimeModule { + /** + * @param {string} chunkName the chunk's name + */ + constructor(chunkName) { + super("chunkName"); + this.chunkName = chunkName; } - deserialize({ read }) { - const length = read(); - const array = []; - for (let i = 0; i < length; i++) { - array.push(read()); + + /** + * @returns {string} runtime code + */ + generate() { + return `${RuntimeGlobals.chunkName} = ${JSON.stringify(this.chunkName)};`; + } +} + +module.exports = ChunkNameRuntimeModule; + + +/***/ }), + +/***/ 24013: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php +*/ + + + +const RuntimeGlobals = __webpack_require__(49404); +const Template = __webpack_require__(92066); +const HelperRuntimeModule = __webpack_require__(22970); + +class CompatGetDefaultExportRuntimeModule extends HelperRuntimeModule { + constructor() { + super("compat get default export"); + } + + /** + * @returns {string} runtime code + */ + generate() { + const { runtimeTemplate } = this.compilation; + const fn = RuntimeGlobals.compatGetDefaultExport; + return Template.asString([ + "// getDefaultExport function for compatibility with non-harmony modules", + `${fn} = ${runtimeTemplate.basicFunction("module", [ + "var getter = module && module.__esModule ?", + Template.indent([ + `${runtimeTemplate.returningFunction("module['default']")} :`, + `${runtimeTemplate.returningFunction("module")};` + ]), + `${RuntimeGlobals.definePropertyGetters}(getter, { a: getter });`, + "return getter;" + ])};` + ]); + } +} + +module.exports = CompatGetDefaultExportRuntimeModule; + + +/***/ }), + +/***/ 65788: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php +*/ + + + +const RuntimeGlobals = __webpack_require__(49404); +const RuntimeModule = __webpack_require__(61439); + +/** @typedef {import("../MainTemplate")} MainTemplate */ + +class CompatRuntimeModule extends RuntimeModule { + constructor() { + super("compat", RuntimeModule.STAGE_ATTACH); + this.fullHash = true; + } + + /** + * @returns {string} runtime code + */ + generate() { + const { chunkGraph, chunk, compilation } = this; + const { + runtimeTemplate, + mainTemplate, + moduleTemplates, + dependencyTemplates + } = compilation; + const bootstrap = mainTemplate.hooks.bootstrap.call( + "", + chunk, + compilation.hash || "XXXX", + moduleTemplates.javascript, + dependencyTemplates + ); + const localVars = mainTemplate.hooks.localVars.call( + "", + chunk, + compilation.hash || "XXXX" + ); + const requireExtensions = mainTemplate.hooks.requireExtensions.call( + "", + chunk, + compilation.hash || "XXXX" + ); + const runtimeRequirements = chunkGraph.getTreeRuntimeRequirements(chunk); + let requireEnsure = ""; + if (runtimeRequirements.has(RuntimeGlobals.ensureChunk)) { + const requireEnsureHandler = mainTemplate.hooks.requireEnsure.call( + "", + chunk, + compilation.hash || "XXXX", + "chunkId" + ); + if (requireEnsureHandler) { + requireEnsure = `${ + RuntimeGlobals.ensureChunkHandlers + }.compat = ${runtimeTemplate.basicFunction( + "chunkId, promises", + requireEnsureHandler + )};`; + } } - return array; + return [bootstrap, localVars, requireEnsure, requireExtensions] + .filter(Boolean) + .join("\n"); + } + + /** + * @returns {boolean} true, if the runtime module should get it's own scope + */ + shouldIsolate() { + // We avoid isolating this to have better backward-compat + return false; } } -module.exports = ArraySerializer; +module.exports = CompatRuntimeModule; /***/ }), -/***/ 7732: +/***/ 58470: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; @@ -112868,956 +112084,540 @@ module.exports = ArraySerializer; -const memoize = __webpack_require__(84297); -const SerializerMiddleware = __webpack_require__(37063); +const RuntimeGlobals = __webpack_require__(49404); +const Template = __webpack_require__(92066); +const HelperRuntimeModule = __webpack_require__(22970); + +class CreateFakeNamespaceObjectRuntimeModule extends HelperRuntimeModule { + constructor() { + super("create fake namespace object"); + } + + /** + * @returns {string} runtime code + */ + generate() { + const { runtimeTemplate } = this.compilation; + const fn = RuntimeGlobals.createFakeNamespaceObject; + return Template.asString([ + `var getProto = Object.getPrototypeOf ? ${runtimeTemplate.returningFunction( + "Object.getPrototypeOf(obj)", + "obj" + )} : ${runtimeTemplate.returningFunction("obj.__proto__", "obj")};`, + "var leafPrototypes;", + "// create a fake namespace object", + "// mode & 1: value is a module id, require it", + "// mode & 2: merge all properties of value into the ns", + "// mode & 4: return value when already ns object", + "// mode & 16: return value when it's Promise-like", + "// mode & 8|1: behave like require", + // Note: must be a function (not arrow), because this is used in body! + `${fn} = function(value, mode) {`, + Template.indent([ + `if(mode & 1) value = this(value);`, + `if(mode & 8) return value;`, + "if(typeof value === 'object' && value) {", + Template.indent([ + "if((mode & 4) && value.__esModule) return value;", + "if((mode & 16) && typeof value.then === 'function') return value;" + ]), + "}", + "var ns = Object.create(null);", + `${RuntimeGlobals.makeNamespaceObject}(ns);`, + "var def = {};", + "leafPrototypes = leafPrototypes || [null, getProto({}), getProto([]), getProto(getProto)];", + "for(var current = mode & 2 && value; typeof current == 'object' && !~leafPrototypes.indexOf(current); current = getProto(current)) {", + Template.indent([ + `Object.getOwnPropertyNames(current).forEach(${runtimeTemplate.expressionFunction( + `def[key] = ${runtimeTemplate.returningFunction("value[key]", "")}`, + "key" + )});` + ]), + "}", + `def['default'] = ${runtimeTemplate.returningFunction("value", "")};`, + `${RuntimeGlobals.definePropertyGetters}(ns, def);`, + "return ns;" + ]), + "};" + ]); + } +} + +module.exports = CreateFakeNamespaceObjectRuntimeModule; -/** @typedef {import("./types").BufferSerializableType} BufferSerializableType */ -/** @typedef {import("./types").PrimitiveSerializableType} PrimitiveSerializableType */ +/***/ }), + +/***/ 41690: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + +"use strict"; /* -Format: + MIT License http://www.opensource.org/licenses/mit-license.php +*/ -File -> Section* -Section -> NullsSection | - BooleansSection | - F64NumbersSection | - I32NumbersSection | - I8NumbersSection | - ShortStringSection | - StringSection | - BufferSection | - NopSection +const RuntimeGlobals = __webpack_require__(49404); +const Template = __webpack_require__(92066); +const HelperRuntimeModule = __webpack_require__(22970); +class CreateScriptUrlRuntimeModule extends HelperRuntimeModule { + constructor() { + super("trusted types"); + } -NullsSection -> - NullHeaderByte | Null2HeaderByte | Null3HeaderByte | - Nulls8HeaderByte 0xnn (n:count - 4) | - Nulls32HeaderByte n:ui32 (n:count - 260) | -BooleansSection -> TrueHeaderByte | FalseHeaderByte | BooleansSectionHeaderByte BooleansCountAndBitsByte -F64NumbersSection -> F64NumbersSectionHeaderByte f64* -I32NumbersSection -> I32NumbersSectionHeaderByte i32* -I8NumbersSection -> I8NumbersSectionHeaderByte i8* -ShortStringSection -> ShortStringSectionHeaderByte ascii-byte* -StringSection -> StringSectionHeaderByte i32:length utf8-byte* -BufferSection -> BufferSectionHeaderByte i32:length byte* -NopSection --> NopSectionHeaderByte + /** + * @returns {string} runtime code + */ + generate() { + const { compilation } = this; + const { runtimeTemplate, outputOptions } = compilation; + const { trustedTypes } = outputOptions; + const fn = RuntimeGlobals.createScriptUrl; -ShortStringSectionHeaderByte -> 0b1nnn_nnnn (n:length) + if (!trustedTypes) { + // Skip Trusted Types logic. + return Template.asString([ + `${fn} = ${runtimeTemplate.returningFunction("url", "url")};` + ]); + } -F64NumbersSectionHeaderByte -> 0b001n_nnnn (n:count - 1) -I32NumbersSectionHeaderByte -> 0b010n_nnnn (n:count - 1) -I8NumbersSectionHeaderByte -> 0b011n_nnnn (n:count - 1) + return Template.asString([ + "var policy;", + `${fn} = ${runtimeTemplate.basicFunction("url", [ + "// Create Trusted Type policy if Trusted Types are available and the policy doesn't exist yet.", + "if (policy === undefined) {", + Template.indent([ + "policy = {", + Template.indent([ + `createScriptURL: ${runtimeTemplate.returningFunction( + "url", + "url" + )}` + ]), + "};", + 'if (typeof trustedTypes !== "undefined" && trustedTypes.createPolicy) {', + Template.indent([ + `policy = trustedTypes.createPolicy(${JSON.stringify( + trustedTypes.policyName + )}, policy);` + ]), + "}" + ]), + "}", + "return policy.createScriptURL(url);" + ])};` + ]); + } +} -NullsSectionHeaderByte -> 0b0001_nnnn (n:count - 1) -BooleansCountAndBitsByte -> - 0b0000_1xxx (count = 3) | - 0b0001_xxxx (count = 4) | - 0b001x_xxxx (count = 5) | - 0b01xx_xxxx (count = 6) | - 0b1nnn_nnnn (n:count - 7, 7 <= count <= 133) - 0xff n:ui32 (n:count, 134 <= count < 2^32) +module.exports = CreateScriptUrlRuntimeModule; -StringSectionHeaderByte -> 0b0000_1110 -BufferSectionHeaderByte -> 0b0000_1111 -NopSectionHeaderByte -> 0b0000_1011 -FalseHeaderByte -> 0b0000_1100 -TrueHeaderByte -> 0b0000_1101 -RawNumber -> n (n <= 10) +/***/ }), +/***/ 24905: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php */ -const LAZY_HEADER = 0x0b; -const TRUE_HEADER = 0x0c; -const FALSE_HEADER = 0x0d; -const BOOLEANS_HEADER = 0x0e; -const NULL_HEADER = 0x10; -const NULL2_HEADER = 0x11; -const NULL3_HEADER = 0x12; -const NULLS8_HEADER = 0x13; -const NULLS32_HEADER = 0x14; -const NULL_AND_I8_HEADER = 0x15; -const NULL_AND_I32_HEADER = 0x16; -const NULL_AND_TRUE_HEADER = 0x17; -const NULL_AND_FALSE_HEADER = 0x18; -const STRING_HEADER = 0x1e; -const BUFFER_HEADER = 0x1f; -const I8_HEADER = 0x60; -const I32_HEADER = 0x40; -const F64_HEADER = 0x20; -const SHORT_STRING_HEADER = 0x80; -/** Uplift high-order bits */ -const NUMBERS_HEADER_MASK = 0xe0; -const NUMBERS_COUNT_MASK = 0x1f; // 0b0001_1111 -const SHORT_STRING_LENGTH_MASK = 0x7f; // 0b0111_1111 -const HEADER_SIZE = 1; -const I8_SIZE = 1; -const I32_SIZE = 4; -const F64_SIZE = 8; +const RuntimeGlobals = __webpack_require__(49404); +const Template = __webpack_require__(92066); +const HelperRuntimeModule = __webpack_require__(22970); + +class DefinePropertyGettersRuntimeModule extends HelperRuntimeModule { + constructor() { + super("define property getters"); + } + + /** + * @returns {string} runtime code + */ + generate() { + const { runtimeTemplate } = this.compilation; + const fn = RuntimeGlobals.definePropertyGetters; + return Template.asString([ + "// define getter functions for harmony exports", + `${fn} = ${runtimeTemplate.basicFunction("exports, definition", [ + `for(var key in definition) {`, + Template.indent([ + `if(${RuntimeGlobals.hasOwnProperty}(definition, key) && !${RuntimeGlobals.hasOwnProperty}(exports, key)) {`, + Template.indent([ + "Object.defineProperty(exports, key, { enumerable: true, get: definition[key] });" + ]), + "}" + ]), + "}" + ])};` + ]); + } +} + +module.exports = DefinePropertyGettersRuntimeModule; + + +/***/ }), + +/***/ 92857: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php +*/ + + + +const RuntimeGlobals = __webpack_require__(49404); +const RuntimeModule = __webpack_require__(61439); +const Template = __webpack_require__(92066); + +class EnsureChunkRuntimeModule extends RuntimeModule { + constructor(runtimeRequirements) { + super("ensure chunk"); + this.runtimeRequirements = runtimeRequirements; + } + + /** + * @returns {string} runtime code + */ + generate() { + const { runtimeTemplate } = this.compilation; + // Check if there are non initial chunks which need to be imported using require-ensure + if (this.runtimeRequirements.has(RuntimeGlobals.ensureChunkHandlers)) { + const handlers = RuntimeGlobals.ensureChunkHandlers; + return Template.asString([ + `${handlers} = {};`, + "// This file contains only the entry chunk.", + "// The chunk loading function for additional chunks", + `${RuntimeGlobals.ensureChunk} = ${runtimeTemplate.basicFunction( + "chunkId", + [ + `return Promise.all(Object.keys(${handlers}).reduce(${runtimeTemplate.basicFunction( + "promises, key", + [`${handlers}[key](chunkId, promises);`, "return promises;"] + )}, []));` + ] + )};` + ]); + } else { + // There ensureChunk is used somewhere in the tree, so we need an empty requireEnsure + // function. This can happen with multiple entrypoints. + return Template.asString([ + "// The chunk loading function for additional chunks", + "// Since all referenced chunks are already included", + "// in this file, this function is empty here.", + `${RuntimeGlobals.ensureChunk} = ${runtimeTemplate.returningFunction( + "Promise.resolve()" + )};` + ]); + } + } +} + +module.exports = EnsureChunkRuntimeModule; + -const MEASURE_START_OPERATION = Symbol("MEASURE_START_OPERATION"); -const MEASURE_END_OPERATION = Symbol("MEASURE_END_OPERATION"); +/***/ }), -/** @typedef {typeof MEASURE_START_OPERATION} MEASURE_START_OPERATION_TYPE */ -/** @typedef {typeof MEASURE_END_OPERATION} MEASURE_END_OPERATION_TYPE */ +/***/ 53288: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { -const identifyNumber = n => { - if (n === (n | 0)) { - if (n <= 127 && n >= -128) return 0; - if (n <= 2147483647 && n >= -2147483648) return 1; - } - return 2; -}; +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php +*/ -/** - * @typedef {PrimitiveSerializableType[]} DeserializedType - * @typedef {BufferSerializableType[]} SerializedType - * @extends {SerializerMiddleware} - */ -class BinaryMiddleware extends SerializerMiddleware { + + +const RuntimeGlobals = __webpack_require__(49404); +const RuntimeModule = __webpack_require__(61439); +const Template = __webpack_require__(92066); +const { first } = __webpack_require__(34715); + +/** @typedef {import("../Chunk")} Chunk */ +/** @typedef {import("../Compilation")} Compilation */ +/** @typedef {import("../Compilation").AssetInfo} AssetInfo */ +/** @typedef {import("../Compilation").PathData} PathData */ + +/** @typedef {function(PathData, AssetInfo=): string} FilenameFunction */ + +class GetChunkFilenameRuntimeModule extends RuntimeModule { /** - * @param {DeserializedType} data data - * @param {Object} context context object - * @returns {SerializedType|Promise} serialized data + * @param {string} contentType the contentType to use the content hash for + * @param {string} name kind of filename + * @param {string} global function name to be assigned + * @param {function(Chunk): string | FilenameFunction} getFilenameForChunk functor to get the filename or function + * @param {boolean} allChunks when false, only async chunks are included */ - serialize(data, context) { - return this._serialize(data, context); - } - - _serializeLazy(fn, context) { - return SerializerMiddleware.serializeLazy(fn, data => - this._serialize(data, context) - ); + constructor(contentType, name, global, getFilenameForChunk, allChunks) { + super(`get ${name} chunk filename`); + this.contentType = contentType; + this.global = global; + this.getFilenameForChunk = getFilenameForChunk; + this.allChunks = allChunks; + this.dependentHash = true; } /** - * @param {DeserializedType} data data - * @param {Object} context context object - * @param {{ leftOverBuffer: Buffer | null, allocationSize: number, increaseCounter: number }} allocationScope allocation scope - * @returns {SerializedType} serialized data + * @returns {string} runtime code */ - _serialize( - data, - context, - allocationScope = { - allocationSize: 1024, - increaseCounter: 0, - leftOverBuffer: null - } - ) { - /** @type {Buffer} */ - let leftOverBuffer = null; - /** @type {BufferSerializableType[]} */ - let buffers = []; - /** @type {Buffer} */ - let currentBuffer = allocationScope ? allocationScope.leftOverBuffer : null; - allocationScope.leftOverBuffer = null; - let currentPosition = 0; - if (currentBuffer === null) { - currentBuffer = Buffer.allocUnsafe(allocationScope.allocationSize); - } - const allocate = bytesNeeded => { - if (currentBuffer !== null) { - if (currentBuffer.length - currentPosition >= bytesNeeded) return; - flush(); - } - if (leftOverBuffer && leftOverBuffer.length >= bytesNeeded) { - currentBuffer = leftOverBuffer; - leftOverBuffer = null; - } else { - currentBuffer = Buffer.allocUnsafe( - Math.max(bytesNeeded, allocationScope.allocationSize) - ); - if ( - !(allocationScope.increaseCounter = - (allocationScope.increaseCounter + 1) % 4) && - allocationScope.allocationSize < 16777216 - ) { - allocationScope.allocationSize = allocationScope.allocationSize << 1; - } - } - }; - const flush = () => { - if (currentBuffer !== null) { - if (currentPosition > 0) { - buffers.push( - Buffer.from( - currentBuffer.buffer, - currentBuffer.byteOffset, - currentPosition - ) - ); - } - if ( - !leftOverBuffer || - leftOverBuffer.length < currentBuffer.length - currentPosition - ) { - leftOverBuffer = Buffer.from( - currentBuffer.buffer, - currentBuffer.byteOffset + currentPosition, - currentBuffer.byteLength - currentPosition - ); - } - - currentBuffer = null; - currentPosition = 0; - } - }; - const writeU8 = byte => { - currentBuffer.writeUInt8(byte, currentPosition++); - }; - const writeU32 = ui32 => { - currentBuffer.writeUInt32LE(ui32, currentPosition); - currentPosition += 4; - }; - const measureStack = []; - const measureStart = () => { - measureStack.push(buffers.length, currentPosition); - }; - const measureEnd = () => { - const oldPos = measureStack.pop(); - const buffersIndex = measureStack.pop(); - let size = currentPosition - oldPos; - for (let i = buffersIndex; i < buffers.length; i++) { - size += buffers[i].length; - } - return size; - }; - for (let i = 0; i < data.length; i++) { - const thing = data[i]; - switch (typeof thing) { - case "function": { - if (!SerializerMiddleware.isLazy(thing)) - throw new Error("Unexpected function " + thing); - /** @type {SerializedType | (() => SerializedType)} */ - let serializedData = - SerializerMiddleware.getLazySerializedValue(thing); - if (serializedData === undefined) { - if (SerializerMiddleware.isLazy(thing, this)) { - flush(); - allocationScope.leftOverBuffer = leftOverBuffer; - const result = - /** @type {(Exclude>)[]} */ ( - thing() - ); - const data = this._serialize(result, context, allocationScope); - leftOverBuffer = allocationScope.leftOverBuffer; - allocationScope.leftOverBuffer = null; - SerializerMiddleware.setLazySerializedValue(thing, data); - serializedData = data; - } else { - serializedData = this._serializeLazy(thing, context); - flush(); - buffers.push(serializedData); - break; - } - } else { - if (typeof serializedData === "function") { - flush(); - buffers.push(serializedData); - break; - } - } - const lengths = []; - for (const item of serializedData) { - let last; - if (typeof item === "function") { - lengths.push(0); - } else if (item.length === 0) { - // ignore - } else if ( - lengths.length > 0 && - (last = lengths[lengths.length - 1]) !== 0 - ) { - const remaining = 0xffffffff - last; - if (remaining >= item.length) { - lengths[lengths.length - 1] += item.length; - } else { - lengths.push(item.length - remaining); - lengths[lengths.length - 2] = 0xffffffff; - } - } else { - lengths.push(item.length); - } - } - allocate(5 + lengths.length * 4); - writeU8(LAZY_HEADER); - writeU32(lengths.length); - for (const l of lengths) { - writeU32(l); - } - flush(); - for (const item of serializedData) { - buffers.push(item); - } - break; - } - case "string": { - const len = Buffer.byteLength(thing); - if (len >= 128 || len !== thing.length) { - allocate(len + HEADER_SIZE + I32_SIZE); - writeU8(STRING_HEADER); - writeU32(len); - currentBuffer.write(thing, currentPosition); - currentPosition += len; - } else if (len >= 70) { - allocate(len + HEADER_SIZE); - writeU8(SHORT_STRING_HEADER | len); - - currentBuffer.write(thing, currentPosition, "latin1"); - currentPosition += len; - } else { - allocate(len + HEADER_SIZE); - writeU8(SHORT_STRING_HEADER | len); + generate() { + const { + global, + chunk, + chunkGraph, + contentType, + getFilenameForChunk, + allChunks, + compilation + } = this; + const { runtimeTemplate } = compilation; - for (let i = 0; i < len; i++) { - currentBuffer[currentPosition++] = thing.charCodeAt(i); - } - } - break; - } - case "number": { - const type = identifyNumber(thing); - if (type === 0 && thing >= 0 && thing <= 10) { - // shortcut for very small numbers - allocate(I8_SIZE); - writeU8(thing); - break; - } - /** - * amount of numbers to write - * @type {number} - */ - let n = 1; - for (; n < 32 && i + n < data.length; n++) { - const item = data[i + n]; - if (typeof item !== "number") break; - if (identifyNumber(item) !== type) break; - } - switch (type) { - case 0: - allocate(HEADER_SIZE + I8_SIZE * n); - writeU8(I8_HEADER | (n - 1)); - while (n > 0) { - currentBuffer.writeInt8( - /** @type {number} */ (data[i]), - currentPosition - ); - currentPosition += I8_SIZE; - n--; - i++; - } - break; - case 1: - allocate(HEADER_SIZE + I32_SIZE * n); - writeU8(I32_HEADER | (n - 1)); - while (n > 0) { - currentBuffer.writeInt32LE( - /** @type {number} */ (data[i]), - currentPosition - ); - currentPosition += I32_SIZE; - n--; - i++; - } - break; - case 2: - allocate(HEADER_SIZE + F64_SIZE * n); - writeU8(F64_HEADER | (n - 1)); - while (n > 0) { - currentBuffer.writeDoubleLE( - /** @type {number} */ (data[i]), - currentPosition - ); - currentPosition += F64_SIZE; - n--; - i++; - } - break; - } + /** @type {Map>} */ + const chunkFilenames = new Map(); + let maxChunks = 0; + /** @type {string} */ + let dynamicFilename; - i--; - break; - } - case "boolean": { - let lastByte = thing === true ? 1 : 0; - const bytes = []; - let count = 1; - let n; - for (n = 1; n < 0xffffffff && i + n < data.length; n++) { - const item = data[i + n]; - if (typeof item !== "boolean") break; - const pos = count & 0x7; - if (pos === 0) { - bytes.push(lastByte); - lastByte = item === true ? 1 : 0; - } else if (item === true) { - lastByte |= 1 << pos; - } - count++; - } - i += count - 1; - if (count === 1) { - allocate(HEADER_SIZE); - writeU8(lastByte === 1 ? TRUE_HEADER : FALSE_HEADER); - } else if (count === 2) { - allocate(HEADER_SIZE * 2); - writeU8(lastByte & 1 ? TRUE_HEADER : FALSE_HEADER); - writeU8(lastByte & 2 ? TRUE_HEADER : FALSE_HEADER); - } else if (count <= 6) { - allocate(HEADER_SIZE + I8_SIZE); - writeU8(BOOLEANS_HEADER); - writeU8((1 << count) | lastByte); - } else if (count <= 133) { - allocate(HEADER_SIZE + I8_SIZE + I8_SIZE * bytes.length + I8_SIZE); - writeU8(BOOLEANS_HEADER); - writeU8(0x80 | (count - 7)); - for (const byte of bytes) writeU8(byte); - writeU8(lastByte); - } else { - allocate( - HEADER_SIZE + - I8_SIZE + - I32_SIZE + - I8_SIZE * bytes.length + - I8_SIZE - ); - writeU8(BOOLEANS_HEADER); - writeU8(0xff); - writeU32(count); - for (const byte of bytes) writeU8(byte); - writeU8(lastByte); - } - break; + /** + * @param {Chunk} c the chunk + * @returns {void} + */ + const addChunk = c => { + const chunkFilename = getFilenameForChunk(c); + if (chunkFilename) { + let set = chunkFilenames.get(chunkFilename); + if (set === undefined) { + chunkFilenames.set(chunkFilename, (set = new Set())); } - case "object": { - if (thing === null) { - let n; - for (n = 1; n < 0x100000104 && i + n < data.length; n++) { - const item = data[i + n]; - if (item !== null) break; - } - i += n - 1; - if (n === 1) { - if (i + 1 < data.length) { - const next = data[i + 1]; - if (next === true) { - allocate(HEADER_SIZE); - writeU8(NULL_AND_TRUE_HEADER); - i++; - } else if (next === false) { - allocate(HEADER_SIZE); - writeU8(NULL_AND_FALSE_HEADER); - i++; - } else if (typeof next === "number") { - const type = identifyNumber(next); - if (type === 0) { - allocate(HEADER_SIZE + I8_SIZE); - writeU8(NULL_AND_I8_HEADER); - currentBuffer.writeInt8(next, currentPosition); - currentPosition += I8_SIZE; - i++; - } else if (type === 1) { - allocate(HEADER_SIZE + I32_SIZE); - writeU8(NULL_AND_I32_HEADER); - currentBuffer.writeInt32LE(next, currentPosition); - currentPosition += I32_SIZE; - i++; - } else { - allocate(HEADER_SIZE); - writeU8(NULL_HEADER); - } - } else { - allocate(HEADER_SIZE); - writeU8(NULL_HEADER); - } - } else { - allocate(HEADER_SIZE); - writeU8(NULL_HEADER); - } - } else if (n === 2) { - allocate(HEADER_SIZE); - writeU8(NULL2_HEADER); - } else if (n === 3) { - allocate(HEADER_SIZE); - writeU8(NULL3_HEADER); - } else if (n < 260) { - allocate(HEADER_SIZE + I8_SIZE); - writeU8(NULLS8_HEADER); - writeU8(n - 4); - } else { - allocate(HEADER_SIZE + I32_SIZE); - writeU8(NULLS32_HEADER); - writeU32(n - 260); - } - } else if (Buffer.isBuffer(thing)) { - if (thing.length < 8192) { - allocate(HEADER_SIZE + I32_SIZE + thing.length); - writeU8(BUFFER_HEADER); - writeU32(thing.length); - thing.copy(currentBuffer, currentPosition); - currentPosition += thing.length; - } else { - allocate(HEADER_SIZE + I32_SIZE); - writeU8(BUFFER_HEADER); - writeU32(thing.length); - flush(); - buffers.push(thing); + set.add(c); + if (typeof chunkFilename === "string") { + if (set.size < maxChunks) return; + if (set.size === maxChunks) { + if (chunkFilename.length < dynamicFilename.length) return; + if (chunkFilename.length === dynamicFilename.length) { + if (chunkFilename < dynamicFilename) return; } } - break; + maxChunks = set.size; + dynamicFilename = chunkFilename; } - case "symbol": { - if (thing === MEASURE_START_OPERATION) { - measureStart(); - } else if (thing === MEASURE_END_OPERATION) { - const size = measureEnd(); - allocate(HEADER_SIZE + I32_SIZE); - writeU8(I32_HEADER); - currentBuffer.writeInt32LE(size, currentPosition); - currentPosition += I32_SIZE; - } - break; + } + }; + + /** @type {string[]} */ + const includedChunksMessages = []; + if (allChunks) { + includedChunksMessages.push("all chunks"); + for (const c of chunk.getAllReferencedChunks()) { + addChunk(c); + } + } else { + includedChunksMessages.push("async chunks"); + for (const c of chunk.getAllAsyncChunks()) { + addChunk(c); + } + const includeEntries = chunkGraph + .getTreeRuntimeRequirements(chunk) + .has(RuntimeGlobals.ensureChunkIncludeEntries); + if (includeEntries) { + includedChunksMessages.push("sibling chunks for the entrypoint"); + for (const c of chunkGraph.getChunkEntryDependentChunksIterable( + chunk + )) { + addChunk(c); } } } - flush(); - - allocationScope.leftOverBuffer = leftOverBuffer; - - // avoid leaking memory - currentBuffer = null; - leftOverBuffer = null; - allocationScope = undefined; - const _buffers = buffers; - buffers = undefined; - return _buffers; - } - - /** - * @param {SerializedType} data data - * @param {Object} context context object - * @returns {DeserializedType|Promise} deserialized data - */ - deserialize(data, context) { - return this._deserialize(data, context); - } - - _createLazyDeserialized(content, context) { - return SerializerMiddleware.createLazy( - memoize(() => this._deserialize(content, context)), - this, - undefined, - content - ); - } - - _deserializeLazy(fn, context) { - return SerializerMiddleware.deserializeLazy(fn, data => - this._deserialize(data, context) - ); - } - - /** - * @param {SerializedType} data data - * @param {Object} context context object - * @returns {DeserializedType} deserialized data - */ - _deserialize(data, context) { - let currentDataItem = 0; - let currentBuffer = data[0]; - let currentIsBuffer = Buffer.isBuffer(currentBuffer); - let currentPosition = 0; + for (const entrypoint of chunk.getAllReferencedAsyncEntrypoints()) { + addChunk(entrypoint.chunks[entrypoint.chunks.length - 1]); + } - const retainedBuffer = context.retainedBuffer || (x => x); + /** @type {Map>} */ + const staticUrls = new Map(); + /** @type {Set} */ + const dynamicUrlChunks = new Set(); - const checkOverflow = () => { - if (currentPosition >= currentBuffer.length) { - currentPosition = 0; - currentDataItem++; - currentBuffer = - currentDataItem < data.length ? data[currentDataItem] : null; - currentIsBuffer = Buffer.isBuffer(currentBuffer); + /** + * @param {Chunk} c the chunk + * @param {string | FilenameFunction} chunkFilename the filename template for the chunk + * @returns {void} + */ + const addStaticUrl = (c, chunkFilename) => { + /** + * @param {string | number} value a value + * @returns {string} string to put in quotes + */ + const unquotedStringify = value => { + const str = `${value}`; + if (str.length >= 5 && str === `${c.id}`) { + // This is shorter and generates the same result + return '" + chunkId + "'; + } + const s = JSON.stringify(str); + return s.slice(1, s.length - 1); + }; + const unquotedStringifyWithLength = value => length => + unquotedStringify(`${value}`.slice(0, length)); + const chunkFilenameValue = + typeof chunkFilename === "function" + ? JSON.stringify( + chunkFilename({ + chunk: c, + contentHashType: contentType + }) + ) + : JSON.stringify(chunkFilename); + const staticChunkFilename = compilation.getPath(chunkFilenameValue, { + hash: `" + ${RuntimeGlobals.getFullHash}() + "`, + hashWithLength: length => + `" + ${RuntimeGlobals.getFullHash}().slice(0, ${length}) + "`, + chunk: { + id: unquotedStringify(c.id), + hash: unquotedStringify(c.renderedHash), + hashWithLength: unquotedStringifyWithLength(c.renderedHash), + name: unquotedStringify(c.name || c.id), + contentHash: { + [contentType]: unquotedStringify(c.contentHash[contentType]) + }, + contentHashWithLength: { + [contentType]: unquotedStringifyWithLength( + c.contentHash[contentType] + ) + } + }, + contentHashType: contentType + }); + let set = staticUrls.get(staticChunkFilename); + if (set === undefined) { + staticUrls.set(staticChunkFilename, (set = new Set())); } + set.add(c.id); }; - const isInCurrentBuffer = n => { - return currentIsBuffer && n + currentPosition <= currentBuffer.length; - }; - const ensureBuffer = () => { - if (!currentIsBuffer) { - throw new Error( - currentBuffer === null - ? "Unexpected end of stream" - : "Unexpected lazy element in stream" - ); + + for (const [filename, chunks] of chunkFilenames) { + if (filename !== dynamicFilename) { + for (const c of chunks) addStaticUrl(c, filename); + } else { + for (const c of chunks) dynamicUrlChunks.add(c); } - }; + } + /** - * Reads n bytes - * @param {number} n amount of bytes to read - * @returns {Buffer} buffer with bytes + * @param {function(Chunk): string | number} fn function from chunk to value + * @returns {string} code with static mapping of results of fn */ - const read = n => { - ensureBuffer(); - const rem = currentBuffer.length - currentPosition; - if (rem < n) { - const buffers = [read(rem)]; - n -= rem; - ensureBuffer(); - while (currentBuffer.length < n) { - const b = /** @type {Buffer} */ (currentBuffer); - buffers.push(b); - n -= b.length; - currentDataItem++; - currentBuffer = - currentDataItem < data.length ? data[currentDataItem] : null; - currentIsBuffer = Buffer.isBuffer(currentBuffer); - ensureBuffer(); + const createMap = fn => { + const obj = {}; + let useId = false; + let lastKey; + let entries = 0; + for (const c of dynamicUrlChunks) { + const value = fn(c); + if (value === c.id) { + useId = true; + } else { + obj[c.id] = value; + lastKey = c.id; + entries++; } - buffers.push(read(n)); - return Buffer.concat(buffers); } - const b = /** @type {Buffer} */ (currentBuffer); - const res = Buffer.from(b.buffer, b.byteOffset + currentPosition, n); - currentPosition += n; - checkOverflow(); - return res; + if (entries === 0) return "chunkId"; + if (entries === 1) { + return useId + ? `(chunkId === ${JSON.stringify(lastKey)} ? ${JSON.stringify( + obj[lastKey] + )} : chunkId)` + : JSON.stringify(obj[lastKey]); + } + return useId + ? `(${JSON.stringify(obj)}[chunkId] || chunkId)` + : `${JSON.stringify(obj)}[chunkId]`; }; + /** - * Reads up to n bytes - * @param {number} n amount of bytes to read - * @returns {Buffer} buffer with bytes + * @param {function(Chunk): string | number} fn function from chunk to value + * @returns {string} code with static mapping of results of fn for including in quoted string */ - const readUpTo = n => { - ensureBuffer(); - const rem = currentBuffer.length - currentPosition; - if (rem < n) { - n = rem; - } - const b = /** @type {Buffer} */ (currentBuffer); - const res = Buffer.from(b.buffer, b.byteOffset + currentPosition, n); - currentPosition += n; - checkOverflow(); - return res; - }; - const readU8 = () => { - ensureBuffer(); - /** - * There is no need to check remaining buffer size here - * since {@link checkOverflow} guarantees at least one byte remaining - */ - const byte = /** @type {Buffer} */ (currentBuffer).readUInt8( - currentPosition - ); - currentPosition += I8_SIZE; - checkOverflow(); - return byte; - }; - const readU32 = () => { - return read(I32_SIZE).readUInt32LE(0); + const mapExpr = fn => { + return `" + ${createMap(fn)} + "`; }; - const readBits = (data, n) => { - let mask = 1; - while (n !== 0) { - result.push((data & mask) !== 0); - mask = mask << 1; - n--; - } + + /** + * @param {function(Chunk): string | number} fn function from chunk to value + * @returns {function(number): string} function which generates code with static mapping of results of fn for including in quoted string for specific length + */ + const mapExprWithLength = fn => length => { + return `" + ${createMap(c => `${fn(c)}`.slice(0, length))} + "`; }; - const dispatchTable = Array.from({ length: 256 }).map((_, header) => { - switch (header) { - case LAZY_HEADER: - return () => { - const count = readU32(); - const lengths = Array.from({ length: count }).map(() => readU32()); - const content = []; - for (let l of lengths) { - if (l === 0) { - if (typeof currentBuffer !== "function") { - throw new Error("Unexpected non-lazy element in stream"); - } - content.push(currentBuffer); - currentDataItem++; - currentBuffer = - currentDataItem < data.length ? data[currentDataItem] : null; - currentIsBuffer = Buffer.isBuffer(currentBuffer); - } else { - do { - const buf = readUpTo(l); - l -= buf.length; - content.push(retainedBuffer(buf)); - } while (l > 0); - } - } - result.push(this._createLazyDeserialized(content, context)); - }; - case BUFFER_HEADER: - return () => { - const len = readU32(); - result.push(retainedBuffer(read(len))); - }; - case TRUE_HEADER: - return () => result.push(true); - case FALSE_HEADER: - return () => result.push(false); - case NULL3_HEADER: - return () => result.push(null, null, null); - case NULL2_HEADER: - return () => result.push(null, null); - case NULL_HEADER: - return () => result.push(null); - case NULL_AND_TRUE_HEADER: - return () => result.push(null, true); - case NULL_AND_FALSE_HEADER: - return () => result.push(null, false); - case NULL_AND_I8_HEADER: - return () => { - if (currentIsBuffer) { - result.push( - null, - /** @type {Buffer} */ (currentBuffer).readInt8(currentPosition) - ); - currentPosition += I8_SIZE; - checkOverflow(); - } else { - result.push(null, read(I8_SIZE).readInt8(0)); - } - }; - case NULL_AND_I32_HEADER: - return () => { - result.push(null); - if (isInCurrentBuffer(I32_SIZE)) { - result.push( - /** @type {Buffer} */ (currentBuffer).readInt32LE( - currentPosition - ) - ); - currentPosition += I32_SIZE; - checkOverflow(); - } else { - result.push(read(I32_SIZE).readInt32LE(0)); - } - }; - case NULLS8_HEADER: - return () => { - const len = readU8() + 4; - for (let i = 0; i < len; i++) { - result.push(null); - } - }; - case NULLS32_HEADER: - return () => { - const len = readU32() + 260; - for (let i = 0; i < len; i++) { - result.push(null); - } - }; - case BOOLEANS_HEADER: - return () => { - const innerHeader = readU8(); - if ((innerHeader & 0xf0) === 0) { - readBits(innerHeader, 3); - } else if ((innerHeader & 0xe0) === 0) { - readBits(innerHeader, 4); - } else if ((innerHeader & 0xc0) === 0) { - readBits(innerHeader, 5); - } else if ((innerHeader & 0x80) === 0) { - readBits(innerHeader, 6); - } else if (innerHeader !== 0xff) { - let count = (innerHeader & 0x7f) + 7; - while (count > 8) { - readBits(readU8(), 8); - count -= 8; - } - readBits(readU8(), count); - } else { - let count = readU32(); - while (count > 8) { - readBits(readU8(), 8); - count -= 8; - } - readBits(readU8(), count); - } - }; - case STRING_HEADER: - return () => { - const len = readU32(); - if (isInCurrentBuffer(len) && currentPosition + len < 0x7fffffff) { - result.push( - currentBuffer.toString( - undefined, - currentPosition, - currentPosition + len - ) - ); - currentPosition += len; - checkOverflow(); - } else { - result.push(read(len).toString()); - } - }; - case SHORT_STRING_HEADER: - return () => result.push(""); - case SHORT_STRING_HEADER | 1: - return () => { - if (currentIsBuffer && currentPosition < 0x7ffffffe) { - result.push( - currentBuffer.toString( - "latin1", - currentPosition, - currentPosition + 1 - ) - ); - currentPosition++; - checkOverflow(); - } else { - result.push(read(1).toString("latin1")); - } - }; - case I8_HEADER: - return () => { - if (currentIsBuffer) { - result.push( - /** @type {Buffer} */ (currentBuffer).readInt8(currentPosition) - ); - currentPosition++; - checkOverflow(); - } else { - result.push(read(1).readInt8(0)); - } - }; - default: - if (header <= 10) { - return () => result.push(header); - } else if ((header & SHORT_STRING_HEADER) === SHORT_STRING_HEADER) { - const len = header & SHORT_STRING_LENGTH_MASK; - return () => { - if ( - isInCurrentBuffer(len) && - currentPosition + len < 0x7fffffff - ) { - result.push( - currentBuffer.toString( - "latin1", - currentPosition, - currentPosition + len - ) - ); - currentPosition += len; - checkOverflow(); - } else { - result.push(read(len).toString("latin1")); - } - }; - } else if ((header & NUMBERS_HEADER_MASK) === F64_HEADER) { - const len = (header & NUMBERS_COUNT_MASK) + 1; - return () => { - const need = F64_SIZE * len; - if (isInCurrentBuffer(need)) { - for (let i = 0; i < len; i++) { - result.push( - /** @type {Buffer} */ (currentBuffer).readDoubleLE( - currentPosition - ) - ); - currentPosition += F64_SIZE; - } - checkOverflow(); - } else { - const buf = read(need); - for (let i = 0; i < len; i++) { - result.push(buf.readDoubleLE(i * F64_SIZE)); - } - } - }; - } else if ((header & NUMBERS_HEADER_MASK) === I32_HEADER) { - const len = (header & NUMBERS_COUNT_MASK) + 1; - return () => { - const need = I32_SIZE * len; - if (isInCurrentBuffer(need)) { - for (let i = 0; i < len; i++) { - result.push( - /** @type {Buffer} */ (currentBuffer).readInt32LE( - currentPosition - ) - ); - currentPosition += I32_SIZE; - } - checkOverflow(); - } else { - const buf = read(need); - for (let i = 0; i < len; i++) { - result.push(buf.readInt32LE(i * I32_SIZE)); - } - } - }; - } else if ((header & NUMBERS_HEADER_MASK) === I8_HEADER) { - const len = (header & NUMBERS_COUNT_MASK) + 1; - return () => { - const need = I8_SIZE * len; - if (isInCurrentBuffer(need)) { - for (let i = 0; i < len; i++) { - result.push( - /** @type {Buffer} */ (currentBuffer).readInt8( - currentPosition - ) - ); - currentPosition += I8_SIZE; - } - checkOverflow(); - } else { - const buf = read(need); - for (let i = 0; i < len; i++) { - result.push(buf.readInt8(i * I8_SIZE)); - } - } - }; - } else { - return () => { - throw new Error( - `Unexpected header byte 0x${header.toString(16)}` - ); - }; + + const url = + dynamicFilename && + compilation.getPath(JSON.stringify(dynamicFilename), { + hash: `" + ${RuntimeGlobals.getFullHash}() + "`, + hashWithLength: length => + `" + ${RuntimeGlobals.getFullHash}().slice(0, ${length}) + "`, + chunk: { + id: `" + chunkId + "`, + hash: mapExpr(c => c.renderedHash), + hashWithLength: mapExprWithLength(c => c.renderedHash), + name: mapExpr(c => c.name || c.id), + contentHash: { + [contentType]: mapExpr(c => c.contentHash[contentType]) + }, + contentHashWithLength: { + [contentType]: mapExprWithLength(c => c.contentHash[contentType]) } - } - }); + }, + contentHashType: contentType + }); - /** @type {DeserializedType} */ - let result = []; - while (currentBuffer !== null) { - if (typeof currentBuffer === "function") { - result.push(this._deserializeLazy(currentBuffer, context)); - currentDataItem++; - currentBuffer = - currentDataItem < data.length ? data[currentDataItem] : null; - currentIsBuffer = Buffer.isBuffer(currentBuffer); - } else { - const header = readU8(); - dispatchTable[header](); - } - } + return Template.asString([ + `// This function allow to reference ${includedChunksMessages.join( + " and " + )}`, + `${global} = ${runtimeTemplate.basicFunction( + "chunkId", - // avoid leaking memory in context - let _result = result; - result = undefined; - return _result; + staticUrls.size > 0 + ? [ + "// return url for filenames not based on template", + // it minimizes to `x===1?"...":x===2?"...":"..."` + Template.asString( + Array.from(staticUrls, ([url, ids]) => { + const condition = + ids.size === 1 + ? `chunkId === ${JSON.stringify(first(ids))}` + : `{${Array.from( + ids, + id => `${JSON.stringify(id)}:1` + ).join(",")}}[chunkId]`; + return `if (${condition}) return ${url};`; + }) + ), + "// return url for filenames based on template", + `return ${url};` + ] + : ["// return url for filenames based on template", `return ${url};`] + )};` + ]); } } -module.exports = BinaryMiddleware; - -module.exports.MEASURE_START_OPERATION = MEASURE_START_OPERATION; -module.exports.MEASURE_END_OPERATION = MEASURE_END_OPERATION; +module.exports = GetChunkFilenameRuntimeModule; /***/ }), -/***/ 32973: -/***/ (function(module) { +/***/ 28454: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; /* @@ -113826,22 +112626,35 @@ module.exports.MEASURE_END_OPERATION = MEASURE_END_OPERATION; -class DateObjectSerializer { - serialize(obj, { write }) { - write(obj.getTime()); +const RuntimeGlobals = __webpack_require__(49404); +const RuntimeModule = __webpack_require__(61439); + +/** @typedef {import("../Compilation")} Compilation */ + +class GetFullHashRuntimeModule extends RuntimeModule { + constructor() { + super("getFullHash"); + this.fullHash = true; } - deserialize({ read }) { - return new Date(read()); + + /** + * @returns {string} runtime code + */ + generate() { + const { runtimeTemplate } = this.compilation; + return `${RuntimeGlobals.getFullHash} = ${runtimeTemplate.returningFunction( + JSON.stringify(this.compilation.hash || "XXXX") + )}`; } } -module.exports = DateObjectSerializer; +module.exports = GetFullHashRuntimeModule; /***/ }), -/***/ 60252: -/***/ (function(module) { +/***/ 10034: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; /* @@ -113850,671 +112663,465 @@ module.exports = DateObjectSerializer; -class ErrorObjectSerializer { - constructor(Type) { - this.Type = Type; +const RuntimeGlobals = __webpack_require__(49404); +const RuntimeModule = __webpack_require__(61439); +const Template = __webpack_require__(92066); + +/** @typedef {import("../Compilation")} Compilation */ + +class GetMainFilenameRuntimeModule extends RuntimeModule { + /** + * @param {string} name readable name + * @param {string} global global object binding + * @param {string} filename main file name + */ + constructor(name, global, filename) { + super(`get ${name} filename`); + this.global = global; + this.filename = filename; } - serialize(obj, { write }) { - write(obj.message); - write(obj.stack); + /** + * @returns {string} runtime code + */ + generate() { + const { global, filename, compilation, chunk } = this; + const { runtimeTemplate } = compilation; + const url = compilation.getPath(JSON.stringify(filename), { + hash: `" + ${RuntimeGlobals.getFullHash}() + "`, + hashWithLength: length => + `" + ${RuntimeGlobals.getFullHash}().slice(0, ${length}) + "`, + chunk, + runtime: chunk.runtime + }); + return Template.asString([ + `${global} = ${runtimeTemplate.returningFunction(url)};` + ]); } +} - deserialize({ read }) { - const err = new this.Type(); +module.exports = GetMainFilenameRuntimeModule; - err.message = read(); - err.stack = read(); - return err; +/***/ }), + +/***/ 89651: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php +*/ + + + +const RuntimeGlobals = __webpack_require__(49404); +const RuntimeModule = __webpack_require__(61439); +const Template = __webpack_require__(92066); + +class GlobalRuntimeModule extends RuntimeModule { + constructor() { + super("global"); + } + + /** + * @returns {string} runtime code + */ + generate() { + return Template.asString([ + `${RuntimeGlobals.global} = (function() {`, + Template.indent([ + "if (typeof globalThis === 'object') return globalThis;", + "try {", + Template.indent( + // This works in non-strict mode + // or + // This works if eval is allowed (see CSP) + "return this || new Function('return this')();" + ), + "} catch (e) {", + Template.indent( + // This works if the window reference is available + "if (typeof window === 'object') return window;" + ), + "}" + // It can still be `undefined`, but nothing to do about it... + // We return `undefined`, instead of nothing here, so it's + // easier to handle this case: + // if (!global) { … } + ]), + "})();" + ]); } } -module.exports = ErrorObjectSerializer; +module.exports = GlobalRuntimeModule; /***/ }), -/***/ 40572: +/***/ 39399: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; /* MIT License http://www.opensource.org/licenses/mit-license.php + Author Sergey Melyukov @smelukov */ -const { constants } = __webpack_require__(64293); -const { pipeline } = __webpack_require__(92413); -const { - createBrotliCompress, - createBrotliDecompress, - createGzip, - createGunzip, - constants: zConstants -} = __webpack_require__(78761); -const createHash = __webpack_require__(24123); -const { dirname, join, mkdirp } = __webpack_require__(93204); -const memoize = __webpack_require__(84297); -const SerializerMiddleware = __webpack_require__(37063); +const RuntimeGlobals = __webpack_require__(49404); +const RuntimeModule = __webpack_require__(61439); +const Template = __webpack_require__(92066); -/** @typedef {typeof import("../util/Hash")} Hash */ -/** @typedef {import("../util/fs").IntermediateFileSystem} IntermediateFileSystem */ -/** @typedef {import("./types").BufferSerializableType} BufferSerializableType */ +class HasOwnPropertyRuntimeModule extends RuntimeModule { + constructor() { + super("hasOwnProperty shorthand"); + } -/* -Format: + /** + * @returns {string} runtime code + */ + generate() { + const { runtimeTemplate } = this.compilation; -File -> Header Section* + return Template.asString([ + `${RuntimeGlobals.hasOwnProperty} = ${runtimeTemplate.returningFunction( + "Object.prototype.hasOwnProperty.call(obj, prop)", + "obj, prop" + )}` + ]); + } +} -Version -> u32 -AmountOfSections -> u32 -SectionSize -> i32 (if less than zero represents lazy value) +module.exports = HasOwnPropertyRuntimeModule; -Header -> Version AmountOfSections SectionSize* -Buffer -> n bytes -Section -> Buffer +/***/ }), + +/***/ 22970: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php */ -// "wpc" + 1 in little-endian -const VERSION = 0x01637077; -/** - * @param {Buffer[]} buffers buffers - * @param {string | Hash} hashFunction hash function to use - * @returns {string} hash - */ -const hashForName = (buffers, hashFunction) => { - const hash = createHash(hashFunction); - for (const buf of buffers) hash.update(buf); - return /** @type {string} */ (hash.digest("hex")); -}; -const COMPRESSION_CHUNK_SIZE = 100 * 1024 * 1024; -const DECOMPRESSION_CHUNK_SIZE = 100 * 1024 * 1024; +const RuntimeModule = __webpack_require__(61439); -const writeUInt64LE = Buffer.prototype.writeBigUInt64LE - ? (buf, value, offset) => { - buf.writeBigUInt64LE(BigInt(value), offset); - } - : (buf, value, offset) => { - const low = value % 0x100000000; - const high = (value - low) / 0x100000000; - buf.writeUInt32LE(low, offset); - buf.writeUInt32LE(high, offset + 4); - }; +class HelperRuntimeModule extends RuntimeModule { + /** + * @param {string} name a readable name + */ + constructor(name) { + super(name); + } +} -const readUInt64LE = Buffer.prototype.readBigUInt64LE - ? (buf, offset) => { - return Number(buf.readBigUInt64LE(offset)); - } - : (buf, offset) => { - const low = buf.readUInt32LE(offset); - const high = buf.readUInt32LE(offset + 4); - return high * 0x100000000 + low; - }; +module.exports = HelperRuntimeModule; -/** - * @typedef {Object} SerializeResult - * @property {string | false} name - * @property {number} size - * @property {Promise=} backgroundJob - */ -/** - * @param {FileMiddleware} middleware this - * @param {BufferSerializableType[] | Promise} data data to be serialized - * @param {string | boolean} name file base name - * @param {function(string | false, Buffer[]): Promise} writeFile writes a file - * @param {string | Hash} hashFunction hash function to use - * @returns {Promise} resulting file pointer and promise - */ -const serialize = async ( - middleware, - data, - name, - writeFile, - hashFunction = "md4" -) => { - /** @type {(Buffer[] | Buffer | SerializeResult | Promise)[]} */ - const processedData = []; - /** @type {WeakMap>} */ - const resultToLazy = new WeakMap(); - /** @type {Buffer[]} */ - let lastBuffers = undefined; - for (const item of await data) { - if (typeof item === "function") { - if (!SerializerMiddleware.isLazy(item)) - throw new Error("Unexpected function"); - if (!SerializerMiddleware.isLazy(item, middleware)) { - throw new Error( - "Unexpected lazy value with non-this target (can't pass through lazy values)" - ); - } - lastBuffers = undefined; - const serializedInfo = SerializerMiddleware.getLazySerializedValue(item); - if (serializedInfo) { - if (typeof serializedInfo === "function") { - throw new Error( - "Unexpected lazy value with non-this target (can't pass through lazy values)" - ); - } else { - processedData.push(serializedInfo); - } - } else { - const content = item(); - if (content) { - const options = SerializerMiddleware.getLazyOptions(item); - processedData.push( - serialize( - middleware, - content, - (options && options.name) || true, - writeFile, - hashFunction - ).then(result => { - /** @type {any} */ (item).options.size = result.size; - resultToLazy.set(result, item); - return result; - }) - ); - } else { - throw new Error( - "Unexpected falsy value returned by lazy value function" - ); - } - } - } else if (item) { - if (lastBuffers) { - lastBuffers.push(item); - } else { - lastBuffers = [item]; - processedData.push(lastBuffers); - } - } else { - throw new Error("Unexpected falsy value in items array"); - } - } - /** @type {Promise[]} */ - const backgroundJobs = []; - const resolvedData = ( - await Promise.all( - /** @type {Promise[]} */ ( - processedData - ) - ) - ).map(item => { - if (Array.isArray(item) || Buffer.isBuffer(item)) return item; +/***/ }), - backgroundJobs.push(item.backgroundJob); - // create pointer buffer from size and name - const name = /** @type {string} */ (item.name); - const nameBuffer = Buffer.from(name); - const buf = Buffer.allocUnsafe(8 + nameBuffer.length); - writeUInt64LE(buf, item.size, 0); - nameBuffer.copy(buf, 8, 0); - const lazy = resultToLazy.get(item); - SerializerMiddleware.setLazySerializedValue(lazy, buf); - return buf; - }); - const lengths = []; - for (const item of resolvedData) { - if (Array.isArray(item)) { - let l = 0; - for (const b of item) l += b.length; - while (l > 0x7fffffff) { - lengths.push(0x7fffffff); - l -= 0x7fffffff; - } - lengths.push(l); - } else if (item) { - lengths.push(-item.length); - } else { - throw new Error("Unexpected falsy value in resolved data " + item); - } - } - const header = Buffer.allocUnsafe(8 + lengths.length * 4); - header.writeUInt32LE(VERSION, 0); - header.writeUInt32LE(lengths.length, 4); - for (let i = 0; i < lengths.length; i++) { - header.writeInt32LE(lengths[i], 8 + i * 4); - } - const buf = [header]; - for (const item of resolvedData) { - if (Array.isArray(item)) { - for (const b of item) buf.push(b); - } else if (item) { - buf.push(item); - } - } - if (name === true) { - name = hashForName(buf, hashFunction); - } - backgroundJobs.push(writeFile(name, buf)); - let size = 0; - for (const b of buf) size += b.length; - return { - size, - name, - backgroundJob: - backgroundJobs.length === 1 - ? backgroundJobs[0] - : Promise.all(backgroundJobs) - }; -}; +/***/ 80647: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { -/** - * @param {FileMiddleware} middleware this - * @param {string | false} name filename - * @param {function(string | false): Promise} readFile read content of a file - * @returns {Promise} deserialized data - */ -const deserialize = async (middleware, name, readFile) => { - const contents = await readFile(name); - if (contents.length === 0) throw new Error("Empty file " + name); - let contentsIndex = 0; - let contentItem = contents[0]; - let contentItemLength = contentItem.length; - let contentPosition = 0; - if (contentItemLength === 0) throw new Error("Empty file " + name); - const nextContent = () => { - contentsIndex++; - contentItem = contents[contentsIndex]; - contentItemLength = contentItem.length; - contentPosition = 0; - }; - const ensureData = n => { - if (contentPosition === contentItemLength) { - nextContent(); - } - while (contentItemLength - contentPosition < n) { - const remaining = contentItem.slice(contentPosition); - let lengthFromNext = n - remaining.length; - const buffers = [remaining]; - for (let i = contentsIndex + 1; i < contents.length; i++) { - const l = contents[i].length; - if (l > lengthFromNext) { - buffers.push(contents[i].slice(0, lengthFromNext)); - contents[i] = contents[i].slice(lengthFromNext); - lengthFromNext = 0; - break; - } else { - buffers.push(contents[i]); - contentsIndex = i; - lengthFromNext -= l; - } - } - if (lengthFromNext > 0) throw new Error("Unexpected end of data"); - contentItem = Buffer.concat(buffers, n); - contentItemLength = n; - contentPosition = 0; - } - }; - const readUInt32LE = () => { - ensureData(4); - const value = contentItem.readUInt32LE(contentPosition); - contentPosition += 4; - return value; - }; - const readInt32LE = () => { - ensureData(4); - const value = contentItem.readInt32LE(contentPosition); - contentPosition += 4; - return value; - }; - const readSlice = l => { - ensureData(l); - if (contentPosition === 0 && contentItemLength === l) { - const result = contentItem; - if (contentsIndex + 1 < contents.length) { - nextContent(); - } else { - contentPosition = l; - } - return result; +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php +*/ + + + +const { SyncWaterfallHook } = __webpack_require__(34718); +const Compilation = __webpack_require__(59622); +const RuntimeGlobals = __webpack_require__(49404); +const Template = __webpack_require__(92066); +const HelperRuntimeModule = __webpack_require__(22970); + +/** @typedef {import("../Chunk")} Chunk */ +/** @typedef {import("../Compiler")} Compiler */ + +/** + * @typedef {Object} LoadScriptCompilationHooks + * @property {SyncWaterfallHook<[string, Chunk]>} createScript + */ + +/** @type {WeakMap} */ +const compilationHooksMap = new WeakMap(); + +class LoadScriptRuntimeModule extends HelperRuntimeModule { + /** + * @param {Compilation} compilation the compilation + * @returns {LoadScriptCompilationHooks} hooks + */ + static getCompilationHooks(compilation) { + if (!(compilation instanceof Compilation)) { + throw new TypeError( + "The 'compilation' argument must be an instance of Compilation" + ); } - const result = contentItem.slice(contentPosition, contentPosition + l); - contentPosition += l; - // we clone the buffer here to allow the original content to be garbage collected - return l * 2 < contentItem.buffer.byteLength ? Buffer.from(result) : result; - }; - const version = readUInt32LE(); - if (version !== VERSION) { - throw new Error("Invalid file version"); - } - const sectionCount = readUInt32LE(); - const lengths = []; - let lastLengthPositive = false; - for (let i = 0; i < sectionCount; i++) { - const value = readInt32LE(); - const valuePositive = value >= 0; - if (lastLengthPositive && valuePositive) { - lengths[lengths.length - 1] += value; - } else { - lengths.push(value); - lastLengthPositive = valuePositive; + let hooks = compilationHooksMap.get(compilation); + if (hooks === undefined) { + hooks = { + createScript: new SyncWaterfallHook(["source", "chunk"]) + }; + compilationHooksMap.set(compilation, hooks); } + return hooks; } - const result = []; - for (let length of lengths) { - if (length < 0) { - const slice = readSlice(-length); - const size = Number(readUInt64LE(slice, 0)); - const nameBuffer = slice.slice(8); - const name = nameBuffer.toString(); - result.push( - SerializerMiddleware.createLazy( - memoize(() => deserialize(middleware, name, readFile)), - middleware, - { - name, - size - }, - slice - ) - ); - } else { - if (contentPosition === contentItemLength) { - nextContent(); - } else if (contentPosition !== 0) { - if (length <= contentItemLength - contentPosition) { - result.push( - Buffer.from( - contentItem.buffer, - contentItem.byteOffset + contentPosition, - length - ) - ); - contentPosition += length; - length = 0; - } else { - const l = contentItemLength - contentPosition; - result.push( - Buffer.from( - contentItem.buffer, - contentItem.byteOffset + contentPosition, - l - ) - ); - length -= l; - contentPosition = contentItemLength; - } - } else { - if (length >= contentItemLength) { - result.push(contentItem); - length -= contentItemLength; - contentPosition = contentItemLength; - } else { - result.push( - Buffer.from(contentItem.buffer, contentItem.byteOffset, length) - ); - contentPosition += length; - length = 0; - } - } - while (length > 0) { - nextContent(); - if (length >= contentItemLength) { - result.push(contentItem); - length -= contentItemLength; - contentPosition = contentItemLength; - } else { - result.push( - Buffer.from(contentItem.buffer, contentItem.byteOffset, length) - ); - contentPosition += length; - length = 0; - } - } - } + + /** + * @param {boolean=} withCreateScriptUrl use create script url for trusted types + */ + constructor(withCreateScriptUrl) { + super("load script"); + this._withCreateScriptUrl = withCreateScriptUrl; } - return result; -}; -/** - * @typedef {BufferSerializableType[]} DeserializedType - * @typedef {true} SerializedType - * @extends {SerializerMiddleware} - */ -class FileMiddleware extends SerializerMiddleware { /** - * @param {IntermediateFileSystem} fs filesystem - * @param {string | Hash} hashFunction hash function to use + * @returns {string} runtime code */ - constructor(fs, hashFunction = "md4") { - super(); - this.fs = fs; - this._hashFunction = hashFunction; + generate() { + const { compilation } = this; + const { runtimeTemplate, outputOptions } = compilation; + const { + scriptType, + chunkLoadTimeout: loadTimeout, + crossOriginLoading, + uniqueName, + charset + } = outputOptions; + const fn = RuntimeGlobals.loadScript; + + const { createScript } = + LoadScriptRuntimeModule.getCompilationHooks(compilation); + + const code = Template.asString([ + "script = document.createElement('script');", + scriptType ? `script.type = ${JSON.stringify(scriptType)};` : "", + charset ? "script.charset = 'utf-8';" : "", + `script.timeout = ${loadTimeout / 1000};`, + `if (${RuntimeGlobals.scriptNonce}) {`, + Template.indent( + `script.setAttribute("nonce", ${RuntimeGlobals.scriptNonce});` + ), + "}", + uniqueName + ? 'script.setAttribute("data-webpack", dataWebpackPrefix + key);' + : "", + `script.src = ${ + this._withCreateScriptUrl + ? `${RuntimeGlobals.createScriptUrl}(url)` + : "url" + };`, + crossOriginLoading + ? Template.asString([ + "if (script.src.indexOf(window.location.origin + '/') !== 0) {", + Template.indent( + `script.crossOrigin = ${JSON.stringify(crossOriginLoading)};` + ), + "}" + ]) + : "" + ]); + + return Template.asString([ + "var inProgress = {};", + uniqueName + ? `var dataWebpackPrefix = ${JSON.stringify(uniqueName + ":")};` + : "// data-webpack is not used as build has no uniqueName", + "// loadScript function to load a script via script tag", + `${fn} = ${runtimeTemplate.basicFunction("url, done, key, chunkId", [ + "if(inProgress[url]) { inProgress[url].push(done); return; }", + "var script, needAttach;", + "if(key !== undefined) {", + Template.indent([ + 'var scripts = document.getElementsByTagName("script");', + "for(var i = 0; i < scripts.length; i++) {", + Template.indent([ + "var s = scripts[i];", + `if(s.getAttribute("src") == url${ + uniqueName + ? ' || s.getAttribute("data-webpack") == dataWebpackPrefix + key' + : "" + }) { script = s; break; }` + ]), + "}" + ]), + "}", + "if(!script) {", + Template.indent([ + "needAttach = true;", + createScript.call(code, this.chunk) + ]), + "}", + "inProgress[url] = [done];", + "var onScriptComplete = " + + runtimeTemplate.basicFunction( + "prev, event", + Template.asString([ + "// avoid mem leaks in IE.", + "script.onerror = script.onload = null;", + "clearTimeout(timeout);", + "var doneFns = inProgress[url];", + "delete inProgress[url];", + "script.parentNode && script.parentNode.removeChild(script);", + `doneFns && doneFns.forEach(${runtimeTemplate.returningFunction( + "fn(event)", + "fn" + )});`, + "if(prev) return prev(event);" + ]) + ), + ";", + `var timeout = setTimeout(onScriptComplete.bind(null, undefined, { type: 'timeout', target: script }), ${loadTimeout});`, + "script.onerror = onScriptComplete.bind(null, script.onerror);", + "script.onload = onScriptComplete.bind(null, script.onload);", + "needAttach && document.head.appendChild(script);" + ])};` + ]); + } +} + +module.exports = LoadScriptRuntimeModule; + + +/***/ }), + +/***/ 62962: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php +*/ + + + +const RuntimeGlobals = __webpack_require__(49404); +const Template = __webpack_require__(92066); +const HelperRuntimeModule = __webpack_require__(22970); + +class MakeNamespaceObjectRuntimeModule extends HelperRuntimeModule { + constructor() { + super("make namespace object"); } + /** - * @param {DeserializedType} data data - * @param {Object} context context object - * @returns {SerializedType|Promise} serialized data + * @returns {string} runtime code */ - serialize(data, context) { - const { filename, extension = "" } = context; - return new Promise((resolve, reject) => { - mkdirp(this.fs, dirname(this.fs, filename), err => { - if (err) return reject(err); + generate() { + const { runtimeTemplate } = this.compilation; + const fn = RuntimeGlobals.makeNamespaceObject; + return Template.asString([ + "// define __esModule on exports", + `${fn} = ${runtimeTemplate.basicFunction("exports", [ + "if(typeof Symbol !== 'undefined' && Symbol.toStringTag) {", + Template.indent([ + "Object.defineProperty(exports, Symbol.toStringTag, { value: 'Module' });" + ]), + "}", + "Object.defineProperty(exports, '__esModule', { value: true });" + ])};` + ]); + } +} - // It's important that we don't touch existing files during serialization - // because serialize may read existing files (when deserializing) - const allWrittenFiles = new Set(); - const writeFile = async (name, content) => { - const file = name - ? join(this.fs, filename, `../${name}${extension}`) - : filename; - await new Promise((resolve, reject) => { - let stream = this.fs.createWriteStream(file + "_"); - let compression; - if (file.endsWith(".gz")) { - compression = createGzip({ - chunkSize: COMPRESSION_CHUNK_SIZE, - level: zConstants.Z_BEST_SPEED - }); - } else if (file.endsWith(".br")) { - compression = createBrotliCompress({ - chunkSize: COMPRESSION_CHUNK_SIZE, - params: { - [zConstants.BROTLI_PARAM_MODE]: zConstants.BROTLI_MODE_TEXT, - [zConstants.BROTLI_PARAM_QUALITY]: 2, - [zConstants.BROTLI_PARAM_DISABLE_LITERAL_CONTEXT_MODELING]: true, - [zConstants.BROTLI_PARAM_SIZE_HINT]: content.reduce( - (size, b) => size + b.length, - 0 - ) - } - }); - } - if (compression) { - pipeline(compression, stream, reject); - stream = compression; - stream.on("finish", () => resolve()); - } else { - stream.on("error", err => reject(err)); - stream.on("finish", () => resolve()); - } - for (const b of content) stream.write(b); - stream.end(); - }); - if (name) allWrittenFiles.add(file); - }; +module.exports = MakeNamespaceObjectRuntimeModule; - resolve( - serialize(this, data, false, writeFile, this._hashFunction).then( - async ({ backgroundJob }) => { - await backgroundJob; - // Rename the index file to disallow access during inconsistent file state - await new Promise(resolve => - this.fs.rename(filename, filename + ".old", err => { - resolve(); - }) - ); +/***/ }), - // update all written files - await Promise.all( - Array.from( - allWrittenFiles, - file => - new Promise((resolve, reject) => { - this.fs.rename(file + "_", file, err => { - if (err) return reject(err); - resolve(); - }); - }) - ) - ); +/***/ 92794: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - // As final step automatically update the index file to have a consistent pack again - await new Promise(resolve => { - this.fs.rename(filename + "_", filename, err => { - if (err) return reject(err); - resolve(); - }); - }); - return /** @type {true} */ (true); - } - ) - ); - }); - }); +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php +*/ + + + +const RuntimeGlobals = __webpack_require__(49404); +const RuntimeModule = __webpack_require__(61439); +const Template = __webpack_require__(92066); + +class OnChunksLoadedRuntimeModule extends RuntimeModule { + constructor() { + super("chunk loaded"); } /** - * @param {SerializedType} data data - * @param {Object} context context object - * @returns {DeserializedType|Promise} deserialized data + * @returns {string} runtime code */ - deserialize(data, context) { - const { filename, extension = "" } = context; - const readFile = name => - new Promise((resolve, reject) => { - const file = name - ? join(this.fs, filename, `../${name}${extension}`) - : filename; - this.fs.stat(file, (err, stats) => { - if (err) { - reject(err); - return; - } - let remaining = /** @type {number} */ (stats.size); - let currentBuffer; - let currentBufferUsed; - const buf = []; - let decompression; - if (file.endsWith(".gz")) { - decompression = createGunzip({ - chunkSize: DECOMPRESSION_CHUNK_SIZE - }); - } else if (file.endsWith(".br")) { - decompression = createBrotliDecompress({ - chunkSize: DECOMPRESSION_CHUNK_SIZE - }); - } - if (decompression) { - let newResolve, newReject; - resolve( - Promise.all([ - new Promise((rs, rj) => { - newResolve = rs; - newReject = rj; - }), - new Promise((resolve, reject) => { - decompression.on("data", chunk => buf.push(chunk)); - decompression.on("end", () => resolve()); - decompression.on("error", err => reject(err)); - }) - ]).then(() => buf) - ); - resolve = newResolve; - reject = newReject; - } - this.fs.open(file, "r", (err, fd) => { - if (err) { - reject(err); - return; - } - const read = () => { - if (currentBuffer === undefined) { - currentBuffer = Buffer.allocUnsafeSlow( - Math.min( - constants.MAX_LENGTH, - remaining, - decompression ? DECOMPRESSION_CHUNK_SIZE : Infinity - ) - ); - currentBufferUsed = 0; - } - let readBuffer = currentBuffer; - let readOffset = currentBufferUsed; - let readLength = currentBuffer.length - currentBufferUsed; - // values passed to fs.read must be valid int32 values - if (readOffset > 0x7fffffff) { - readBuffer = currentBuffer.slice(readOffset); - readOffset = 0; - } - if (readLength > 0x7fffffff) { - readLength = 0x7fffffff; - } - this.fs.read( - fd, - readBuffer, - readOffset, - readLength, - null, - (err, bytesRead) => { - if (err) { - this.fs.close(fd, () => { - reject(err); - }); - return; - } - currentBufferUsed += bytesRead; - remaining -= bytesRead; - if (currentBufferUsed === currentBuffer.length) { - if (decompression) { - decompression.write(currentBuffer); - } else { - buf.push(currentBuffer); - } - currentBuffer = undefined; - if (remaining === 0) { - if (decompression) { - decompression.end(); - } - this.fs.close(fd, err => { - if (err) { - reject(err); - return; - } - resolve(buf); - }); - return; - } - } - read(); - } - ); - }; - read(); - }); - }); - }); - return deserialize(this, false, readFile); + generate() { + const { compilation } = this; + const { runtimeTemplate } = compilation; + return Template.asString([ + "var deferred = [];", + `${RuntimeGlobals.onChunksLoaded} = ${runtimeTemplate.basicFunction( + "result, chunkIds, fn, priority", + [ + "if(chunkIds) {", + Template.indent([ + "priority = priority || 0;", + "for(var i = deferred.length; i > 0 && deferred[i - 1][2] > priority; i--) deferred[i] = deferred[i - 1];", + "deferred[i] = [chunkIds, fn, priority];", + "return;" + ]), + "}", + "var notFulfilled = Infinity;", + "for (var i = 0; i < deferred.length; i++) {", + Template.indent([ + runtimeTemplate.destructureArray( + ["chunkIds", "fn", "priority"], + "deferred[i]" + ), + "var fulfilled = true;", + "for (var j = 0; j < chunkIds.length; j++) {", + Template.indent([ + `if ((priority & 1 === 0 || notFulfilled >= priority) && Object.keys(${ + RuntimeGlobals.onChunksLoaded + }).every(${runtimeTemplate.returningFunction( + `${RuntimeGlobals.onChunksLoaded}[key](chunkIds[j])`, + "key" + )})) {`, + Template.indent(["chunkIds.splice(j--, 1);"]), + "} else {", + Template.indent([ + "fulfilled = false;", + "if(priority < notFulfilled) notFulfilled = priority;" + ]), + "}" + ]), + "}", + "if(fulfilled) {", + Template.indent([ + "deferred.splice(i--, 1)", + "var r = fn();", + "if (r !== undefined) result = r;" + ]), + "}" + ]), + "}", + "return result;" + ] + )};` + ]); } } -module.exports = FileMiddleware; +module.exports = OnChunksLoadedRuntimeModule; /***/ }), -/***/ 82547: -/***/ (function(module) { +/***/ 10569: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; /* @@ -114523,37 +113130,36 @@ module.exports = FileMiddleware; -class MapObjectSerializer { - serialize(obj, { write }) { - write(obj.size); - for (const key of obj.keys()) { - write(key); - } - for (const value of obj.values()) { - write(value); - } +const RuntimeGlobals = __webpack_require__(49404); +const RuntimeModule = __webpack_require__(61439); + +class PublicPathRuntimeModule extends RuntimeModule { + constructor(publicPath) { + super("publicPath", RuntimeModule.STAGE_BASIC); + this.publicPath = publicPath; } - deserialize({ read }) { - let size = read(); - const map = new Map(); - const keys = []; - for (let i = 0; i < size; i++) { - keys.push(read()); - } - for (let i = 0; i < size; i++) { - map.set(keys[i], read()); - } - return map; + + /** + * @returns {string} runtime code + */ + generate() { + const { compilation, publicPath } = this; + + return `${RuntimeGlobals.publicPath} = ${JSON.stringify( + compilation.getPath(publicPath || "", { + hash: compilation.hash || "XXXX" + }) + )};`; } } -module.exports = MapObjectSerializer; +module.exports = PublicPathRuntimeModule; /***/ }), -/***/ 52985: -/***/ (function(module) { +/***/ 68642: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; /* @@ -114562,39 +113168,47 @@ module.exports = MapObjectSerializer; -class NullPrototypeObjectSerializer { - serialize(obj, { write }) { - const keys = Object.keys(obj); - for (const key of keys) { - write(key); - } - write(null); - for (const key of keys) { - write(obj[key]); - } +const RuntimeGlobals = __webpack_require__(49404); +const Template = __webpack_require__(92066); +const HelperRuntimeModule = __webpack_require__(22970); + +class RelativeUrlRuntimeModule extends HelperRuntimeModule { + constructor() { + super("relative url"); } - deserialize({ read }) { - const obj = Object.create(null); - const keys = []; - let key = read(); - while (key !== null) { - keys.push(key); - key = read(); - } - for (const key of keys) { - obj[key] = read(); - } - return obj; + + /** + * @returns {string} runtime code + */ + generate() { + const { runtimeTemplate } = this.compilation; + return Template.asString([ + `${RuntimeGlobals.relativeUrl} = function RelativeURL(url) {`, + Template.indent([ + 'var realUrl = new URL(url, "x:/");', + "var values = {};", + "for (var key in realUrl) values[key] = realUrl[key];", + "values.href = url;", + 'values.pathname = url.replace(/[?#].*/, "");', + 'values.origin = values.protocol = "";', + `values.toString = values.toJSON = ${runtimeTemplate.returningFunction( + "url" + )};`, + "for (var key in values) Object.defineProperty(this, key, { enumerable: true, configurable: true, value: values[key] });" + ]), + "};", + `${RuntimeGlobals.relativeUrl}.prototype = URL.prototype;` + ]); } } -module.exports = NullPrototypeObjectSerializer; +module.exports = RelativeUrlRuntimeModule; /***/ }), -/***/ 77815: -/***/ (function(module, exports, __webpack_require__) { +/***/ 90984: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; /* @@ -114603,1067 +113217,1466 @@ module.exports = NullPrototypeObjectSerializer; -const createHash = __webpack_require__(24123); -const ArraySerializer = __webpack_require__(80573); -const DateObjectSerializer = __webpack_require__(32973); -const ErrorObjectSerializer = __webpack_require__(60252); -const MapObjectSerializer = __webpack_require__(82547); -const NullPrototypeObjectSerializer = __webpack_require__(52985); -const PlainObjectSerializer = __webpack_require__(24298); -const RegExpObjectSerializer = __webpack_require__(90410); -const SerializerMiddleware = __webpack_require__(37063); -const SetObjectSerializer = __webpack_require__(85199); - -/** @typedef {typeof import("../util/Hash")} Hash */ -/** @typedef {import("./types").ComplexSerializableType} ComplexSerializableType */ -/** @typedef {import("./types").PrimitiveSerializableType} PrimitiveSerializableType */ +const RuntimeGlobals = __webpack_require__(49404); +const RuntimeModule = __webpack_require__(61439); -/** @typedef {new (...params: any[]) => any} Constructor */ +class RuntimeIdRuntimeModule extends RuntimeModule { + constructor() { + super("runtimeId"); + } -/* + /** + * @returns {string} runtime code + */ + generate() { + const { chunkGraph, chunk } = this; + const runtime = chunk.runtime; + if (typeof runtime !== "string") + throw new Error("RuntimeIdRuntimeModule must be in a single runtime"); + const id = chunkGraph.getRuntimeId(runtime); + return `${RuntimeGlobals.runtimeId} = ${JSON.stringify(id)};`; + } +} -Format: +module.exports = RuntimeIdRuntimeModule; -File -> Section* -Section -> ObjectSection | ReferenceSection | EscapeSection | OtherSection -ObjectSection -> ESCAPE ( - number:relativeOffset (number > 0) | - string:request (string|null):export -) Section:value* ESCAPE ESCAPE_END_OBJECT -ReferenceSection -> ESCAPE number:relativeOffset (number < 0) -EscapeSection -> ESCAPE ESCAPE_ESCAPE_VALUE (escaped value ESCAPE) -EscapeSection -> ESCAPE ESCAPE_UNDEFINED (escaped value ESCAPE) -OtherSection -> any (except ESCAPE) +/***/ }), -Why using null as escape value? -Multiple null values can merged by the BinaryMiddleware, which makes it very efficient -Technically any value can be used. +/***/ 23613: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php */ -/** - * @typedef {Object} ObjectSerializerContext - * @property {function(any): void} write - */ -/** - * @typedef {Object} ObjectDeserializerContext - * @property {function(): any} read - */ -/** - * @typedef {Object} ObjectSerializer - * @property {function(any, ObjectSerializerContext): void} serialize - * @property {function(ObjectDeserializerContext): any} deserialize - */ +const RuntimeGlobals = __webpack_require__(49404); +const StartupChunkDependenciesRuntimeModule = __webpack_require__(7902); +const StartupEntrypointRuntimeModule = __webpack_require__(53372); -const setSetSize = (set, size) => { - let i = 0; - for (const item of set) { - if (i++ >= size) { - set.delete(item); - } - } -}; +/** @typedef {import("../Compiler")} Compiler */ -const setMapSize = (map, size) => { - let i = 0; - for (const item of map.keys()) { - if (i++ >= size) { - map.delete(item); - } +class StartupChunkDependenciesPlugin { + constructor(options) { + this.chunkLoading = options.chunkLoading; + this.asyncChunkLoading = + typeof options.asyncChunkLoading === "boolean" + ? options.asyncChunkLoading + : true; } -}; - -/** - * @param {Buffer} buffer buffer - * @param {string | Hash} hashFunction hash function to use - * @returns {string} hash - */ -const toHash = (buffer, hashFunction) => { - const hash = createHash(hashFunction); - hash.update(buffer); - return /** @type {string} */ (hash.digest("latin1")); -}; - -const ESCAPE = null; -const ESCAPE_ESCAPE_VALUE = null; -const ESCAPE_END_OBJECT = true; -const ESCAPE_UNDEFINED = false; -const CURRENT_VERSION = 2; + /** + * Apply the plugin + * @param {Compiler} compiler the compiler instance + * @returns {void} + */ + apply(compiler) { + compiler.hooks.thisCompilation.tap( + "StartupChunkDependenciesPlugin", + compilation => { + const globalChunkLoading = compilation.outputOptions.chunkLoading; + const isEnabledForChunk = chunk => { + const options = chunk.getEntryOptions(); + const chunkLoading = + options && options.chunkLoading !== undefined + ? options.chunkLoading + : globalChunkLoading; + return chunkLoading === this.chunkLoading; + }; + compilation.hooks.additionalTreeRuntimeRequirements.tap( + "StartupChunkDependenciesPlugin", + (chunk, set, { chunkGraph }) => { + if (!isEnabledForChunk(chunk)) return; + if (chunkGraph.hasChunkEntryDependentChunks(chunk)) { + set.add(RuntimeGlobals.startup); + set.add(RuntimeGlobals.ensureChunk); + set.add(RuntimeGlobals.ensureChunkIncludeEntries); + compilation.addRuntimeModule( + chunk, + new StartupChunkDependenciesRuntimeModule( + this.asyncChunkLoading + ) + ); + } + } + ); + compilation.hooks.runtimeRequirementInTree + .for(RuntimeGlobals.startupEntrypoint) + .tap("StartupChunkDependenciesPlugin", (chunk, set) => { + if (!isEnabledForChunk(chunk)) return; + set.add(RuntimeGlobals.require); + set.add(RuntimeGlobals.ensureChunk); + set.add(RuntimeGlobals.ensureChunkIncludeEntries); + compilation.addRuntimeModule( + chunk, + new StartupEntrypointRuntimeModule(this.asyncChunkLoading) + ); + }); + } + ); + } +} -const serializers = new Map(); -const serializerInversed = new Map(); +module.exports = StartupChunkDependenciesPlugin; -const loadedRequests = new Set(); -const NOT_SERIALIZABLE = {}; +/***/ }), -const jsTypes = new Map(); -jsTypes.set(Object, new PlainObjectSerializer()); -jsTypes.set(Array, new ArraySerializer()); -jsTypes.set(null, new NullPrototypeObjectSerializer()); -jsTypes.set(Map, new MapObjectSerializer()); -jsTypes.set(Set, new SetObjectSerializer()); -jsTypes.set(Date, new DateObjectSerializer()); -jsTypes.set(RegExp, new RegExpObjectSerializer()); -jsTypes.set(Error, new ErrorObjectSerializer(Error)); -jsTypes.set(EvalError, new ErrorObjectSerializer(EvalError)); -jsTypes.set(RangeError, new ErrorObjectSerializer(RangeError)); -jsTypes.set(ReferenceError, new ErrorObjectSerializer(ReferenceError)); -jsTypes.set(SyntaxError, new ErrorObjectSerializer(SyntaxError)); -jsTypes.set(TypeError, new ErrorObjectSerializer(TypeError)); +/***/ 7902: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { -// If in a sandboxed environment (e. g. jest), this escapes the sandbox and registers -// real Object and Array types to. These types may occur in the wild too, e. g. when -// using Structured Clone in postMessage. -if (exports.constructor !== Object) { - const Obj = /** @type {typeof Object} */ (exports.constructor); - const Fn = /** @type {typeof Function} */ (Obj.constructor); - for (const [type, config] of Array.from(jsTypes)) { - if (type) { - const Type = new Fn(`return ${type.name};`)(); - jsTypes.set(Type, config); - } - } -} +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ -{ - let i = 1; - for (const [type, serializer] of jsTypes) { - serializers.set(type, { - request: "", - name: i++, - serializer - }); - } -} -for (const { request, name, serializer } of serializers.values()) { - serializerInversed.set(`${request}/${name}`, serializer); -} -/** @type {Map boolean>} */ -const loaders = new Map(); +const RuntimeGlobals = __webpack_require__(49404); +const RuntimeModule = __webpack_require__(61439); +const Template = __webpack_require__(92066); -/** - * @typedef {ComplexSerializableType[]} DeserializedType - * @typedef {PrimitiveSerializableType[]} SerializedType - * @extends {SerializerMiddleware} - */ -class ObjectMiddleware extends SerializerMiddleware { - /** - * @param {function(any): void} extendContext context extensions - * @param {string | Hash} hashFunction hash function to use - */ - constructor(extendContext, hashFunction = "md4") { - super(); - this.extendContext = extendContext; - this._hashFunction = hashFunction; - } - /** - * @param {RegExp} regExp RegExp for which the request is tested - * @param {function(string): boolean} loader loader to load the request, returns true when successful - * @returns {void} - */ - static registerLoader(regExp, loader) { - loaders.set(regExp, loader); +class StartupChunkDependenciesRuntimeModule extends RuntimeModule { + constructor(asyncChunkLoading) { + super("startup chunk dependencies", RuntimeModule.STAGE_TRIGGER); + this.asyncChunkLoading = asyncChunkLoading; } /** - * @param {Constructor} Constructor the constructor - * @param {string} request the request which will be required when deserializing - * @param {string} name the name to make multiple serializer unique when sharing a request - * @param {ObjectSerializer} serializer the serializer - * @returns {void} + * @returns {string} runtime code */ - static register(Constructor, request, name, serializer) { - const key = request + "/" + name; - - if (serializers.has(Constructor)) { - throw new Error( - `ObjectMiddleware.register: serializer for ${Constructor.name} is already registered` - ); - } - - if (serializerInversed.has(key)) { - throw new Error( - `ObjectMiddleware.register: serializer for ${key} is already registered` - ); - } - - serializers.set(Constructor, { - request, - name, - serializer + generate() { + const { chunkGraph, chunk, compilation } = this; + const { runtimeTemplate } = compilation; + const chunkIds = Array.from( + chunkGraph.getChunkEntryDependentChunksIterable(chunk) + ).map(chunk => { + return chunk.id; }); - - serializerInversed.set(key, serializer); + return Template.asString([ + `var next = ${RuntimeGlobals.startup};`, + `${RuntimeGlobals.startup} = ${runtimeTemplate.basicFunction( + "", + !this.asyncChunkLoading + ? chunkIds + .map( + id => `${RuntimeGlobals.ensureChunk}(${JSON.stringify(id)});` + ) + .concat("return next();") + : chunkIds.length === 1 + ? `return ${RuntimeGlobals.ensureChunk}(${JSON.stringify( + chunkIds[0] + )}).then(next);` + : chunkIds.length > 2 + ? [ + // using map is shorter for 3 or more chunks + `return Promise.all(${JSON.stringify(chunkIds)}.map(${ + RuntimeGlobals.ensureChunk + }, __webpack_require__)).then(next);` + ] + : [ + // calling ensureChunk directly is shorter for 0 - 2 chunks + "return Promise.all([", + Template.indent( + chunkIds + .map( + id => `${RuntimeGlobals.ensureChunk}(${JSON.stringify(id)})` + ) + .join(",\n") + ), + "]).then(next);" + ] + )};` + ]); } +} - /** - * @param {Constructor} Constructor the constructor - * @returns {void} - */ - static registerNotSerializable(Constructor) { - if (serializers.has(Constructor)) { - throw new Error( - `ObjectMiddleware.registerNotSerializable: serializer for ${Constructor.name} is already registered` - ); - } +module.exports = StartupChunkDependenciesRuntimeModule; - serializers.set(Constructor, NOT_SERIALIZABLE); - } - static getSerializerFor(object) { - const proto = Object.getPrototypeOf(object); - let c; - if (proto === null) { - // Object created with Object.create(null) - c = null; - } else { - c = proto.constructor; - if (!c) { - throw new Error( - "Serialization of objects with prototype without valid constructor property not possible" - ); - } - } - const config = serializers.get(c); +/***/ }), - if (!config) throw new Error(`No serializer registered for ${c.name}`); - if (config === NOT_SERIALIZABLE) throw NOT_SERIALIZABLE; +/***/ 53372: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php +*/ - return config; - } - static getDeserializerFor(request, name) { - const key = request + "/" + name; - const serializer = serializerInversed.get(key); - if (serializer === undefined) { - throw new Error(`No deserializer registered for ${key}`); - } +const RuntimeGlobals = __webpack_require__(49404); +const RuntimeModule = __webpack_require__(61439); - return serializer; - } +/** @typedef {import("../MainTemplate")} MainTemplate */ - static _getDeserializerForWithoutError(request, name) { - const key = request + "/" + name; - const serializer = serializerInversed.get(key); - return serializer; +class StartupEntrypointRuntimeModule extends RuntimeModule { + constructor(asyncChunkLoading) { + super("startup entrypoint"); + this.asyncChunkLoading = asyncChunkLoading; } /** - * @param {DeserializedType} data data - * @param {Object} context context object - * @returns {SerializedType|Promise} serialized data + * @returns {string} runtime code */ - serialize(data, context) { - /** @type {any[]} */ - let result = [CURRENT_VERSION]; - let currentPos = 0; - let referenceable = new Map(); - const addReferenceable = item => { - referenceable.set(item, currentPos++); - }; - let bufferDedupeMap = new Map(); - const dedupeBuffer = buf => { - const len = buf.length; - const entry = bufferDedupeMap.get(len); - if (entry === undefined) { - bufferDedupeMap.set(len, buf); - return buf; - } - if (Buffer.isBuffer(entry)) { - if (len < 32) { - if (buf.equals(entry)) { - return entry; - } - bufferDedupeMap.set(len, [entry, buf]); - return buf; - } else { - const hash = toHash(entry, this._hashFunction); - const newMap = new Map(); - newMap.set(hash, entry); - bufferDedupeMap.set(len, newMap); - const hashBuf = toHash(buf, this._hashFunction); - if (hash === hashBuf) { - return entry; - } - return buf; - } - } else if (Array.isArray(entry)) { - if (entry.length < 16) { - for (const item of entry) { - if (buf.equals(item)) { - return item; - } - } - entry.push(buf); - return buf; - } else { - const newMap = new Map(); - const hash = toHash(buf, this._hashFunction); - let found; - for (const item of entry) { - const itemHash = toHash(item, this._hashFunction); - newMap.set(itemHash, item); - if (found === undefined && itemHash === hash) found = item; - } - bufferDedupeMap.set(len, newMap); - if (found === undefined) { - newMap.set(hash, buf); - return buf; - } else { - return found; - } - } - } else { - const hash = toHash(buf, this._hashFunction); - const item = entry.get(hash); - if (item !== undefined) { - return item; - } - entry.set(hash, buf); - return buf; - } - }; - let currentPosTypeLookup = 0; - let objectTypeLookup = new Map(); - const cycleStack = new Set(); - const stackToString = item => { - const arr = Array.from(cycleStack); - arr.push(item); - return arr - .map(item => { - if (typeof item === "string") { - if (item.length > 100) { - return `String ${JSON.stringify(item.slice(0, 100)).slice( - 0, - -1 - )}..."`; - } - return `String ${JSON.stringify(item)}`; - } - try { - const { request, name } = ObjectMiddleware.getSerializerFor(item); - if (request) { - return `${request}${name ? `.${name}` : ""}`; - } - } catch (e) { - // ignore -> fallback - } - if (typeof item === "object" && item !== null) { - if (item.constructor) { - if (item.constructor === Object) - return `Object { ${Object.keys(item).join(", ")} }`; - if (item.constructor === Map) return `Map { ${item.size} items }`; - if (item.constructor === Array) - return `Array { ${item.length} items }`; - if (item.constructor === Set) return `Set { ${item.size} items }`; - if (item.constructor === RegExp) return item.toString(); - return `${item.constructor.name}`; - } - return `Object [null prototype] { ${Object.keys(item).join( - ", " - )} }`; - } - try { - return `${item}`; - } catch (e) { - return `(${e.message})`; - } - }) - .join(" -> "); - }; - let hasDebugInfoAttached; - let ctx = { - write(value, key) { - try { - process(value); - } catch (e) { - if (e !== NOT_SERIALIZABLE) { - if (hasDebugInfoAttached === undefined) - hasDebugInfoAttached = new WeakSet(); - if (!hasDebugInfoAttached.has(e)) { - e.message += `\nwhile serializing ${stackToString(value)}`; - hasDebugInfoAttached.add(e); - } - } - throw e; - } - }, - setCircularReference(ref) { - addReferenceable(ref); - }, - snapshot() { - return { - length: result.length, - cycleStackSize: cycleStack.size, - referenceableSize: referenceable.size, - currentPos, - objectTypeLookupSize: objectTypeLookup.size, - currentPosTypeLookup - }; - }, - rollback(snapshot) { - result.length = snapshot.length; - setSetSize(cycleStack, snapshot.cycleStackSize); - setMapSize(referenceable, snapshot.referenceableSize); - currentPos = snapshot.currentPos; - setMapSize(objectTypeLookup, snapshot.objectTypeLookupSize); - currentPosTypeLookup = snapshot.currentPosTypeLookup; - }, - ...context - }; - this.extendContext(ctx); - const process = item => { - if (Buffer.isBuffer(item)) { - // check if we can emit a reference - const ref = referenceable.get(item); - if (ref !== undefined) { - result.push(ESCAPE, ref - currentPos); - return; - } - const alreadyUsedBuffer = dedupeBuffer(item); - if (alreadyUsedBuffer !== item) { - const ref = referenceable.get(alreadyUsedBuffer); - if (ref !== undefined) { - referenceable.set(item, ref); - result.push(ESCAPE, ref - currentPos); - return; - } - item = alreadyUsedBuffer; - } - addReferenceable(item); - - result.push(item); - } else if (item === ESCAPE) { - result.push(ESCAPE, ESCAPE_ESCAPE_VALUE); - } else if ( - typeof item === "object" - // We don't have to check for null as ESCAPE is null and this has been checked before - ) { - // check if we can emit a reference - const ref = referenceable.get(item); - if (ref !== undefined) { - result.push(ESCAPE, ref - currentPos); - return; - } - - if (cycleStack.has(item)) { - throw new Error( - `This is a circular references. To serialize circular references use 'setCircularReference' somewhere in the circle during serialize and deserialize.` - ); - } - - const { request, name, serializer } = - ObjectMiddleware.getSerializerFor(item); - const key = `${request}/${name}`; - const lastIndex = objectTypeLookup.get(key); + generate() { + const { compilation } = this; + const { runtimeTemplate } = compilation; + return `${ + RuntimeGlobals.startupEntrypoint + } = ${runtimeTemplate.basicFunction("result, chunkIds, fn", [ + "// arguments: chunkIds, moduleId are deprecated", + "var moduleId = chunkIds;", + `if(!fn) chunkIds = result, fn = ${runtimeTemplate.returningFunction( + `__webpack_require__(${RuntimeGlobals.entryModuleId} = moduleId)` + )};`, + ...(this.asyncChunkLoading + ? [ + `return Promise.all(chunkIds.map(${ + RuntimeGlobals.ensureChunk + }, __webpack_require__)).then(${runtimeTemplate.basicFunction("", [ + "var r = fn();", + "return r === undefined ? result : r;" + ])})` + ] + : [ + `chunkIds.map(${RuntimeGlobals.ensureChunk}, __webpack_require__)`, + "var r = fn();", + "return r === undefined ? result : r;" + ]) + ])}`; + } +} - if (lastIndex === undefined) { - objectTypeLookup.set(key, currentPosTypeLookup++); +module.exports = StartupEntrypointRuntimeModule; - result.push(ESCAPE, request, name); - } else { - result.push(ESCAPE, currentPosTypeLookup - lastIndex); - } - cycleStack.add(item); +/***/ }), - try { - serializer.serialize(item, ctx); - } finally { - cycleStack.delete(item); - } +/***/ 33248: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - result.push(ESCAPE, ESCAPE_END_OBJECT); +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php +*/ - addReferenceable(item); - } else if (typeof item === "string") { - if (item.length > 1) { - // short strings are shorter when not emitting a reference (this saves 1 byte per empty string) - // check if we can emit a reference - const ref = referenceable.get(item); - if (ref !== undefined) { - result.push(ESCAPE, ref - currentPos); - return; - } - addReferenceable(item); - } - if (item.length > 102400 && context.logger) { - context.logger.warn( - `Serializing big strings (${Math.round( - item.length / 1024 - )}kiB) impacts deserialization performance (consider using Buffer instead and decode when needed)` - ); - } - result.push(item); - } else if (typeof item === "function") { - if (!SerializerMiddleware.isLazy(item)) - throw new Error("Unexpected function " + item); - /** @type {SerializedType} */ - const serializedData = - SerializerMiddleware.getLazySerializedValue(item); - if (serializedData !== undefined) { - if (typeof serializedData === "function") { - result.push(serializedData); - } else { - throw new Error("Not implemented"); - } - } else if (SerializerMiddleware.isLazy(item, this)) { - throw new Error("Not implemented"); - } else { - const data = SerializerMiddleware.serializeLazy(item, data => - this.serialize([data], context) - ); - SerializerMiddleware.setLazySerializedValue(item, data); - result.push(data); - } - } else if (item === undefined) { - result.push(ESCAPE, ESCAPE_UNDEFINED); - } else { - result.push(item); - } - }; +const RuntimeGlobals = __webpack_require__(49404); +const RuntimeModule = __webpack_require__(61439); - try { - for (const item of data) { - process(item); - } - return result; - } catch (e) { - if (e === NOT_SERIALIZABLE) return null; +/** @typedef {import("../Compilation")} Compilation */ - throw e; - } finally { - // Get rid of these references to avoid leaking memory - // This happens because the optimized code v8 generates - // is optimized for our "ctx.write" method so it will reference - // it from e. g. Dependency.prototype.serialize -(IC)-> ctx.write - data = - result = - referenceable = - bufferDedupeMap = - objectTypeLookup = - ctx = - undefined; - } +class SystemContextRuntimeModule extends RuntimeModule { + constructor() { + super("__system_context__"); } /** - * @param {SerializedType} data data - * @param {Object} context context object - * @returns {DeserializedType|Promise} deserialized data + * @returns {string} runtime code */ - deserialize(data, context) { - let currentDataPos = 0; - const read = () => { - if (currentDataPos >= data.length) - throw new Error("Unexpected end of stream"); + generate() { + return `${RuntimeGlobals.systemContext} = __system_context__;`; + } +} - return data[currentDataPos++]; - }; +module.exports = SystemContextRuntimeModule; - if (read() !== CURRENT_VERSION) - throw new Error("Version mismatch, serializer changed"); - let currentPos = 0; - let referenceable = []; - const addReferenceable = item => { - referenceable.push(item); - currentPos++; - }; - let currentPosTypeLookup = 0; - let objectTypeLookup = []; - let result = []; - let ctx = { - read() { - return decodeValue(); - }, - setCircularReference(ref) { - addReferenceable(ref); - }, - ...context - }; - this.extendContext(ctx); - const decodeValue = () => { - const item = read(); +/***/ }), - if (item === ESCAPE) { - const nextItem = read(); +/***/ 71276: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - if (nextItem === ESCAPE_ESCAPE_VALUE) { - return ESCAPE; - } else if (nextItem === ESCAPE_UNDEFINED) { - return undefined; - } else if (nextItem === ESCAPE_END_OBJECT) { - throw new Error( - `Unexpected end of object at position ${currentDataPos - 1}` - ); - } else { - const request = nextItem; - let serializer; +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ - if (typeof request === "number") { - if (request < 0) { - // relative reference - return referenceable[currentPos + request]; - } - serializer = objectTypeLookup[currentPosTypeLookup - request]; - } else { - if (typeof request !== "string") { - throw new Error( - `Unexpected type (${typeof request}) of request ` + - `at position ${currentDataPos - 1}` - ); - } - const name = read(); - serializer = ObjectMiddleware._getDeserializerForWithoutError( - request, - name - ); - if (serializer === undefined) { - if (request && !loadedRequests.has(request)) { - let loaded = false; - for (const [regExp, loader] of loaders) { - if (regExp.test(request)) { - if (loader(request)) { - loaded = true; - break; - } - } - } - if (!loaded) { - require(request); - } +const NormalModule = __webpack_require__(11026); - loadedRequests.add(request); - } +/** @typedef {import("../Compiler")} Compiler */ - serializer = ObjectMiddleware.getDeserializerFor(request, name); - } +// data URL scheme: "data:text/javascript;charset=utf-8;base64,some-string" +// http://www.ietf.org/rfc/rfc2397.txt +const URIRegEx = /^data:([^;,]+)?((?:;[^;,]+)*?)(?:;(base64))?,(.*)$/i; - objectTypeLookup.push(serializer); - currentPosTypeLookup++; - } - try { - const item = serializer.deserialize(ctx); - const end1 = read(); +const decodeDataURI = uri => { + const match = URIRegEx.exec(uri); + if (!match) return null; - if (end1 !== ESCAPE) { - throw new Error("Expected end of object"); + const isBase64 = match[3]; + const body = match[4]; + return isBase64 + ? Buffer.from(body, "base64") + : Buffer.from(decodeURIComponent(body), "ascii"); +}; + +class DataUriPlugin { + /** + * Apply the plugin + * @param {Compiler} compiler the compiler instance + * @returns {void} + */ + apply(compiler) { + compiler.hooks.compilation.tap( + "DataUriPlugin", + (compilation, { normalModuleFactory }) => { + normalModuleFactory.hooks.resolveForScheme + .for("data") + .tap("DataUriPlugin", resourceData => { + const match = URIRegEx.exec(resourceData.resource); + if (match) { + resourceData.data.mimetype = match[1] || ""; + resourceData.data.parameters = match[2] || ""; + resourceData.data.encoding = match[3] || false; + resourceData.data.encodedContent = match[4] || ""; } + }); + NormalModule.getCompilationHooks(compilation) + .readResourceForScheme.for("data") + .tap("DataUriPlugin", resource => decodeDataURI(resource)); + } + ); + } +} - const end2 = read(); +module.exports = DataUriPlugin; - if (end2 !== ESCAPE_END_OBJECT) { - throw new Error("Expected end of object"); - } - addReferenceable(item); +/***/ }), + +/***/ 75275: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ + - return item; - } catch (err) { - // As this is only for error handling, we omit creating a Map for - // faster access to this information, as this would affect performance - // in the good case - let serializerEntry; - for (const entry of serializers) { - if (entry[1].serializer === serializer) { - serializerEntry = entry; - break; - } - } - const name = !serializerEntry - ? "unknown" - : !serializerEntry[1].request - ? serializerEntry[0].name - : serializerEntry[1].name - ? `${serializerEntry[1].request} ${serializerEntry[1].name}` - : serializerEntry[1].request; - err.message += `\n(during deserialization of ${name})`; - throw err; - } - } - } else if (typeof item === "string") { - if (item.length > 1) { - addReferenceable(item); - } - return item; - } else if (Buffer.isBuffer(item)) { - addReferenceable(item); +const { URL, fileURLToPath } = __webpack_require__(78835); +const { NormalModule } = __webpack_require__(48169); - return item; - } else if (typeof item === "function") { - return SerializerMiddleware.deserializeLazy( - item, - data => this.deserialize(data, context)[0] - ); - } else { - return item; - } - }; +/** @typedef {import("../Compiler")} Compiler */ - try { - while (currentDataPos < data.length) { - result.push(decodeValue()); +class FileUriPlugin { + /** + * Apply the plugin + * @param {Compiler} compiler the compiler instance + * @returns {void} + */ + apply(compiler) { + compiler.hooks.compilation.tap( + "FileUriPlugin", + (compilation, { normalModuleFactory }) => { + normalModuleFactory.hooks.resolveForScheme + .for("file") + .tap("FileUriPlugin", resourceData => { + const url = new URL(resourceData.resource); + const path = fileURLToPath(url); + const query = url.search; + const fragment = url.hash; + resourceData.path = path; + resourceData.query = query; + resourceData.fragment = fragment; + resourceData.resource = path + query + fragment; + return true; + }); + const hooks = NormalModule.getCompilationHooks(compilation); + hooks.readResource + .for(undefined) + .tapAsync("FileUriPlugin", (loaderContext, callback) => { + const { resourcePath } = loaderContext; + loaderContext.addDependency(resourcePath); + loaderContext.fs.readFile(resourcePath, callback); + }); } - return result; - } finally { - // Get rid of these references to avoid leaking memory - // This happens because the optimized code v8 generates - // is optimized for our "ctx.read" method so it will reference - // it from e. g. Dependency.prototype.deserialize -(IC)-> ctx.read - result = referenceable = data = objectTypeLookup = ctx = undefined; - } + ); } } -module.exports = ObjectMiddleware; -module.exports.NOT_SERIALIZABLE = NOT_SERIALIZABLE; +module.exports = FileUriPlugin; /***/ }), -/***/ 24298: -/***/ (function(module) { +/***/ 34747: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; /* MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra */ -const cache = new WeakMap(); +const { extname, basename } = __webpack_require__(85622); +const { URL } = __webpack_require__(78835); +const { createGunzip, createBrotliDecompress, createInflate } = __webpack_require__(78761); +const NormalModule = __webpack_require__(11026); +const createSchemaValidation = __webpack_require__(77695); +const createHash = __webpack_require__(24123); +const { mkdirp, dirname, join } = __webpack_require__(93204); +const memoize = __webpack_require__(84297); -class ObjectStructure { - constructor() { - this.keys = undefined; - this.children = undefined; - } +/** @typedef {import("../../declarations/plugins/schemes/HttpUriPlugin").HttpUriPluginOptions} HttpUriPluginOptions */ +/** @typedef {import("../Compiler")} Compiler */ - getKeys(keys) { - if (this.keys === undefined) this.keys = keys; - return this.keys; - } +const getHttp = memoize(() => __webpack_require__(98605)); +const getHttps = memoize(() => __webpack_require__(57211)); - key(key) { - if (this.children === undefined) this.children = new Map(); - const child = this.children.get(key); - if (child !== undefined) return child; - const newChild = new ObjectStructure(); - this.children.set(key, newChild); - return newChild; +/** @type {(() => void)[] | undefined} */ +let inProgressWrite = undefined; + +const validate = createSchemaValidation( + __webpack_require__(87387), + () => __webpack_require__(75110), + { + name: "Http Uri Plugin", + baseDataPath: "options" } -} +); -const getCachedKeys = (keys, cacheAssoc) => { - let root = cache.get(cacheAssoc); - if (root === undefined) { - root = new ObjectStructure(); - cache.set(cacheAssoc, root); +const toSafePath = str => + str + .replace(/^[^a-zA-Z0-9]+|[^a-zA-Z0-9]+$/g, "") + .replace(/[^a-zA-Z0-9._-]+/g, "_"); + +const computeIntegrity = content => { + const hash = createHash("sha512"); + hash.update(content); + const integrity = "sha512-" + hash.digest("base64"); + return integrity; +}; + +const verifyIntegrity = (content, integrity) => { + if (integrity === "ignore") return true; + return computeIntegrity(content) === integrity; +}; + +/** + * @param {string} str input + * @returns {Record} parsed + */ +const parseKeyValuePairs = str => { + /** @type {Record} */ + const result = {}; + for (const item of str.split(",")) { + const i = item.indexOf("="); + if (i >= 0) { + const key = item.slice(0, i).trim(); + const value = item.slice(i + 1).trim(); + result[key] = value; + } else { + const key = item.trim(); + if (!key) continue; + result[key] = key; + } } - let current = root; - for (const key of keys) { - current = current.key(key); + return result; +}; + +const parseCacheControl = (cacheControl, requestTime) => { + // When false resource is not stored in cache + let storeCache = true; + // When false resource is not stored in lockfile cache + let storeLock = true; + // Resource is only revalidated, after that timestamp and when upgrade is chosen + let validUntil = 0; + if (cacheControl) { + const parsed = parseKeyValuePairs(cacheControl); + if (parsed["no-cache"]) storeCache = storeLock = false; + if (parsed["max-age"] && !isNaN(+parsed["max-age"])) { + validUntil = requestTime + +parsed["max-age"] * 1000; + } + if (parsed["must-revalidate"]) validUntil = 0; } - return current.getKeys(keys); + return { + storeLock, + storeCache, + validUntil + }; }; -class PlainObjectSerializer { - serialize(obj, { write }) { - const keys = Object.keys(obj); - if (keys.length > 128) { - // Objects with so many keys are unlikely to share structure - // with other objects - write(keys); - for (const key of keys) { - write(obj[key]); - } - } else if (keys.length > 1) { - write(getCachedKeys(keys, write)); - for (const key of keys) { - write(obj[key]); - } - } else if (keys.length === 1) { - const key = keys[0]; - write(key); - write(obj[key]); - } else { - write(null); +/** + * @typedef {Object} LockfileEntry + * @property {string} resolved + * @property {string} integrity + * @property {string} contentType + */ + +const areLockfileEntriesEqual = (a, b) => { + return ( + a.resolved === b.resolved && + a.integrity === b.integrity && + a.contentType === b.contentType + ); +}; + +const entryToString = entry => { + return `resolved: ${entry.resolved}, integrity: ${entry.integrity}, contentType: ${entry.contentType}`; +}; + +class Lockfile { + constructor() { + this.version = 1; + /** @type {Map} */ + this.entries = new Map(); + } + + static parse(content) { + // TODO handle merge conflicts + const data = JSON.parse(content); + if (data.version !== 1) + throw new Error(`Unsupported lockfile version ${data.version}`); + const lockfile = new Lockfile(); + for (const key of Object.keys(data)) { + if (key === "version") continue; + const entry = data[key]; + lockfile.entries.set( + key, + typeof entry === "string" + ? entry + : { + resolved: key, + ...entry + } + ); } + return lockfile; } - deserialize({ read }) { - const keys = read(); - const obj = {}; - if (Array.isArray(keys)) { - for (const key of keys) { - obj[key] = read(); + + toString() { + let str = "{\n"; + const entries = Array.from(this.entries).sort(([a], [b]) => + a < b ? -1 : 1 + ); + for (const [key, entry] of entries) { + if (typeof entry === "string") { + str += ` ${JSON.stringify(key)}: ${JSON.stringify(entry)},\n`; + } else { + str += ` ${JSON.stringify(key)}: { `; + if (entry.resolved !== key) + str += `"resolved": ${JSON.stringify(entry.resolved)}, `; + str += `"integrity": ${JSON.stringify( + entry.integrity + )}, "contentType": ${JSON.stringify(entry.contentType)} },\n`; } - } else if (keys !== null) { - obj[keys] = read(); } - return obj; + str += ` "version": ${this.version}\n}\n`; + return str; } } -module.exports = PlainObjectSerializer; +/** + * @template R + * @param {function(function(Error=, R=): void): void} fn function + * @returns {function(function(Error=, R=): void): void} cached function + */ +const cachedWithoutKey = fn => { + let inFlight = false; + /** @type {Error | undefined} */ + let cachedError = undefined; + /** @type {R | undefined} */ + let cachedResult = undefined; + /** @type {(function(Error=, R=): void)[] | undefined} */ + let cachedCallbacks = undefined; + return callback => { + if (inFlight) { + if (cachedResult !== undefined) return callback(null, cachedResult); + if (cachedError !== undefined) return callback(cachedError); + if (cachedCallbacks === undefined) cachedCallbacks = [callback]; + else cachedCallbacks.push(callback); + return; + } + inFlight = true; + fn((err, result) => { + if (err) cachedError = err; + else cachedResult = result; + const callbacks = cachedCallbacks; + cachedCallbacks = undefined; + callback(err, result); + if (callbacks !== undefined) for (const cb of callbacks) cb(err, result); + }); + }; +}; + +/** + * @template T + * @template R + * @param {function(T, function(Error=, R=): void): void} fn function + * @param {function(T, function(Error=, R=): void): void=} forceFn function for the second try + * @returns {(function(T, function(Error=, R=): void): void) & { force: function(T, function(Error=, R=): void): void }} cached function + */ +const cachedWithKey = (fn, forceFn = fn) => { + /** @typedef {{ result?: R, error?: Error, callbacks?: (function(Error=, R=): void)[], force?: true }} CacheEntry */ + /** @type {Map} */ + const cache = new Map(); + const resultFn = (arg, callback) => { + const cacheEntry = cache.get(arg); + if (cacheEntry !== undefined) { + if (cacheEntry.result !== undefined) + return callback(null, cacheEntry.result); + if (cacheEntry.error !== undefined) return callback(cacheEntry.error); + if (cacheEntry.callbacks === undefined) cacheEntry.callbacks = [callback]; + else cacheEntry.callbacks.push(callback); + return; + } + /** @type {CacheEntry} */ + const newCacheEntry = { + result: undefined, + error: undefined, + callbacks: undefined + }; + cache.set(arg, newCacheEntry); + fn(arg, (err, result) => { + if (err) newCacheEntry.error = err; + else newCacheEntry.result = result; + const callbacks = newCacheEntry.callbacks; + newCacheEntry.callbacks = undefined; + callback(err, result); + if (callbacks !== undefined) for (const cb of callbacks) cb(err, result); + }); + }; + resultFn.force = (arg, callback) => { + const cacheEntry = cache.get(arg); + if (cacheEntry !== undefined && cacheEntry.force) { + if (cacheEntry.result !== undefined) + return callback(null, cacheEntry.result); + if (cacheEntry.error !== undefined) return callback(cacheEntry.error); + if (cacheEntry.callbacks === undefined) cacheEntry.callbacks = [callback]; + else cacheEntry.callbacks.push(callback); + return; + } + /** @type {CacheEntry} */ + const newCacheEntry = { + result: undefined, + error: undefined, + callbacks: undefined, + force: true + }; + cache.set(arg, newCacheEntry); + forceFn(arg, (err, result) => { + if (err) newCacheEntry.error = err; + else newCacheEntry.result = result; + const callbacks = newCacheEntry.callbacks; + newCacheEntry.callbacks = undefined; + callback(err, result); + if (callbacks !== undefined) for (const cb of callbacks) cb(err, result); + }); + }; + return resultFn; +}; + +class HttpUriPlugin { + /** + * @param {HttpUriPluginOptions} options options + */ + constructor(options) { + validate(options); + this._lockfileLocation = options.lockfileLocation; + this._cacheLocation = options.cacheLocation; + this._upgrade = options.upgrade; + this._frozen = options.frozen; + this._allowedUris = options.allowedUris; + } + + /** + * Apply the plugin + * @param {Compiler} compiler the compiler instance + * @returns {void} + */ + apply(compiler) { + const schemes = [ + { + scheme: "http", + fetch: (url, options, callback) => getHttp().get(url, options, callback) + }, + { + scheme: "https", + fetch: (url, options, callback) => + getHttps().get(url, options, callback) + } + ]; + let lockfileCache; + compiler.hooks.compilation.tap( + "HttpUriPlugin", + (compilation, { normalModuleFactory }) => { + const intermediateFs = compiler.intermediateFileSystem; + const fs = compilation.inputFileSystem; + const cache = compilation.getCache("webpack.HttpUriPlugin"); + const logger = compilation.getLogger("webpack.HttpUriPlugin"); + const lockfileLocation = + this._lockfileLocation || + join( + intermediateFs, + compiler.context, + compiler.name + ? `${toSafePath(compiler.name)}.webpack.lock` + : "webpack.lock" + ); + const cacheLocation = + this._cacheLocation !== undefined + ? this._cacheLocation + : lockfileLocation + ".data"; + const upgrade = this._upgrade || false; + const frozen = this._frozen || false; + const hashFunction = "sha512"; + const hashDigest = "hex"; + const hashDigestLength = 20; + const allowedUris = this._allowedUris; + + let warnedAboutEol = false; + + const cacheKeyCache = new Map(); + /** + * @param {string} url the url + * @returns {string} the key + */ + const getCacheKey = url => { + const cachedResult = cacheKeyCache.get(url); + if (cachedResult !== undefined) return cachedResult; + const result = _getCacheKey(url); + cacheKeyCache.set(url, result); + return result; + }; + + /** + * @param {string} url the url + * @returns {string} the key + */ + const _getCacheKey = url => { + const parsedUrl = new URL(url); + const folder = toSafePath(parsedUrl.origin); + const name = toSafePath(parsedUrl.pathname); + const query = toSafePath(parsedUrl.search); + let ext = extname(name); + if (ext.length > 20) ext = ""; + const basename = ext ? name.slice(0, -ext.length) : name; + const hash = createHash(hashFunction); + hash.update(url); + const digest = hash.digest(hashDigest).slice(0, hashDigestLength); + return `${folder.slice(-50)}/${`${basename}${ + query ? `_${query}` : "" + }`.slice(0, 150)}_${digest}${ext}`; + }; + + const getLockfile = cachedWithoutKey( + /** + * @param {function(Error=, Lockfile=): void} callback callback + * @returns {void} + */ + callback => { + const readLockfile = () => { + intermediateFs.readFile(lockfileLocation, (err, buffer) => { + if (err && err.code !== "ENOENT") { + compilation.missingDependencies.add(lockfileLocation); + return callback(err); + } + compilation.fileDependencies.add(lockfileLocation); + compilation.fileSystemInfo.createSnapshot( + compiler.fsStartTime, + buffer ? [lockfileLocation] : [], + [], + buffer ? [] : [lockfileLocation], + { timestamp: true }, + (err, snapshot) => { + if (err) return callback(err); + const lockfile = buffer + ? Lockfile.parse(buffer.toString("utf-8")) + : new Lockfile(); + lockfileCache = { + lockfile, + snapshot + }; + callback(null, lockfile); + } + ); + }); + }; + if (lockfileCache) { + compilation.fileSystemInfo.checkSnapshotValid( + lockfileCache.snapshot, + (err, valid) => { + if (err) return callback(err); + if (!valid) return readLockfile(); + callback(null, lockfileCache.lockfile); + } + ); + } else { + readLockfile(); + } + } + ); + /** @type {Map | undefined} */ + let lockfileUpdates = undefined; + const storeLockEntry = (lockfile, url, entry) => { + const oldEntry = lockfile.entries.get(url); + if (lockfileUpdates === undefined) lockfileUpdates = new Map(); + lockfileUpdates.set(url, entry); + lockfile.entries.set(url, entry); + if (!oldEntry) { + logger.log(`${url} added to lockfile`); + } else if (typeof oldEntry === "string") { + if (typeof entry === "string") { + logger.log(`${url} updated in lockfile: ${oldEntry} -> ${entry}`); + } else { + logger.log( + `${url} updated in lockfile: ${oldEntry} -> ${entry.resolved}` + ); + } + } else if (typeof entry === "string") { + logger.log( + `${url} updated in lockfile: ${oldEntry.resolved} -> ${entry}` + ); + } else if (oldEntry.resolved !== entry.resolved) { + logger.log( + `${url} updated in lockfile: ${oldEntry.resolved} -> ${entry.resolved}` + ); + } else if (oldEntry.integrity !== entry.integrity) { + logger.log(`${url} updated in lockfile: content changed`); + } else if (oldEntry.contentType !== entry.contentType) { + logger.log( + `${url} updated in lockfile: ${oldEntry.contentType} -> ${entry.contentType}` + ); + } else { + logger.log(`${url} updated in lockfile`); + } + }; -/***/ }), + const storeResult = (lockfile, url, result, callback) => { + if (result.storeLock) { + storeLockEntry(lockfile, url, result.entry); + if (!cacheLocation || !result.content) + return callback(null, result); + const key = getCacheKey(result.entry.resolved); + const filePath = join(intermediateFs, cacheLocation, key); + mkdirp(intermediateFs, dirname(intermediateFs, filePath), err => { + if (err) return callback(err); + intermediateFs.writeFile(filePath, result.content, err => { + if (err) return callback(err); + callback(null, result); + }); + }); + } else { + storeLockEntry(lockfile, url, "no-cache"); + callback(null, result); + } + }; -/***/ 90410: -/***/ (function(module) { + for (const { scheme, fetch } of schemes) { + /** + * + * @param {string} url URL + * @param {string} integrity integrity + * @param {function(Error=, { entry: LockfileEntry, content: Buffer, storeLock: boolean }=): void} callback callback + */ + const resolveContent = (url, integrity, callback) => { + const handleResult = (err, result) => { + if (err) return callback(err); + if ("location" in result) { + return resolveContent( + result.location, + integrity, + (err, innerResult) => { + if (err) return callback(err); + callback(null, { + entry: innerResult.entry, + content: innerResult.content, + storeLock: innerResult.storeLock && result.storeLock + }); + } + ); + } else { + if ( + !result.fresh && + integrity && + result.entry.integrity !== integrity && + !verifyIntegrity(result.content, integrity) + ) { + return fetchContent.force(url, handleResult); + } + return callback(null, { + entry: result.entry, + content: result.content, + storeLock: result.storeLock + }); + } + }; + fetchContent(url, handleResult); + }; -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php -*/ + /** @typedef {{ storeCache: boolean, storeLock: boolean, validUntil: number, etag: string | undefined, fresh: boolean }} FetchResultMeta */ + /** @typedef {FetchResultMeta & { location: string }} RedirectFetchResult */ + /** @typedef {FetchResultMeta & { entry: LockfileEntry, content: Buffer }} ContentFetchResult */ + /** @typedef {RedirectFetchResult | ContentFetchResult} FetchResult */ + /** + * @param {string} url URL + * @param {FetchResult} cachedResult result from cache + * @param {function(Error=, FetchResult=): void} callback callback + * @returns {void} + */ + const fetchContentRaw = (url, cachedResult, callback) => { + const requestTime = Date.now(); + fetch( + new URL(url), + { + headers: { + "accept-encoding": "gzip, deflate, br", + "user-agent": "webpack", + "if-none-match": cachedResult + ? cachedResult.etag || null + : null + } + }, + res => { + const etag = res.headers["etag"]; + const location = res.headers["location"]; + const cacheControl = res.headers["cache-control"]; + const { storeLock, storeCache, validUntil } = parseCacheControl( + cacheControl, + requestTime + ); + /** + * @param {Partial> & (Pick | Pick)} partialResult result + * @returns {void} + */ + const finishWith = partialResult => { + if ("location" in partialResult) { + logger.debug( + `GET ${url} [${res.statusCode}] -> ${partialResult.location}` + ); + } else { + logger.debug( + `GET ${url} [${res.statusCode}] ${Math.ceil( + partialResult.content.length / 1024 + )} kB${!storeLock ? " no-cache" : ""}` + ); + } + const result = { + ...partialResult, + fresh: true, + storeLock, + storeCache, + validUntil, + etag + }; + if (!storeCache) { + logger.log( + `${url} can't be stored in cache, due to Cache-Control header: ${cacheControl}` + ); + return callback(null, result); + } + cache.store( + url, + null, + { + ...result, + fresh: false + }, + err => { + if (err) { + logger.warn( + `${url} can't be stored in cache: ${err.message}` + ); + logger.debug(err.stack); + } + callback(null, result); + } + ); + }; + if (res.statusCode === 304) { + if ( + cachedResult.validUntil < validUntil || + cachedResult.storeLock !== storeLock || + cachedResult.storeCache !== storeCache || + cachedResult.etag !== etag + ) { + return finishWith(cachedResult); + } else { + logger.debug(`GET ${url} [${res.statusCode}] (unchanged)`); + return callback(null, { + ...cachedResult, + fresh: true + }); + } + } + if ( + location && + res.statusCode >= 301 && + res.statusCode <= 308 + ) { + return finishWith({ + location: new URL(location, url).href + }); + } + const contentType = res.headers["content-type"] || ""; + const bufferArr = []; + const contentEncoding = res.headers["content-encoding"]; + let stream = res; + if (contentEncoding === "gzip") { + stream = stream.pipe(createGunzip()); + } else if (contentEncoding === "br") { + stream = stream.pipe(createBrotliDecompress()); + } else if (contentEncoding === "deflate") { + stream = stream.pipe(createInflate()); + } -class RegExpObjectSerializer { - serialize(obj, { write }) { - write(obj.source); - write(obj.flags); - } - deserialize({ read }) { - return new RegExp(read(), read()); - } -} + stream.on("data", chunk => { + bufferArr.push(chunk); + }); -module.exports = RegExpObjectSerializer; + stream.on("end", () => { + if (!res.complete) { + logger.log(`GET ${url} [${res.statusCode}] (terminated)`); + return callback(new Error(`${url} request was terminated`)); + } + const content = Buffer.concat(bufferArr); -/***/ }), + if (res.statusCode !== 200) { + logger.log(`GET ${url} [${res.statusCode}]`); + return callback( + new Error( + `${url} request status code = ${ + res.statusCode + }\n${content.toString("utf-8")}` + ) + ); + } -/***/ 24754: -/***/ (function(module) { + const integrity = computeIntegrity(content); + const entry = { resolved: url, integrity, contentType }; -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php -*/ + finishWith({ + entry, + content + }); + }); + } + ).on("error", err => { + logger.log(`GET ${url} (error)`); + err.message += `\nwhile fetching ${url}`; + callback(err); + }); + }; + const fetchContent = cachedWithKey( + /** + * @param {string} url URL + * @param {function(Error=, { validUntil: number, etag?: string, entry: LockfileEntry, content: Buffer, fresh: boolean } | { validUntil: number, etag?: string, location: string, fresh: boolean }=): void} callback callback + * @returns {void} + */ (url, callback) => { + cache.get(url, null, (err, cachedResult) => { + if (err) return callback(err); + if (cachedResult) { + const isValid = cachedResult.validUntil >= Date.now(); + if (isValid) return callback(null, cachedResult); + } + fetchContentRaw(url, cachedResult, callback); + }); + }, + (url, callback) => fetchContentRaw(url, undefined, callback) + ); + const isAllowed = uri => { + for (const allowed of allowedUris) { + if (typeof allowed === "string") { + if (uri.startsWith(allowed)) return true; + } else if (typeof allowed === "function") { + if (allowed(uri)) return true; + } else { + if (allowed.test(uri)) return true; + } + } + return false; + }; -class Serializer { - constructor(middlewares, context) { - this.serializeMiddlewares = middlewares.slice(); - this.deserializeMiddlewares = middlewares.slice().reverse(); - this.context = context; - } + const getInfo = cachedWithKey( + /** + * @param {string} url the url + * @param {function(Error=, { entry: LockfileEntry, content: Buffer }=): void} callback callback + * @returns {void} + */ + (url, callback) => { + if (!isAllowed(url)) { + return callback( + new Error( + `${url} doesn't match the allowedUris policy. These URIs are allowed:\n${allowedUris + .map(uri => ` - ${uri}`) + .join("\n")}` + ) + ); + } + getLockfile((err, lockfile) => { + if (err) return callback(err); + const entryOrString = lockfile.entries.get(url); + if (!entryOrString) { + if (frozen) { + return callback( + new Error( + `${url} has no lockfile entry and lockfile is frozen` + ) + ); + } + resolveContent(url, null, (err, result) => { + if (err) return callback(err); + storeResult(lockfile, url, result, callback); + }); + return; + } + if (typeof entryOrString === "string") { + const entryTag = entryOrString; + resolveContent(url, null, (err, result) => { + if (err) return callback(err); + if (!result.storeLock || entryTag === "ignore") + return callback(null, result); + if (frozen) { + return callback( + new Error( + `${url} used to have ${entryTag} lockfile entry and has content now, but lockfile is frozen` + ) + ); + } + if (!upgrade) { + return callback( + new Error( + `${url} used to have ${entryTag} lockfile entry and has content now. +This should be reflected in the lockfile, so this lockfile entry must be upgraded, but upgrading is not enabled. +Remove this line from the lockfile to force upgrading.` + ) + ); + } + storeResult(lockfile, url, result, callback); + }); + return; + } + let entry = entryOrString; + const doFetch = lockedContent => { + resolveContent(url, entry.integrity, (err, result) => { + if (err) { + if (lockedContent) { + logger.warn( + `Upgrade request to ${url} failed: ${err.message}` + ); + logger.debug(err.stack); + return callback(null, { + entry, + content: lockedContent + }); + } + return callback(err); + } + if (!result.storeLock) { + // When the lockfile entry should be no-cache + // we need to update the lockfile + if (frozen) { + return callback( + new Error( + `${url} has a lockfile entry and is no-cache now, but lockfile is frozen\nLockfile: ${entryToString( + entry + )}` + ) + ); + } + storeResult(lockfile, url, result, callback); + return; + } + if (!areLockfileEntriesEqual(result.entry, entry)) { + // When the lockfile entry is outdated + // we need to update the lockfile + if (frozen) { + return callback( + new Error( + `${url} has an outdated lockfile entry, but lockfile is frozen\nLockfile: ${entryToString( + entry + )}\nExpected: ${entryToString(result.entry)}` + ) + ); + } + storeResult(lockfile, url, result, callback); + return; + } + if (!lockedContent && cacheLocation) { + // When the lockfile cache content is missing + // we need to update the lockfile + if (frozen) { + return callback( + new Error( + `${url} is missing content in the lockfile cache, but lockfile is frozen\nLockfile: ${entryToString( + entry + )}` + ) + ); + } + storeResult(lockfile, url, result, callback); + return; + } + return callback(null, result); + }); + }; + if (cacheLocation) { + // When there is a lockfile cache + // we read the content from there + const key = getCacheKey(entry.resolved); + const filePath = join(intermediateFs, cacheLocation, key); + fs.readFile(filePath, (err, result) => { + const content = /** @type {Buffer} */ (result); + if (err) { + if (err.code === "ENOENT") return doFetch(); + return callback(err); + } + const continueWithCachedContent = result => { + if (!upgrade) { + // When not in upgrade mode, we accept the result from the lockfile cache + return callback(null, { entry, content }); + } + return doFetch(content); + }; + if (!verifyIntegrity(content, entry.integrity)) { + let contentWithChangedEol; + let isEolChanged = false; + try { + contentWithChangedEol = Buffer.from( + content.toString("utf-8").replace(/\r\n/g, "\n") + ); + isEolChanged = verifyIntegrity( + contentWithChangedEol, + entry.integrity + ); + } catch (e) { + // ignore + } + if (isEolChanged) { + if (!warnedAboutEol) { + const explainer = `Incorrect end of line sequence was detected in the lockfile cache. +The lockfile cache is protected by integrity checks, so any external modification will lead to a corrupted lockfile cache. +When using git make sure to configure .gitattributes correctly for the lockfile cache: + **/*webpack.lock.data/** -text +This will avoid that the end of line sequence is changed by git on Windows.`; + if (frozen) { + logger.error(explainer); + } else { + logger.warn(explainer); + logger.info( + "Lockfile cache will be automatically fixed now, but when lockfile is frozen this would result in an error." + ); + } + warnedAboutEol = true; + } + if (!frozen) { + // "fix" the end of line sequence of the lockfile content + logger.log( + `${filePath} fixed end of line sequence (\\r\\n instead of \\n).` + ); + intermediateFs.writeFile( + filePath, + contentWithChangedEol, + err => { + if (err) return callback(err); + continueWithCachedContent(contentWithChangedEol); + } + ); + return; + } + } + if (frozen) { + return callback( + new Error( + `${ + entry.resolved + } integrity mismatch, expected content with integrity ${ + entry.integrity + } but got ${computeIntegrity(content)}. +Lockfile corrupted (${ + isEolChanged + ? "end of line sequence was unexpectedly changed" + : "incorrectly merged? changed by other tools?" + }). +Run build with un-frozen lockfile to automatically fix lockfile.` + ) + ); + } else { + // "fix" the lockfile entry to the correct integrity + // the content has priority over the integrity value + entry = { + ...entry, + integrity: computeIntegrity(content) + }; + storeLockEntry(lockfile, url, entry); + } + } + continueWithCachedContent(result); + }); + } else { + doFetch(); + } + }); + } + ); - serialize(obj, context) { - const ctx = { ...context, ...this.context }; - let current = obj; - for (const middleware of this.serializeMiddlewares) { - if (current && typeof current.then === "function") { - current = current.then(data => data && middleware.serialize(data, ctx)); - } else if (current) { - try { - current = middleware.serialize(current, ctx); - } catch (err) { - current = Promise.reject(err); + const respondWithUrlModule = (url, resourceData, callback) => { + getInfo(url.href, (err, result) => { + if (err) return callback(err); + resourceData.resource = url.href; + resourceData.path = url.origin + url.pathname; + resourceData.query = url.search; + resourceData.fragment = url.hash; + resourceData.context = new URL( + ".", + result.entry.resolved + ).href.slice(0, -1); + resourceData.data.mimetype = result.entry.contentType; + callback(null, true); + }); + }; + normalModuleFactory.hooks.resolveForScheme + .for(scheme) + .tapAsync( + "HttpUriPlugin", + (resourceData, resolveData, callback) => { + respondWithUrlModule( + new URL(resourceData.resource), + resourceData, + callback + ); + } + ); + normalModuleFactory.hooks.resolveInScheme + .for(scheme) + .tapAsync("HttpUriPlugin", (resourceData, data, callback) => { + // Only handle relative urls (./xxx, ../xxx, /xxx, //xxx) + if ( + data.dependencyType !== "url" && + !/^\.{0,2}\//.test(resourceData.resource) + ) { + return callback(); + } + respondWithUrlModule( + new URL(resourceData.resource, data.context + "/"), + resourceData, + callback + ); + }); + const hooks = NormalModule.getCompilationHooks(compilation); + hooks.readResourceForScheme + .for(scheme) + .tapAsync("HttpUriPlugin", (resource, module, callback) => { + return getInfo(resource, (err, result) => { + if (err) return callback(err); + module.buildInfo.resourceIntegrity = result.entry.integrity; + callback(null, result.content); + }); + }); + hooks.needBuild.tapAsync( + "HttpUriPlugin", + (module, context, callback) => { + if ( + module.resource && + module.resource.startsWith(`${scheme}://`) + ) { + getInfo(module.resource, (err, result) => { + if (err) return callback(err); + if ( + result.entry.integrity !== + module.buildInfo.resourceIntegrity + ) { + return callback(null, true); + } + callback(); + }); + } else { + return callback(); + } + } + ); } - } else break; - } - return current; - } - - deserialize(value, context) { - const ctx = { ...context, ...this.context }; - /** @type {any} */ - let current = value; - for (const middleware of this.deserializeMiddlewares) { - if (current && typeof current.then === "function") { - current = current.then(data => middleware.deserialize(data, ctx)); - } else { - current = middleware.deserialize(current, ctx); - } - } - return current; - } -} - -module.exports = Serializer; - - -/***/ }), - -/***/ 37063: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php -*/ - - - -const memoize = __webpack_require__(84297); - -const LAZY_TARGET = Symbol("lazy serialization target"); -const LAZY_SERIALIZED_VALUE = Symbol("lazy serialization data"); - -/** - * @template DeserializedType - * @template SerializedType - */ -class SerializerMiddleware { - /* istanbul ignore next */ - /** - * @abstract - * @param {DeserializedType} data data - * @param {Object} context context object - * @returns {SerializedType|Promise} serialized data - */ - serialize(data, context) { - const AbstractMethodError = __webpack_require__(570); - throw new AbstractMethodError(); - } - - /* istanbul ignore next */ - /** - * @abstract - * @param {SerializedType} data data - * @param {Object} context context object - * @returns {DeserializedType|Promise} deserialized data - */ - deserialize(data, context) { - const AbstractMethodError = __webpack_require__(570); - throw new AbstractMethodError(); - } - - /** - * @param {any | function(): Promise | any} value contained value or function to value - * @param {SerializerMiddleware} target target middleware - * @param {object=} options lazy options - * @param {any=} serializedValue serialized value - * @returns {function(): Promise | any} lazy function - */ - static createLazy(value, target, options = {}, serializedValue) { - if (SerializerMiddleware.isLazy(value, target)) return value; - const fn = typeof value === "function" ? value : () => value; - fn[LAZY_TARGET] = target; - /** @type {any} */ (fn).options = options; - fn[LAZY_SERIALIZED_VALUE] = serializedValue; - return fn; - } - - /** - * @param {function(): Promise | any} fn lazy function - * @param {SerializerMiddleware=} target target middleware - * @returns {boolean} true, when fn is a lazy function (optionally of that target) - */ - static isLazy(fn, target) { - if (typeof fn !== "function") return false; - const t = fn[LAZY_TARGET]; - return target ? t === target : !!t; - } - - /** - * @param {function(): Promise | any} fn lazy function - * @returns {object} options - */ - static getLazyOptions(fn) { - if (typeof fn !== "function") return undefined; - return /** @type {any} */ (fn).options; - } - - /** - * @param {function(): Promise | any} fn lazy function - * @returns {any} serialized value - */ - static getLazySerializedValue(fn) { - if (typeof fn !== "function") return undefined; - return fn[LAZY_SERIALIZED_VALUE]; - } - - /** - * @param {function(): Promise | any} fn lazy function - * @param {any} value serialized value - * @returns {void} - */ - static setLazySerializedValue(fn, value) { - fn[LAZY_SERIALIZED_VALUE] = value; - } - - /** - * @param {function(): Promise | any} lazy lazy function - * @param {function(any): Promise | any} serialize serialize function - * @returns {function(): Promise | any} new lazy - */ - static serializeLazy(lazy, serialize) { - const fn = memoize(() => { - const r = lazy(); - if (r && typeof r.then === "function") { - return r.then(data => data && serialize(data)); - } - return serialize(r); - }); - fn[LAZY_TARGET] = lazy[LAZY_TARGET]; - /** @type {any} */ (fn).options = /** @type {any} */ (lazy).options; - lazy[LAZY_SERIALIZED_VALUE] = fn; - return fn; - } + compilation.hooks.finishModules.tapAsync( + "HttpUriPlugin", + (modules, callback) => { + if (!lockfileUpdates) return callback(); + const ext = extname(lockfileLocation); + const tempFile = join( + intermediateFs, + dirname(intermediateFs, lockfileLocation), + `.${basename(lockfileLocation, ext)}.${ + (Math.random() * 10000) | 0 + }${ext}` + ); - /** - * @param {function(): Promise | any} lazy lazy function - * @param {function(any): Promise | any} deserialize deserialize function - * @returns {function(): Promise | any} new lazy - */ - static deserializeLazy(lazy, deserialize) { - const fn = memoize(() => { - const r = lazy(); - if (r && typeof r.then === "function") { - return r.then(data => deserialize(data)); + const writeDone = () => { + const nextOperation = inProgressWrite.shift(); + if (nextOperation) { + nextOperation(); + } else { + inProgressWrite = undefined; + } + }; + const runWrite = () => { + intermediateFs.readFile(lockfileLocation, (err, buffer) => { + if (err && err.code !== "ENOENT") { + writeDone(); + return callback(err); + } + const lockfile = buffer + ? Lockfile.parse(buffer.toString("utf-8")) + : new Lockfile(); + for (const [key, value] of lockfileUpdates) { + lockfile.entries.set(key, value); + } + intermediateFs.writeFile(tempFile, lockfile.toString(), err => { + if (err) { + writeDone(); + return intermediateFs.unlink(tempFile, () => callback(err)); + } + intermediateFs.rename(tempFile, lockfileLocation, err => { + if (err) { + writeDone(); + return intermediateFs.unlink(tempFile, () => + callback(err) + ); + } + writeDone(); + callback(); + }); + }); + }); + }; + if (inProgressWrite) { + inProgressWrite.push(runWrite); + } else { + inProgressWrite = []; + runWrite(); + } + } + ); } - return deserialize(r); - }); - fn[LAZY_TARGET] = lazy[LAZY_TARGET]; - /** @type {any} */ (fn).options = /** @type {any} */ (lazy).options; - fn[LAZY_SERIALIZED_VALUE] = lazy; - return fn; - } - - /** - * @param {function(): Promise | any} lazy lazy function - * @returns {function(): Promise | any} new lazy - */ - static unMemoizeLazy(lazy) { - if (!SerializerMiddleware.isLazy(lazy)) return lazy; - const fn = () => { - throw new Error( - "A lazy value that has been unmemorized can't be called again" - ); - }; - fn[LAZY_SERIALIZED_VALUE] = SerializerMiddleware.unMemoizeLazy( - lazy[LAZY_SERIALIZED_VALUE] ); - fn[LAZY_TARGET] = lazy[LAZY_TARGET]; - fn.options = /** @type {any} */ (lazy).options; - return fn; } } -module.exports = SerializerMiddleware; +module.exports = HttpUriPlugin; /***/ }), -/***/ 85199: +/***/ 80573: /***/ (function(module) { "use strict"; @@ -115673,29 +114686,27 @@ module.exports = SerializerMiddleware; -class SetObjectSerializer { - serialize(obj, { write }) { - write(obj.size); - for (const value of obj) { - write(value); - } +class ArraySerializer { + serialize(array, { write }) { + write(array.length); + for (const item of array) write(item); } deserialize({ read }) { - let size = read(); - const set = new Set(); - for (let i = 0; i < size; i++) { - set.add(read()); + const length = read(); + const array = []; + for (let i = 0; i < length; i++) { + array.push(read()); } - return set; + return array; } } -module.exports = SetObjectSerializer; +module.exports = ArraySerializer; /***/ }), -/***/ 63340: +/***/ 7732: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; @@ -115705,4736 +114716,4532 @@ module.exports = SetObjectSerializer; +const memoize = __webpack_require__(84297); const SerializerMiddleware = __webpack_require__(37063); -/** - * @typedef {any} DeserializedType - * @typedef {any[]} SerializedType - * @extends {SerializerMiddleware} - */ -class SingleItemMiddleware extends SerializerMiddleware { - /** - * @param {DeserializedType} data data - * @param {Object} context context object - * @returns {SerializedType|Promise} serialized data - */ - serialize(data, context) { - return [data]; - } - - /** - * @param {SerializedType} data data - * @param {Object} context context object - * @returns {DeserializedType|Promise} deserialized data - */ - deserialize(data, context) { - return data[0]; - } -} - -module.exports = SingleItemMiddleware; - - -/***/ }), - -/***/ 90489: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { +/** @typedef {import("./types").BufferSerializableType} BufferSerializableType */ +/** @typedef {import("./types").PrimitiveSerializableType} PrimitiveSerializableType */ -"use strict"; /* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ - +Format: +File -> Section* -const ModuleDependency = __webpack_require__(80944); -const makeSerializable = __webpack_require__(26522); +Section -> NullsSection | + BooleansSection | + F64NumbersSection | + I32NumbersSection | + I8NumbersSection | + ShortStringSection | + StringSection | + BufferSection | + NopSection -class ConsumeSharedFallbackDependency extends ModuleDependency { - constructor(request) { - super(request); - } - get type() { - return "consume shared fallback"; - } - get category() { - return "esm"; - } -} +NullsSection -> + NullHeaderByte | Null2HeaderByte | Null3HeaderByte | + Nulls8HeaderByte 0xnn (n:count - 4) | + Nulls32HeaderByte n:ui32 (n:count - 260) | +BooleansSection -> TrueHeaderByte | FalseHeaderByte | BooleansSectionHeaderByte BooleansCountAndBitsByte +F64NumbersSection -> F64NumbersSectionHeaderByte f64* +I32NumbersSection -> I32NumbersSectionHeaderByte i32* +I8NumbersSection -> I8NumbersSectionHeaderByte i8* +ShortStringSection -> ShortStringSectionHeaderByte ascii-byte* +StringSection -> StringSectionHeaderByte i32:length utf8-byte* +BufferSection -> BufferSectionHeaderByte i32:length byte* +NopSection --> NopSectionHeaderByte -makeSerializable( - ConsumeSharedFallbackDependency, - "webpack/lib/sharing/ConsumeSharedFallbackDependency" -); +ShortStringSectionHeaderByte -> 0b1nnn_nnnn (n:length) -module.exports = ConsumeSharedFallbackDependency; +F64NumbersSectionHeaderByte -> 0b001n_nnnn (n:count - 1) +I32NumbersSectionHeaderByte -> 0b010n_nnnn (n:count - 1) +I8NumbersSectionHeaderByte -> 0b011n_nnnn (n:count - 1) +NullsSectionHeaderByte -> 0b0001_nnnn (n:count - 1) +BooleansCountAndBitsByte -> + 0b0000_1xxx (count = 3) | + 0b0001_xxxx (count = 4) | + 0b001x_xxxx (count = 5) | + 0b01xx_xxxx (count = 6) | + 0b1nnn_nnnn (n:count - 7, 7 <= count <= 133) + 0xff n:ui32 (n:count, 134 <= count < 2^32) -/***/ }), +StringSectionHeaderByte -> 0b0000_1110 +BufferSectionHeaderByte -> 0b0000_1111 +NopSectionHeaderByte -> 0b0000_1011 +FalseHeaderByte -> 0b0000_1100 +TrueHeaderByte -> 0b0000_1101 -/***/ 61474: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { +RawNumber -> n (n <= 10) -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra */ +const LAZY_HEADER = 0x0b; +const TRUE_HEADER = 0x0c; +const FALSE_HEADER = 0x0d; +const BOOLEANS_HEADER = 0x0e; +const NULL_HEADER = 0x10; +const NULL2_HEADER = 0x11; +const NULL3_HEADER = 0x12; +const NULLS8_HEADER = 0x13; +const NULLS32_HEADER = 0x14; +const NULL_AND_I8_HEADER = 0x15; +const NULL_AND_I32_HEADER = 0x16; +const NULL_AND_TRUE_HEADER = 0x17; +const NULL_AND_FALSE_HEADER = 0x18; +const STRING_HEADER = 0x1e; +const BUFFER_HEADER = 0x1f; +const I8_HEADER = 0x60; +const I32_HEADER = 0x40; +const F64_HEADER = 0x20; +const SHORT_STRING_HEADER = 0x80; + +/** Uplift high-order bits */ +const NUMBERS_HEADER_MASK = 0xe0; +const NUMBERS_COUNT_MASK = 0x1f; // 0b0001_1111 +const SHORT_STRING_LENGTH_MASK = 0x7f; // 0b0111_1111 + +const HEADER_SIZE = 1; +const I8_SIZE = 1; +const I32_SIZE = 4; +const F64_SIZE = 8; +const MEASURE_START_OPERATION = Symbol("MEASURE_START_OPERATION"); +const MEASURE_END_OPERATION = Symbol("MEASURE_END_OPERATION"); -const { RawSource } = __webpack_require__(96192); -const AsyncDependenciesBlock = __webpack_require__(11315); -const Module = __webpack_require__(85887); -const RuntimeGlobals = __webpack_require__(49404); -const makeSerializable = __webpack_require__(26522); -const { rangeToString, stringifyHoley } = __webpack_require__(60473); -const ConsumeSharedFallbackDependency = __webpack_require__(90489); +/** @typedef {typeof MEASURE_START_OPERATION} MEASURE_START_OPERATION_TYPE */ +/** @typedef {typeof MEASURE_END_OPERATION} MEASURE_END_OPERATION_TYPE */ -/** @typedef {import("../../declarations/WebpackOptions").WebpackOptionsNormalized} WebpackOptions */ -/** @typedef {import("../ChunkGraph")} ChunkGraph */ -/** @typedef {import("../ChunkGroup")} ChunkGroup */ -/** @typedef {import("../Compilation")} Compilation */ -/** @typedef {import("../Dependency").UpdateHashContext} UpdateHashContext */ -/** @typedef {import("../Module").CodeGenerationContext} CodeGenerationContext */ -/** @typedef {import("../Module").CodeGenerationResult} CodeGenerationResult */ -/** @typedef {import("../Module").LibIdentOptions} LibIdentOptions */ -/** @typedef {import("../Module").NeedBuildContext} NeedBuildContext */ -/** @typedef {import("../RequestShortener")} RequestShortener */ -/** @typedef {import("../ResolverFactory").ResolverWithOptions} ResolverWithOptions */ -/** @typedef {import("../WebpackError")} WebpackError */ -/** @typedef {import("../util/Hash")} Hash */ -/** @typedef {import("../util/fs").InputFileSystem} InputFileSystem */ -/** @typedef {import("../util/semver").SemVerRange} SemVerRange */ +const identifyNumber = n => { + if (n === (n | 0)) { + if (n <= 127 && n >= -128) return 0; + if (n <= 2147483647 && n >= -2147483648) return 1; + } + return 2; +}; /** - * @typedef {Object} ConsumeOptions - * @property {string=} import fallback request - * @property {string=} importResolved resolved fallback request - * @property {string} shareKey global share key - * @property {string} shareScope share scope - * @property {SemVerRange | false | undefined} requiredVersion version requirement - * @property {string} packageName package name to determine required version automatically - * @property {boolean} strictVersion don't use shared version even if version isn't valid - * @property {boolean} singleton use single global version - * @property {boolean} eager include the fallback module in a sync way + * @typedef {PrimitiveSerializableType[]} DeserializedType + * @typedef {BufferSerializableType[]} SerializedType + * @extends {SerializerMiddleware} */ - -const TYPES = new Set(["consume-shared"]); - -class ConsumeSharedModule extends Module { +class BinaryMiddleware extends SerializerMiddleware { /** - * @param {string} context context - * @param {ConsumeOptions} options consume options + * @param {DeserializedType} data data + * @param {Object} context context object + * @returns {SerializedType|Promise} serialized data */ - constructor(context, options) { - super("consume-shared-module", context); - this.options = options; + serialize(data, context) { + return this._serialize(data, context); } - /** - * @returns {string} a unique identifier of the module - */ - identifier() { - const { - shareKey, - shareScope, - importResolved, - requiredVersion, - strictVersion, - singleton, - eager - } = this.options; - return `consume-shared-module|${shareScope}|${shareKey}|${ - requiredVersion && rangeToString(requiredVersion) - }|${strictVersion}|${importResolved}|${singleton}|${eager}`; + _serializeLazy(fn, context) { + return SerializerMiddleware.serializeLazy(fn, data => + this._serialize(data, context) + ); } /** - * @param {RequestShortener} requestShortener the request shortener - * @returns {string} a user readable identifier of the module + * @param {DeserializedType} data data + * @param {Object} context context object + * @param {{ leftOverBuffer: Buffer | null, allocationSize: number, increaseCounter: number }} allocationScope allocation scope + * @returns {SerializedType} serialized data */ - readableIdentifier(requestShortener) { - const { - shareKey, - shareScope, - importResolved, - requiredVersion, - strictVersion, - singleton, - eager - } = this.options; - return `consume shared module (${shareScope}) ${shareKey}@${ - requiredVersion ? rangeToString(requiredVersion) : "*" - }${strictVersion ? " (strict)" : ""}${singleton ? " (singleton)" : ""}${ - importResolved - ? ` (fallback: ${requestShortener.shorten(importResolved)})` - : "" - }${eager ? " (eager)" : ""}`; - } + _serialize( + data, + context, + allocationScope = { + allocationSize: 1024, + increaseCounter: 0, + leftOverBuffer: null + } + ) { + /** @type {Buffer} */ + let leftOverBuffer = null; + /** @type {BufferSerializableType[]} */ + let buffers = []; + /** @type {Buffer} */ + let currentBuffer = allocationScope ? allocationScope.leftOverBuffer : null; + allocationScope.leftOverBuffer = null; + let currentPosition = 0; + if (currentBuffer === null) { + currentBuffer = Buffer.allocUnsafe(allocationScope.allocationSize); + } + const allocate = bytesNeeded => { + if (currentBuffer !== null) { + if (currentBuffer.length - currentPosition >= bytesNeeded) return; + flush(); + } + if (leftOverBuffer && leftOverBuffer.length >= bytesNeeded) { + currentBuffer = leftOverBuffer; + leftOverBuffer = null; + } else { + currentBuffer = Buffer.allocUnsafe( + Math.max(bytesNeeded, allocationScope.allocationSize) + ); + if ( + !(allocationScope.increaseCounter = + (allocationScope.increaseCounter + 1) % 4) && + allocationScope.allocationSize < 16777216 + ) { + allocationScope.allocationSize = allocationScope.allocationSize << 1; + } + } + }; + const flush = () => { + if (currentBuffer !== null) { + if (currentPosition > 0) { + buffers.push( + Buffer.from( + currentBuffer.buffer, + currentBuffer.byteOffset, + currentPosition + ) + ); + } + if ( + !leftOverBuffer || + leftOverBuffer.length < currentBuffer.length - currentPosition + ) { + leftOverBuffer = Buffer.from( + currentBuffer.buffer, + currentBuffer.byteOffset + currentPosition, + currentBuffer.byteLength - currentPosition + ); + } - /** - * @param {LibIdentOptions} options options - * @returns {string | null} an identifier for library inclusion - */ - libIdent(options) { - const { shareKey, shareScope, import: request } = this.options; - return `webpack/sharing/consume/${shareScope}/${shareKey}${ - request ? `/${request}` : "" - }`; - } + currentBuffer = null; + currentPosition = 0; + } + }; + const writeU8 = byte => { + currentBuffer.writeUInt8(byte, currentPosition++); + }; + const writeU32 = ui32 => { + currentBuffer.writeUInt32LE(ui32, currentPosition); + currentPosition += 4; + }; + const measureStack = []; + const measureStart = () => { + measureStack.push(buffers.length, currentPosition); + }; + const measureEnd = () => { + const oldPos = measureStack.pop(); + const buffersIndex = measureStack.pop(); + let size = currentPosition - oldPos; + for (let i = buffersIndex; i < buffers.length; i++) { + size += buffers[i].length; + } + return size; + }; + for (let i = 0; i < data.length; i++) { + const thing = data[i]; + switch (typeof thing) { + case "function": { + if (!SerializerMiddleware.isLazy(thing)) + throw new Error("Unexpected function " + thing); + /** @type {SerializedType | (() => SerializedType)} */ + let serializedData = + SerializerMiddleware.getLazySerializedValue(thing); + if (serializedData === undefined) { + if (SerializerMiddleware.isLazy(thing, this)) { + flush(); + allocationScope.leftOverBuffer = leftOverBuffer; + const result = + /** @type {(Exclude>)[]} */ ( + thing() + ); + const data = this._serialize(result, context, allocationScope); + leftOverBuffer = allocationScope.leftOverBuffer; + allocationScope.leftOverBuffer = null; + SerializerMiddleware.setLazySerializedValue(thing, data); + serializedData = data; + } else { + serializedData = this._serializeLazy(thing, context); + flush(); + buffers.push(serializedData); + break; + } + } else { + if (typeof serializedData === "function") { + flush(); + buffers.push(serializedData); + break; + } + } + const lengths = []; + for (const item of serializedData) { + let last; + if (typeof item === "function") { + lengths.push(0); + } else if (item.length === 0) { + // ignore + } else if ( + lengths.length > 0 && + (last = lengths[lengths.length - 1]) !== 0 + ) { + const remaining = 0xffffffff - last; + if (remaining >= item.length) { + lengths[lengths.length - 1] += item.length; + } else { + lengths.push(item.length - remaining); + lengths[lengths.length - 2] = 0xffffffff; + } + } else { + lengths.push(item.length); + } + } + allocate(5 + lengths.length * 4); + writeU8(LAZY_HEADER); + writeU32(lengths.length); + for (const l of lengths) { + writeU32(l); + } + flush(); + for (const item of serializedData) { + buffers.push(item); + } + break; + } + case "string": { + const len = Buffer.byteLength(thing); + if (len >= 128 || len !== thing.length) { + allocate(len + HEADER_SIZE + I32_SIZE); + writeU8(STRING_HEADER); + writeU32(len); + currentBuffer.write(thing, currentPosition); + currentPosition += len; + } else if (len >= 70) { + allocate(len + HEADER_SIZE); + writeU8(SHORT_STRING_HEADER | len); - /** - * @param {NeedBuildContext} context context info - * @param {function(WebpackError=, boolean=): void} callback callback function, returns true, if the module needs a rebuild - * @returns {void} - */ - needBuild(context, callback) { - callback(null, !this.buildInfo); - } + currentBuffer.write(thing, currentPosition, "latin1"); + currentPosition += len; + } else { + allocate(len + HEADER_SIZE); + writeU8(SHORT_STRING_HEADER | len); - /** - * @param {WebpackOptions} options webpack options - * @param {Compilation} compilation the compilation - * @param {ResolverWithOptions} resolver the resolver - * @param {InputFileSystem} fs the file system - * @param {function(WebpackError=): void} callback callback function - * @returns {void} - */ - build(options, compilation, resolver, fs, callback) { - this.buildMeta = {}; - this.buildInfo = {}; - if (this.options.import) { - const dep = new ConsumeSharedFallbackDependency(this.options.import); - if (this.options.eager) { - this.addDependency(dep); - } else { - const block = new AsyncDependenciesBlock({}); - block.addDependency(dep); - this.addBlock(block); + for (let i = 0; i < len; i++) { + currentBuffer[currentPosition++] = thing.charCodeAt(i); + } + } + break; + } + case "number": { + const type = identifyNumber(thing); + if (type === 0 && thing >= 0 && thing <= 10) { + // shortcut for very small numbers + allocate(I8_SIZE); + writeU8(thing); + break; + } + /** + * amount of numbers to write + * @type {number} + */ + let n = 1; + for (; n < 32 && i + n < data.length; n++) { + const item = data[i + n]; + if (typeof item !== "number") break; + if (identifyNumber(item) !== type) break; + } + switch (type) { + case 0: + allocate(HEADER_SIZE + I8_SIZE * n); + writeU8(I8_HEADER | (n - 1)); + while (n > 0) { + currentBuffer.writeInt8( + /** @type {number} */ (data[i]), + currentPosition + ); + currentPosition += I8_SIZE; + n--; + i++; + } + break; + case 1: + allocate(HEADER_SIZE + I32_SIZE * n); + writeU8(I32_HEADER | (n - 1)); + while (n > 0) { + currentBuffer.writeInt32LE( + /** @type {number} */ (data[i]), + currentPosition + ); + currentPosition += I32_SIZE; + n--; + i++; + } + break; + case 2: + allocate(HEADER_SIZE + F64_SIZE * n); + writeU8(F64_HEADER | (n - 1)); + while (n > 0) { + currentBuffer.writeDoubleLE( + /** @type {number} */ (data[i]), + currentPosition + ); + currentPosition += F64_SIZE; + n--; + i++; + } + break; + } + + i--; + break; + } + case "boolean": { + let lastByte = thing === true ? 1 : 0; + const bytes = []; + let count = 1; + let n; + for (n = 1; n < 0xffffffff && i + n < data.length; n++) { + const item = data[i + n]; + if (typeof item !== "boolean") break; + const pos = count & 0x7; + if (pos === 0) { + bytes.push(lastByte); + lastByte = item === true ? 1 : 0; + } else if (item === true) { + lastByte |= 1 << pos; + } + count++; + } + i += count - 1; + if (count === 1) { + allocate(HEADER_SIZE); + writeU8(lastByte === 1 ? TRUE_HEADER : FALSE_HEADER); + } else if (count === 2) { + allocate(HEADER_SIZE * 2); + writeU8(lastByte & 1 ? TRUE_HEADER : FALSE_HEADER); + writeU8(lastByte & 2 ? TRUE_HEADER : FALSE_HEADER); + } else if (count <= 6) { + allocate(HEADER_SIZE + I8_SIZE); + writeU8(BOOLEANS_HEADER); + writeU8((1 << count) | lastByte); + } else if (count <= 133) { + allocate(HEADER_SIZE + I8_SIZE + I8_SIZE * bytes.length + I8_SIZE); + writeU8(BOOLEANS_HEADER); + writeU8(0x80 | (count - 7)); + for (const byte of bytes) writeU8(byte); + writeU8(lastByte); + } else { + allocate( + HEADER_SIZE + + I8_SIZE + + I32_SIZE + + I8_SIZE * bytes.length + + I8_SIZE + ); + writeU8(BOOLEANS_HEADER); + writeU8(0xff); + writeU32(count); + for (const byte of bytes) writeU8(byte); + writeU8(lastByte); + } + break; + } + case "object": { + if (thing === null) { + let n; + for (n = 1; n < 0x100000104 && i + n < data.length; n++) { + const item = data[i + n]; + if (item !== null) break; + } + i += n - 1; + if (n === 1) { + if (i + 1 < data.length) { + const next = data[i + 1]; + if (next === true) { + allocate(HEADER_SIZE); + writeU8(NULL_AND_TRUE_HEADER); + i++; + } else if (next === false) { + allocate(HEADER_SIZE); + writeU8(NULL_AND_FALSE_HEADER); + i++; + } else if (typeof next === "number") { + const type = identifyNumber(next); + if (type === 0) { + allocate(HEADER_SIZE + I8_SIZE); + writeU8(NULL_AND_I8_HEADER); + currentBuffer.writeInt8(next, currentPosition); + currentPosition += I8_SIZE; + i++; + } else if (type === 1) { + allocate(HEADER_SIZE + I32_SIZE); + writeU8(NULL_AND_I32_HEADER); + currentBuffer.writeInt32LE(next, currentPosition); + currentPosition += I32_SIZE; + i++; + } else { + allocate(HEADER_SIZE); + writeU8(NULL_HEADER); + } + } else { + allocate(HEADER_SIZE); + writeU8(NULL_HEADER); + } + } else { + allocate(HEADER_SIZE); + writeU8(NULL_HEADER); + } + } else if (n === 2) { + allocate(HEADER_SIZE); + writeU8(NULL2_HEADER); + } else if (n === 3) { + allocate(HEADER_SIZE); + writeU8(NULL3_HEADER); + } else if (n < 260) { + allocate(HEADER_SIZE + I8_SIZE); + writeU8(NULLS8_HEADER); + writeU8(n - 4); + } else { + allocate(HEADER_SIZE + I32_SIZE); + writeU8(NULLS32_HEADER); + writeU32(n - 260); + } + } else if (Buffer.isBuffer(thing)) { + if (thing.length < 8192) { + allocate(HEADER_SIZE + I32_SIZE + thing.length); + writeU8(BUFFER_HEADER); + writeU32(thing.length); + thing.copy(currentBuffer, currentPosition); + currentPosition += thing.length; + } else { + allocate(HEADER_SIZE + I32_SIZE); + writeU8(BUFFER_HEADER); + writeU32(thing.length); + flush(); + buffers.push(thing); + } + } + break; + } + case "symbol": { + if (thing === MEASURE_START_OPERATION) { + measureStart(); + } else if (thing === MEASURE_END_OPERATION) { + const size = measureEnd(); + allocate(HEADER_SIZE + I32_SIZE); + writeU8(I32_HEADER); + currentBuffer.writeInt32LE(size, currentPosition); + currentPosition += I32_SIZE; + } + break; + } } } - callback(); - } - - /** - * @returns {Set} types available (do not mutate) - */ - getSourceTypes() { - return TYPES; - } + flush(); - /** - * @param {string=} type the source type for which the size should be estimated - * @returns {number} the estimated size of the module (must be non-zero) - */ - size(type) { - return 42; - } + allocationScope.leftOverBuffer = leftOverBuffer; - /** - * @param {Hash} hash the hash used to track dependencies - * @param {UpdateHashContext} context context - * @returns {void} - */ - updateHash(hash, context) { - hash.update(JSON.stringify(this.options)); - super.updateHash(hash, context); + // avoid leaking memory + currentBuffer = null; + leftOverBuffer = null; + allocationScope = undefined; + const _buffers = buffers; + buffers = undefined; + return _buffers; } /** - * @param {CodeGenerationContext} context context for code generation - * @returns {CodeGenerationResult} result + * @param {SerializedType} data data + * @param {Object} context context object + * @returns {DeserializedType|Promise} deserialized data */ - codeGeneration({ chunkGraph, moduleGraph, runtimeTemplate }) { - const runtimeRequirements = new Set([RuntimeGlobals.shareScopeMap]); - const { - shareScope, - shareKey, - strictVersion, - requiredVersion, - import: request, - singleton, - eager - } = this.options; - let fallbackCode; - if (request) { - if (eager) { - const dep = this.dependencies[0]; - fallbackCode = runtimeTemplate.syncModuleFactory({ - dependency: dep, - chunkGraph, - runtimeRequirements, - request: this.options.import - }); - } else { - const block = this.blocks[0]; - fallbackCode = runtimeTemplate.asyncModuleFactory({ - block, - chunkGraph, - runtimeRequirements, - request: this.options.import - }); - } - } - let fn = "load"; - const args = [JSON.stringify(shareScope), JSON.stringify(shareKey)]; - if (requiredVersion) { - if (strictVersion) { - fn += "Strict"; - } - if (singleton) { - fn += "Singleton"; - } - args.push(stringifyHoley(requiredVersion)); - fn += "VersionCheck"; - } - if (fallbackCode) { - fn += "Fallback"; - args.push(fallbackCode); - } - const code = runtimeTemplate.returningFunction(`${fn}(${args.join(", ")})`); - const sources = new Map(); - sources.set("consume-shared", new RawSource(code)); - return { - runtimeRequirements, - sources - }; - } - - serialize(context) { - const { write } = context; - write(this.options); - super.serialize(context); - } - - deserialize(context) { - const { read } = context; - this.options = read(); - super.deserialize(context); + deserialize(data, context) { + return this._deserialize(data, context); } -} - -makeSerializable( - ConsumeSharedModule, - "webpack/lib/sharing/ConsumeSharedModule" -); - -module.exports = ConsumeSharedModule; - - -/***/ }), - -/***/ 19984: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ - - - -const ModuleNotFoundError = __webpack_require__(82908); -const RuntimeGlobals = __webpack_require__(49404); -const WebpackError = __webpack_require__(68422); -const { parseOptions } = __webpack_require__(56084); -const LazySet = __webpack_require__(59534); -const createSchemaValidation = __webpack_require__(77695); -const { parseRange } = __webpack_require__(60473); -const ConsumeSharedFallbackDependency = __webpack_require__(90489); -const ConsumeSharedModule = __webpack_require__(61474); -const ConsumeSharedRuntimeModule = __webpack_require__(830); -const ProvideForSharedDependency = __webpack_require__(40235); -const { resolveMatchedConfigs } = __webpack_require__(18436); -const { - isRequiredVersion, - getDescriptionFile, - getRequiredVersionFromDescriptionFile -} = __webpack_require__(58854); - -/** @typedef {import("../../declarations/plugins/sharing/ConsumeSharedPlugin").ConsumeSharedPluginOptions} ConsumeSharedPluginOptions */ -/** @typedef {import("../../declarations/plugins/sharing/ConsumeSharedPlugin").ConsumesConfig} ConsumesConfig */ -/** @typedef {import("../Compiler")} Compiler */ -/** @typedef {import("../ResolverFactory").ResolveOptionsWithDependencyType} ResolveOptionsWithDependencyType */ -/** @typedef {import("./ConsumeSharedModule").ConsumeOptions} ConsumeOptions */ -const validate = createSchemaValidation( - __webpack_require__(64246), - () => __webpack_require__(9515), - { - name: "Consume Shared Plugin", - baseDataPath: "options" + _createLazyDeserialized(content, context) { + return SerializerMiddleware.createLazy( + memoize(() => this._deserialize(content, context)), + this, + undefined, + content + ); } -); - -/** @type {ResolveOptionsWithDependencyType} */ -const RESOLVE_OPTIONS = { dependencyType: "esm" }; -const PLUGIN_NAME = "ConsumeSharedPlugin"; - -class ConsumeSharedPlugin { - /** - * @param {ConsumeSharedPluginOptions} options options - */ - constructor(options) { - if (typeof options !== "string") { - validate(options); - } - /** @type {[string, ConsumeOptions][]} */ - this._consumes = parseOptions( - options.consumes, - (item, key) => { - if (Array.isArray(item)) throw new Error("Unexpected array in options"); - /** @type {ConsumeOptions} */ - let result = - item === key || !isRequiredVersion(item) - ? // item is a request/key - { - import: key, - shareScope: options.shareScope || "default", - shareKey: key, - requiredVersion: undefined, - packageName: undefined, - strictVersion: false, - singleton: false, - eager: false - } - : // key is a request/key - // item is a version - { - import: key, - shareScope: options.shareScope || "default", - shareKey: key, - requiredVersion: parseRange(item), - strictVersion: true, - packageName: undefined, - singleton: false, - eager: false - }; - return result; - }, - (item, key) => ({ - import: item.import === false ? undefined : item.import || key, - shareScope: item.shareScope || options.shareScope || "default", - shareKey: item.shareKey || key, - requiredVersion: - typeof item.requiredVersion === "string" - ? parseRange(item.requiredVersion) - : item.requiredVersion, - strictVersion: - typeof item.strictVersion === "boolean" - ? item.strictVersion - : item.import !== false && !item.singleton, - packageName: item.packageName, - singleton: !!item.singleton, - eager: !!item.eager - }) + _deserializeLazy(fn, context) { + return SerializerMiddleware.deserializeLazy(fn, data => + this._deserialize(data, context) ); } /** - * Apply the plugin - * @param {Compiler} compiler the compiler instance - * @returns {void} + * @param {SerializedType} data data + * @param {Object} context context object + * @returns {DeserializedType} deserialized data */ - apply(compiler) { - compiler.hooks.thisCompilation.tap( - PLUGIN_NAME, - (compilation, { normalModuleFactory }) => { - compilation.dependencyFactories.set( - ConsumeSharedFallbackDependency, - normalModuleFactory - ); + _deserialize(data, context) { + let currentDataItem = 0; + let currentBuffer = data[0]; + let currentIsBuffer = Buffer.isBuffer(currentBuffer); + let currentPosition = 0; - let unresolvedConsumes, resolvedConsumes, prefixedConsumes; - const promise = resolveMatchedConfigs(compilation, this._consumes).then( - ({ resolved, unresolved, prefixed }) => { - resolvedConsumes = resolved; - unresolvedConsumes = unresolved; - prefixedConsumes = prefixed; - } - ); + const retainedBuffer = context.retainedBuffer || (x => x); - const resolver = compilation.resolverFactory.get( - "normal", - RESOLVE_OPTIONS + const checkOverflow = () => { + if (currentPosition >= currentBuffer.length) { + currentPosition = 0; + currentDataItem++; + currentBuffer = + currentDataItem < data.length ? data[currentDataItem] : null; + currentIsBuffer = Buffer.isBuffer(currentBuffer); + } + }; + const isInCurrentBuffer = n => { + return currentIsBuffer && n + currentPosition <= currentBuffer.length; + }; + const ensureBuffer = () => { + if (!currentIsBuffer) { + throw new Error( + currentBuffer === null + ? "Unexpected end of stream" + : "Unexpected lazy element in stream" ); - - /** - * @param {string} context issuer directory - * @param {string} request request - * @param {ConsumeOptions} config options - * @returns {Promise} create module - */ - const createConsumeSharedModule = (context, request, config) => { - const requiredVersionWarning = details => { - const error = new WebpackError( - `No required version specified and unable to automatically determine one. ${details}` - ); - error.file = `shared module ${request}`; - compilation.warnings.push(error); + } + }; + /** + * Reads n bytes + * @param {number} n amount of bytes to read + * @returns {Buffer} buffer with bytes + */ + const read = n => { + ensureBuffer(); + const rem = currentBuffer.length - currentPosition; + if (rem < n) { + const buffers = [read(rem)]; + n -= rem; + ensureBuffer(); + while (currentBuffer.length < n) { + const b = /** @type {Buffer} */ (currentBuffer); + buffers.push(b); + n -= b.length; + currentDataItem++; + currentBuffer = + currentDataItem < data.length ? data[currentDataItem] : null; + currentIsBuffer = Buffer.isBuffer(currentBuffer); + ensureBuffer(); + } + buffers.push(read(n)); + return Buffer.concat(buffers); + } + const b = /** @type {Buffer} */ (currentBuffer); + const res = Buffer.from(b.buffer, b.byteOffset + currentPosition, n); + currentPosition += n; + checkOverflow(); + return res; + }; + /** + * Reads up to n bytes + * @param {number} n amount of bytes to read + * @returns {Buffer} buffer with bytes + */ + const readUpTo = n => { + ensureBuffer(); + const rem = currentBuffer.length - currentPosition; + if (rem < n) { + n = rem; + } + const b = /** @type {Buffer} */ (currentBuffer); + const res = Buffer.from(b.buffer, b.byteOffset + currentPosition, n); + currentPosition += n; + checkOverflow(); + return res; + }; + const readU8 = () => { + ensureBuffer(); + /** + * There is no need to check remaining buffer size here + * since {@link checkOverflow} guarantees at least one byte remaining + */ + const byte = /** @type {Buffer} */ (currentBuffer).readUInt8( + currentPosition + ); + currentPosition += I8_SIZE; + checkOverflow(); + return byte; + }; + const readU32 = () => { + return read(I32_SIZE).readUInt32LE(0); + }; + const readBits = (data, n) => { + let mask = 1; + while (n !== 0) { + result.push((data & mask) !== 0); + mask = mask << 1; + n--; + } + }; + const dispatchTable = Array.from({ length: 256 }).map((_, header) => { + switch (header) { + case LAZY_HEADER: + return () => { + const count = readU32(); + const lengths = Array.from({ length: count }).map(() => readU32()); + const content = []; + for (let l of lengths) { + if (l === 0) { + if (typeof currentBuffer !== "function") { + throw new Error("Unexpected non-lazy element in stream"); + } + content.push(currentBuffer); + currentDataItem++; + currentBuffer = + currentDataItem < data.length ? data[currentDataItem] : null; + currentIsBuffer = Buffer.isBuffer(currentBuffer); + } else { + do { + const buf = readUpTo(l); + l -= buf.length; + content.push(retainedBuffer(buf)); + } while (l > 0); + } + } + result.push(this._createLazyDeserialized(content, context)); + }; + case BUFFER_HEADER: + return () => { + const len = readU32(); + result.push(retainedBuffer(read(len))); + }; + case TRUE_HEADER: + return () => result.push(true); + case FALSE_HEADER: + return () => result.push(false); + case NULL3_HEADER: + return () => result.push(null, null, null); + case NULL2_HEADER: + return () => result.push(null, null); + case NULL_HEADER: + return () => result.push(null); + case NULL_AND_TRUE_HEADER: + return () => result.push(null, true); + case NULL_AND_FALSE_HEADER: + return () => result.push(null, false); + case NULL_AND_I8_HEADER: + return () => { + if (currentIsBuffer) { + result.push( + null, + /** @type {Buffer} */ (currentBuffer).readInt8(currentPosition) + ); + currentPosition += I8_SIZE; + checkOverflow(); + } else { + result.push(null, read(I8_SIZE).readInt8(0)); + } + }; + case NULL_AND_I32_HEADER: + return () => { + result.push(null); + if (isInCurrentBuffer(I32_SIZE)) { + result.push( + /** @type {Buffer} */ (currentBuffer).readInt32LE( + currentPosition + ) + ); + currentPosition += I32_SIZE; + checkOverflow(); + } else { + result.push(read(I32_SIZE).readInt32LE(0)); + } + }; + case NULLS8_HEADER: + return () => { + const len = readU8() + 4; + for (let i = 0; i < len; i++) { + result.push(null); + } + }; + case NULLS32_HEADER: + return () => { + const len = readU32() + 260; + for (let i = 0; i < len; i++) { + result.push(null); + } + }; + case BOOLEANS_HEADER: + return () => { + const innerHeader = readU8(); + if ((innerHeader & 0xf0) === 0) { + readBits(innerHeader, 3); + } else if ((innerHeader & 0xe0) === 0) { + readBits(innerHeader, 4); + } else if ((innerHeader & 0xc0) === 0) { + readBits(innerHeader, 5); + } else if ((innerHeader & 0x80) === 0) { + readBits(innerHeader, 6); + } else if (innerHeader !== 0xff) { + let count = (innerHeader & 0x7f) + 7; + while (count > 8) { + readBits(readU8(), 8); + count -= 8; + } + readBits(readU8(), count); + } else { + let count = readU32(); + while (count > 8) { + readBits(readU8(), 8); + count -= 8; + } + readBits(readU8(), count); + } + }; + case STRING_HEADER: + return () => { + const len = readU32(); + if (isInCurrentBuffer(len) && currentPosition + len < 0x7fffffff) { + result.push( + currentBuffer.toString( + undefined, + currentPosition, + currentPosition + len + ) + ); + currentPosition += len; + checkOverflow(); + } else { + result.push(read(len).toString()); + } }; - const directFallback = - config.import && - /^(\.\.?(\/|$)|\/|[A-Za-z]:|\\\\)/.test(config.import); - return Promise.all([ - new Promise(resolve => { - if (!config.import) return resolve(); - const resolveContext = { - /** @type {LazySet} */ - fileDependencies: new LazySet(), - /** @type {LazySet} */ - contextDependencies: new LazySet(), - /** @type {LazySet} */ - missingDependencies: new LazySet() - }; - resolver.resolve( - {}, - directFallback ? compiler.context : context, - config.import, - resolveContext, - (err, result) => { - compilation.contextDependencies.addAll( - resolveContext.contextDependencies - ); - compilation.fileDependencies.addAll( - resolveContext.fileDependencies - ); - compilation.missingDependencies.addAll( - resolveContext.missingDependencies - ); - if (err) { - compilation.errors.push( - new ModuleNotFoundError(null, err, { - name: `resolving fallback for shared module ${request}` - }) - ); - return resolve(); - } - resolve(result); - } + case SHORT_STRING_HEADER: + return () => result.push(""); + case SHORT_STRING_HEADER | 1: + return () => { + if (currentIsBuffer && currentPosition < 0x7ffffffe) { + result.push( + currentBuffer.toString( + "latin1", + currentPosition, + currentPosition + 1 + ) ); - }), - new Promise(resolve => { - if (config.requiredVersion !== undefined) - return resolve(config.requiredVersion); - let packageName = config.packageName; - if (packageName === undefined) { - if (/^(\/|[A-Za-z]:|\\\\)/.test(request)) { - // For relative or absolute requests we don't automatically use a packageName. - // If wished one can specify one with the packageName option. - return resolve(); - } - const match = /^((?:@[^\\/]+[\\/])?[^\\/]+)/.exec(request); - if (!match) { - requiredVersionWarning( - "Unable to extract the package name from request." - ); - return resolve(); - } - packageName = match[0]; - } - - getDescriptionFile( - compilation.inputFileSystem, - context, - ["package.json"], - (err, result) => { - if (err) { - requiredVersionWarning( - `Unable to read description file: ${err}` - ); - return resolve(); - } - const { data, path: descriptionPath } = result; - if (!data) { - requiredVersionWarning( - `Unable to find description file in ${context}.` - ); - return resolve(); - } - const requiredVersion = getRequiredVersionFromDescriptionFile( - data, - packageName - ); - if (typeof requiredVersion !== "string") { - requiredVersionWarning( - `Unable to find required version for "${packageName}" in description file (${descriptionPath}). It need to be in dependencies, devDependencies or peerDependencies.` - ); - return resolve(); - } - resolve(parseRange(requiredVersion)); - } + currentPosition++; + checkOverflow(); + } else { + result.push(read(1).toString("latin1")); + } + }; + case I8_HEADER: + return () => { + if (currentIsBuffer) { + result.push( + /** @type {Buffer} */ (currentBuffer).readInt8(currentPosition) ); - }) - ]).then(([importResolved, requiredVersion]) => { - return new ConsumeSharedModule( - directFallback ? compiler.context : context, - { - ...config, - importResolved, - import: importResolved ? config.import : undefined, - requiredVersion - } - ); - }); - }; - - normalModuleFactory.hooks.factorize.tapPromise( - PLUGIN_NAME, - ({ context, request, dependencies }) => - // wait for resolving to be complete - promise.then(() => { + currentPosition++; + checkOverflow(); + } else { + result.push(read(1).readInt8(0)); + } + }; + default: + if (header <= 10) { + return () => result.push(header); + } else if ((header & SHORT_STRING_HEADER) === SHORT_STRING_HEADER) { + const len = header & SHORT_STRING_LENGTH_MASK; + return () => { if ( - dependencies[0] instanceof ConsumeSharedFallbackDependency || - dependencies[0] instanceof ProvideForSharedDependency + isInCurrentBuffer(len) && + currentPosition + len < 0x7fffffff ) { - return; - } - const match = unresolvedConsumes.get(request); - if (match !== undefined) { - return createConsumeSharedModule(context, request, match); + result.push( + currentBuffer.toString( + "latin1", + currentPosition, + currentPosition + len + ) + ); + currentPosition += len; + checkOverflow(); + } else { + result.push(read(len).toString("latin1")); } - for (const [prefix, options] of prefixedConsumes) { - if (request.startsWith(prefix)) { - const remainder = request.slice(prefix.length); - return createConsumeSharedModule(context, request, { - ...options, - import: options.import - ? options.import + remainder - : undefined, - shareKey: options.shareKey + remainder - }); + }; + } else if ((header & NUMBERS_HEADER_MASK) === F64_HEADER) { + const len = (header & NUMBERS_COUNT_MASK) + 1; + return () => { + const need = F64_SIZE * len; + if (isInCurrentBuffer(need)) { + for (let i = 0; i < len; i++) { + result.push( + /** @type {Buffer} */ (currentBuffer).readDoubleLE( + currentPosition + ) + ); + currentPosition += F64_SIZE; + } + checkOverflow(); + } else { + const buf = read(need); + for (let i = 0; i < len; i++) { + result.push(buf.readDoubleLE(i * F64_SIZE)); } } - }) - ); - normalModuleFactory.hooks.createModule.tapPromise( - PLUGIN_NAME, - ({ resource }, { context, dependencies }) => { - if ( - dependencies[0] instanceof ConsumeSharedFallbackDependency || - dependencies[0] instanceof ProvideForSharedDependency - ) { - return Promise.resolve(); - } - const options = resolvedConsumes.get(resource); - if (options !== undefined) { - return createConsumeSharedModule(context, resource, options); - } - return Promise.resolve(); - } - ); - compilation.hooks.additionalTreeRuntimeRequirements.tap( - PLUGIN_NAME, - (chunk, set) => { - set.add(RuntimeGlobals.module); - set.add(RuntimeGlobals.moduleCache); - set.add(RuntimeGlobals.moduleFactoriesAddOnly); - set.add(RuntimeGlobals.shareScopeMap); - set.add(RuntimeGlobals.initializeSharing); - set.add(RuntimeGlobals.hasOwnProperty); - compilation.addRuntimeModule( - chunk, - new ConsumeSharedRuntimeModule(set) - ); - } - ); - } - ); - } -} - -module.exports = ConsumeSharedPlugin; - - -/***/ }), - -/***/ 830: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ - - - -const RuntimeGlobals = __webpack_require__(49404); -const RuntimeModule = __webpack_require__(61439); -const Template = __webpack_require__(92066); -const { - parseVersionRuntimeCode, - versionLtRuntimeCode, - rangeToStringRuntimeCode, - satisfyRuntimeCode -} = __webpack_require__(60473); - -/** @typedef {import("webpack-sources").Source} Source */ -/** @typedef {import("../Chunk")} Chunk */ -/** @typedef {import("../Module")} Module */ -/** @typedef {import("./ConsumeSharedModule")} ConsumeSharedModule */ - -class ConsumeSharedRuntimeModule extends RuntimeModule { - constructor(runtimeRequirements) { - super("consumes", RuntimeModule.STAGE_ATTACH); - this._runtimeRequirements = runtimeRequirements; - } - - /** - * @returns {string} runtime code - */ - generate() { - const { compilation, chunkGraph } = this; - const { runtimeTemplate, codeGenerationResults } = compilation; - const chunkToModuleMapping = {}; - /** @type {Map} */ - const moduleIdToSourceMapping = new Map(); - const initialConsumes = []; - /** - * - * @param {Iterable} modules modules - * @param {Chunk} chunk the chunk - * @param {(string | number)[]} list list of ids - */ - const addModules = (modules, chunk, list) => { - for (const m of modules) { - const module = /** @type {ConsumeSharedModule} */ (m); - const id = chunkGraph.getModuleId(module); - list.push(id); - moduleIdToSourceMapping.set( - id, - codeGenerationResults.getSource( - module, - chunk.runtime, - "consume-shared" - ) - ); - } - }; - for (const chunk of this.chunk.getAllAsyncChunks()) { - const modules = chunkGraph.getChunkModulesIterableBySourceType( - chunk, - "consume-shared" - ); - if (!modules) continue; - addModules(modules, chunk, (chunkToModuleMapping[chunk.id] = [])); - } - for (const chunk of this.chunk.getAllInitialChunks()) { - const modules = chunkGraph.getChunkModulesIterableBySourceType( - chunk, - "consume-shared" - ); - if (!modules) continue; - addModules(modules, chunk, initialConsumes); - } - if (moduleIdToSourceMapping.size === 0) return null; - return Template.asString([ - parseVersionRuntimeCode(runtimeTemplate), - versionLtRuntimeCode(runtimeTemplate), - rangeToStringRuntimeCode(runtimeTemplate), - satisfyRuntimeCode(runtimeTemplate), - `var ensureExistence = ${runtimeTemplate.basicFunction("scopeName, key", [ - `var scope = ${RuntimeGlobals.shareScopeMap}[scopeName];`, - `if(!scope || !${RuntimeGlobals.hasOwnProperty}(scope, key)) throw new Error("Shared module " + key + " doesn't exist in shared scope " + scopeName);`, - "return scope;" - ])};`, - `var findVersion = ${runtimeTemplate.basicFunction("scope, key", [ - "var versions = scope[key];", - `var key = Object.keys(versions).reduce(${runtimeTemplate.basicFunction( - "a, b", - ["return !a || versionLt(a, b) ? b : a;"] - )}, 0);`, - "return key && versions[key]" - ])};`, - `var findSingletonVersionKey = ${runtimeTemplate.basicFunction( - "scope, key", - [ - "var versions = scope[key];", - `return Object.keys(versions).reduce(${runtimeTemplate.basicFunction( - "a, b", - ["return !a || (!versions[a].loaded && versionLt(a, b)) ? b : a;"] - )}, 0);` - ] - )};`, - `var getInvalidSingletonVersionMessage = ${runtimeTemplate.basicFunction( - "key, version, requiredVersion", - [ - `return "Unsatisfied version " + version + " of shared singleton module " + key + " (required " + rangeToString(requiredVersion) + ")"` - ] - )};`, - `var getSingletonVersion = ${runtimeTemplate.basicFunction( - "scope, scopeName, key, requiredVersion", - [ - "var version = findSingletonVersionKey(scope, key);", - "if (!satisfy(requiredVersion, version)) " + - 'typeof console !== "undefined" && console.warn && console.warn(getInvalidSingletonVersionMessage(key, version, requiredVersion));', - "return get(scope[key][version]);" - ] - )};`, - `var getStrictSingletonVersion = ${runtimeTemplate.basicFunction( - "scope, scopeName, key, requiredVersion", - [ - "var version = findSingletonVersionKey(scope, key);", - "if (!satisfy(requiredVersion, version)) " + - "throw new Error(getInvalidSingletonVersionMessage(key, version, requiredVersion));", - "return get(scope[key][version]);" - ] - )};`, - `var findValidVersion = ${runtimeTemplate.basicFunction( - "scope, key, requiredVersion", - [ - "var versions = scope[key];", - `var key = Object.keys(versions).reduce(${runtimeTemplate.basicFunction( - "a, b", - [ - "if (!satisfy(requiredVersion, b)) return a;", - "return !a || versionLt(a, b) ? b : a;" - ] - )}, 0);`, - "return key && versions[key]" - ] - )};`, - `var getInvalidVersionMessage = ${runtimeTemplate.basicFunction( - "scope, scopeName, key, requiredVersion", - [ - "var versions = scope[key];", - 'return "No satisfying version (" + rangeToString(requiredVersion) + ") of shared module " + key + " found in shared scope " + scopeName + ".\\n" +', - `\t"Available versions: " + Object.keys(versions).map(${runtimeTemplate.basicFunction( - "key", - ['return key + " from " + versions[key].from;'] - )}).join(", ");` - ] - )};`, - `var getValidVersion = ${runtimeTemplate.basicFunction( - "scope, scopeName, key, requiredVersion", - [ - "var entry = findValidVersion(scope, key, requiredVersion);", - "if(entry) return get(entry);", - "throw new Error(getInvalidVersionMessage(scope, scopeName, key, requiredVersion));" - ] - )};`, - `var warnInvalidVersion = ${runtimeTemplate.basicFunction( - "scope, scopeName, key, requiredVersion", - [ - 'typeof console !== "undefined" && console.warn && console.warn(getInvalidVersionMessage(scope, scopeName, key, requiredVersion));' - ] - )};`, - `var get = ${runtimeTemplate.basicFunction("entry", [ - "entry.loaded = 1;", - "return entry.get()" - ])};`, - `var init = ${runtimeTemplate.returningFunction( - Template.asString([ - "function(scopeName, a, b, c) {", - Template.indent([ - `var promise = ${RuntimeGlobals.initializeSharing}(scopeName);`, - `if (promise && promise.then) return promise.then(fn.bind(fn, scopeName, ${RuntimeGlobals.shareScopeMap}[scopeName], a, b, c));`, - `return fn(scopeName, ${RuntimeGlobals.shareScopeMap}[scopeName], a, b, c);` - ]), - "}" - ]), - "fn" - )};`, - "", - `var load = /*#__PURE__*/ init(${runtimeTemplate.basicFunction( - "scopeName, scope, key", - [ - "ensureExistence(scopeName, key);", - "return get(findVersion(scope, key));" - ] - )});`, - `var loadFallback = /*#__PURE__*/ init(${runtimeTemplate.basicFunction( - "scopeName, scope, key, fallback", - [ - `return scope && ${RuntimeGlobals.hasOwnProperty}(scope, key) ? get(findVersion(scope, key)) : fallback();` - ] - )});`, - `var loadVersionCheck = /*#__PURE__*/ init(${runtimeTemplate.basicFunction( - "scopeName, scope, key, version", - [ - "ensureExistence(scopeName, key);", - "return get(findValidVersion(scope, key, version) || warnInvalidVersion(scope, scopeName, key, version) || findVersion(scope, key));" - ] - )});`, - `var loadSingletonVersionCheck = /*#__PURE__*/ init(${runtimeTemplate.basicFunction( - "scopeName, scope, key, version", - [ - "ensureExistence(scopeName, key);", - "return getSingletonVersion(scope, scopeName, key, version);" - ] - )});`, - `var loadStrictVersionCheck = /*#__PURE__*/ init(${runtimeTemplate.basicFunction( - "scopeName, scope, key, version", - [ - "ensureExistence(scopeName, key);", - "return getValidVersion(scope, scopeName, key, version);" - ] - )});`, - `var loadStrictSingletonVersionCheck = /*#__PURE__*/ init(${runtimeTemplate.basicFunction( - "scopeName, scope, key, version", - [ - "ensureExistence(scopeName, key);", - "return getStrictSingletonVersion(scope, scopeName, key, version);" - ] - )});`, - `var loadVersionCheckFallback = /*#__PURE__*/ init(${runtimeTemplate.basicFunction( - "scopeName, scope, key, version, fallback", - [ - `if(!scope || !${RuntimeGlobals.hasOwnProperty}(scope, key)) return fallback();`, - "return get(findValidVersion(scope, key, version) || warnInvalidVersion(scope, scopeName, key, version) || findVersion(scope, key));" - ] - )});`, - `var loadSingletonVersionCheckFallback = /*#__PURE__*/ init(${runtimeTemplate.basicFunction( - "scopeName, scope, key, version, fallback", - [ - `if(!scope || !${RuntimeGlobals.hasOwnProperty}(scope, key)) return fallback();`, - "return getSingletonVersion(scope, scopeName, key, version);" - ] - )});`, - `var loadStrictVersionCheckFallback = /*#__PURE__*/ init(${runtimeTemplate.basicFunction( - "scopeName, scope, key, version, fallback", - [ - `var entry = scope && ${RuntimeGlobals.hasOwnProperty}(scope, key) && findValidVersion(scope, key, version);`, - `return entry ? get(entry) : fallback();` - ] - )});`, - `var loadStrictSingletonVersionCheckFallback = /*#__PURE__*/ init(${runtimeTemplate.basicFunction( - "scopeName, scope, key, version, fallback", - [ - `if(!scope || !${RuntimeGlobals.hasOwnProperty}(scope, key)) return fallback();`, - "return getStrictSingletonVersion(scope, scopeName, key, version);" - ] - )});`, - "var installedModules = {};", - "var moduleToHandlerMapping = {", - Template.indent( - Array.from( - moduleIdToSourceMapping, - ([key, source]) => `${JSON.stringify(key)}: ${source.source()}` - ).join(",\n") - ), - "};", + }; + } else if ((header & NUMBERS_HEADER_MASK) === I32_HEADER) { + const len = (header & NUMBERS_COUNT_MASK) + 1; + return () => { + const need = I32_SIZE * len; + if (isInCurrentBuffer(need)) { + for (let i = 0; i < len; i++) { + result.push( + /** @type {Buffer} */ (currentBuffer).readInt32LE( + currentPosition + ) + ); + currentPosition += I32_SIZE; + } + checkOverflow(); + } else { + const buf = read(need); + for (let i = 0; i < len; i++) { + result.push(buf.readInt32LE(i * I32_SIZE)); + } + } + }; + } else if ((header & NUMBERS_HEADER_MASK) === I8_HEADER) { + const len = (header & NUMBERS_COUNT_MASK) + 1; + return () => { + const need = I8_SIZE * len; + if (isInCurrentBuffer(need)) { + for (let i = 0; i < len; i++) { + result.push( + /** @type {Buffer} */ (currentBuffer).readInt8( + currentPosition + ) + ); + currentPosition += I8_SIZE; + } + checkOverflow(); + } else { + const buf = read(need); + for (let i = 0; i < len; i++) { + result.push(buf.readInt8(i * I8_SIZE)); + } + } + }; + } else { + return () => { + throw new Error( + `Unexpected header byte 0x${header.toString(16)}` + ); + }; + } + } + }); - initialConsumes.length > 0 - ? Template.asString([ - `var initialConsumes = ${JSON.stringify(initialConsumes)};`, - `initialConsumes.forEach(${runtimeTemplate.basicFunction("id", [ - `${ - RuntimeGlobals.moduleFactories - }[id] = ${runtimeTemplate.basicFunction("module", [ - "// Handle case when module is used sync", - "installedModules[id] = 0;", - `delete ${RuntimeGlobals.moduleCache}[id];`, - "var factory = moduleToHandlerMapping[id]();", - 'if(typeof factory !== "function") throw new Error("Shared module is not available for eager consumption: " + id);', - `module.exports = factory();` - ])}` - ])});` - ]) - : "// no consumes in initial chunks", - this._runtimeRequirements.has(RuntimeGlobals.ensureChunkHandlers) - ? Template.asString([ - `var chunkMapping = ${JSON.stringify( - chunkToModuleMapping, - null, - "\t" - )};`, - `${ - RuntimeGlobals.ensureChunkHandlers - }.consumes = ${runtimeTemplate.basicFunction("chunkId, promises", [ - `if(${RuntimeGlobals.hasOwnProperty}(chunkMapping, chunkId)) {`, - Template.indent([ - `chunkMapping[chunkId].forEach(${runtimeTemplate.basicFunction( - "id", - [ - `if(${RuntimeGlobals.hasOwnProperty}(installedModules, id)) return promises.push(installedModules[id]);`, - `var onFactory = ${runtimeTemplate.basicFunction( - "factory", - [ - "installedModules[id] = 0;", - `${ - RuntimeGlobals.moduleFactories - }[id] = ${runtimeTemplate.basicFunction("module", [ - `delete ${RuntimeGlobals.moduleCache}[id];`, - "module.exports = factory();" - ])}` - ] - )};`, - `var onError = ${runtimeTemplate.basicFunction("error", [ - "delete installedModules[id];", - `${ - RuntimeGlobals.moduleFactories - }[id] = ${runtimeTemplate.basicFunction("module", [ - `delete ${RuntimeGlobals.moduleCache}[id];`, - "throw error;" - ])}` - ])};`, - "try {", - Template.indent([ - "var promise = moduleToHandlerMapping[id]();", - "if(promise.then) {", - Template.indent( - "promises.push(installedModules[id] = promise.then(onFactory)['catch'](onError));" - ), - "} else onFactory(promise);" - ]), - "} catch(e) { onError(e); }" - ] - )});` - ]), - "}" - ])}` - ]) - : "// no chunk loading of consumes" - ]); + /** @type {DeserializedType} */ + let result = []; + while (currentBuffer !== null) { + if (typeof currentBuffer === "function") { + result.push(this._deserializeLazy(currentBuffer, context)); + currentDataItem++; + currentBuffer = + currentDataItem < data.length ? data[currentDataItem] : null; + currentIsBuffer = Buffer.isBuffer(currentBuffer); + } else { + const header = readU8(); + dispatchTable[header](); + } + } + + // avoid leaking memory in context + let _result = result; + result = undefined; + return _result; } } -module.exports = ConsumeSharedRuntimeModule; +module.exports = BinaryMiddleware; + +module.exports.MEASURE_START_OPERATION = MEASURE_START_OPERATION; +module.exports.MEASURE_END_OPERATION = MEASURE_END_OPERATION; /***/ }), -/***/ 40235: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { +/***/ 32973: +/***/ (function(module) { "use strict"; /* MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra */ -const ModuleDependency = __webpack_require__(80944); -const makeSerializable = __webpack_require__(26522); - -class ProvideForSharedDependency extends ModuleDependency { - /** - * - * @param {string} request request string - */ - constructor(request) { - super(request); - } - - get type() { - return "provide module for shared"; +class DateObjectSerializer { + serialize(obj, { write }) { + write(obj.getTime()); } - - get category() { - return "esm"; + deserialize({ read }) { + return new Date(read()); } } -makeSerializable( - ProvideForSharedDependency, - "webpack/lib/sharing/ProvideForSharedDependency" -); - -module.exports = ProvideForSharedDependency; +module.exports = DateObjectSerializer; /***/ }), -/***/ 99355: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { +/***/ 60252: +/***/ (function(module) { "use strict"; /* MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra */ -const Dependency = __webpack_require__(50384); -const makeSerializable = __webpack_require__(26522); - -class ProvideSharedDependency extends Dependency { - constructor(shareScope, name, version, request, eager) { - super(); - this.shareScope = shareScope; - this.name = name; - this.version = version; - this.request = request; - this.eager = eager; +class ErrorObjectSerializer { + constructor(Type) { + this.Type = Type; } - get type() { - return "provide shared module"; + serialize(obj, { write }) { + write(obj.message); + write(obj.stack); } - /** - * @returns {string | null} an identifier to merge equal requests - */ - getResourceIdentifier() { - return `provide module (${this.shareScope}) ${this.request} as ${ - this.name - } @ ${this.version}${this.eager ? " (eager)" : ""}`; - } + deserialize({ read }) { + const err = new this.Type(); - serialize(context) { - context.write(this.shareScope); - context.write(this.name); - context.write(this.request); - context.write(this.version); - context.write(this.eager); - super.serialize(context); - } + err.message = read(); + err.stack = read(); - static deserialize(context) { - const { read } = context; - const obj = new ProvideSharedDependency( - read(), - read(), - read(), - read(), - read() - ); - this.shareScope = context.read(); - obj.deserialize(context); - return obj; + return err; } } -makeSerializable( - ProvideSharedDependency, - "webpack/lib/sharing/ProvideSharedDependency" -); - -module.exports = ProvideSharedDependency; +module.exports = ErrorObjectSerializer; /***/ }), -/***/ 65945: +/***/ 40572: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; /* MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra and Zackary Jackson @ScriptedAlchemy */ -const AsyncDependenciesBlock = __webpack_require__(11315); -const Module = __webpack_require__(85887); -const RuntimeGlobals = __webpack_require__(49404); -const makeSerializable = __webpack_require__(26522); -const ProvideForSharedDependency = __webpack_require__(40235); +const { constants } = __webpack_require__(64293); +const { pipeline } = __webpack_require__(92413); +const { + createBrotliCompress, + createBrotliDecompress, + createGzip, + createGunzip, + constants: zConstants +} = __webpack_require__(78761); +const createHash = __webpack_require__(24123); +const { dirname, join, mkdirp } = __webpack_require__(93204); +const memoize = __webpack_require__(84297); +const SerializerMiddleware = __webpack_require__(37063); -/** @typedef {import("../../declarations/WebpackOptions").WebpackOptionsNormalized} WebpackOptions */ -/** @typedef {import("../Chunk")} Chunk */ -/** @typedef {import("../ChunkGraph")} ChunkGraph */ -/** @typedef {import("../ChunkGroup")} ChunkGroup */ -/** @typedef {import("../Compilation")} Compilation */ -/** @typedef {import("../Module").CodeGenerationContext} CodeGenerationContext */ -/** @typedef {import("../Module").CodeGenerationResult} CodeGenerationResult */ -/** @typedef {import("../Module").LibIdentOptions} LibIdentOptions */ -/** @typedef {import("../Module").NeedBuildContext} NeedBuildContext */ -/** @typedef {import("../RequestShortener")} RequestShortener */ -/** @typedef {import("../ResolverFactory").ResolverWithOptions} ResolverWithOptions */ -/** @typedef {import("../WebpackError")} WebpackError */ -/** @typedef {import("../util/Hash")} Hash */ -/** @typedef {import("../util/fs").InputFileSystem} InputFileSystem */ +/** @typedef {typeof import("../util/Hash")} Hash */ +/** @typedef {import("../util/fs").IntermediateFileSystem} IntermediateFileSystem */ +/** @typedef {import("./types").BufferSerializableType} BufferSerializableType */ -const TYPES = new Set(["share-init"]); +/* +Format: -class ProvideSharedModule extends Module { - /** - * @param {string} shareScope shared scope name - * @param {string} name shared key - * @param {string | false} version version - * @param {string} request request to the provided module - * @param {boolean} eager include the module in sync way - */ - constructor(shareScope, name, version, request, eager) { - super("provide-module"); - this._shareScope = shareScope; - this._name = name; - this._version = version; - this._request = request; - this._eager = eager; - } +File -> Header Section* - /** - * @returns {string} a unique identifier of the module - */ - identifier() { - return `provide module (${this._shareScope}) ${this._name}@${this._version} = ${this._request}`; - } +Version -> u32 +AmountOfSections -> u32 +SectionSize -> i32 (if less than zero represents lazy value) - /** - * @param {RequestShortener} requestShortener the request shortener - * @returns {string} a user readable identifier of the module - */ - readableIdentifier(requestShortener) { - return `provide shared module (${this._shareScope}) ${this._name}@${ - this._version - } = ${requestShortener.shorten(this._request)}`; - } +Header -> Version AmountOfSections SectionSize* - /** - * @param {LibIdentOptions} options options - * @returns {string | null} an identifier for library inclusion - */ - libIdent(options) { - return `webpack/sharing/provide/${this._shareScope}/${this._name}`; - } +Buffer -> n bytes +Section -> Buffer - /** - * @param {NeedBuildContext} context context info - * @param {function(WebpackError=, boolean=): void} callback callback function, returns true, if the module needs a rebuild - * @returns {void} - */ - needBuild(context, callback) { - callback(null, !this.buildInfo); - } +*/ - /** - * @param {WebpackOptions} options webpack options - * @param {Compilation} compilation the compilation - * @param {ResolverWithOptions} resolver the resolver - * @param {InputFileSystem} fs the file system - * @param {function(WebpackError=): void} callback callback function - * @returns {void} - */ - build(options, compilation, resolver, fs, callback) { - this.buildMeta = {}; - this.buildInfo = { - strict: true - }; +// "wpc" + 1 in little-endian +const VERSION = 0x01637077; - this.clearDependenciesAndBlocks(); - const dep = new ProvideForSharedDependency(this._request); - if (this._eager) { - this.addDependency(dep); - } else { - const block = new AsyncDependenciesBlock({}); - block.addDependency(dep); - this.addBlock(block); - } +/** + * @param {Buffer[]} buffers buffers + * @param {string | Hash} hashFunction hash function to use + * @returns {string} hash + */ +const hashForName = (buffers, hashFunction) => { + const hash = createHash(hashFunction); + for (const buf of buffers) hash.update(buf); + return /** @type {string} */ (hash.digest("hex")); +}; - callback(); - } +const COMPRESSION_CHUNK_SIZE = 100 * 1024 * 1024; +const DECOMPRESSION_CHUNK_SIZE = 100 * 1024 * 1024; - /** - * @param {string=} type the source type for which the size should be estimated - * @returns {number} the estimated size of the module (must be non-zero) - */ - size(type) { - return 42; - } +const writeUInt64LE = Buffer.prototype.writeBigUInt64LE + ? (buf, value, offset) => { + buf.writeBigUInt64LE(BigInt(value), offset); + } + : (buf, value, offset) => { + const low = value % 0x100000000; + const high = (value - low) / 0x100000000; + buf.writeUInt32LE(low, offset); + buf.writeUInt32LE(high, offset + 4); + }; - /** - * @returns {Set} types available (do not mutate) - */ - getSourceTypes() { - return TYPES; - } +const readUInt64LE = Buffer.prototype.readBigUInt64LE + ? (buf, offset) => { + return Number(buf.readBigUInt64LE(offset)); + } + : (buf, offset) => { + const low = buf.readUInt32LE(offset); + const high = buf.readUInt32LE(offset + 4); + return high * 0x100000000 + low; + }; - /** - * @param {CodeGenerationContext} context context for code generation - * @returns {CodeGenerationResult} result - */ - codeGeneration({ runtimeTemplate, moduleGraph, chunkGraph }) { - const runtimeRequirements = new Set([RuntimeGlobals.initializeSharing]); - const code = `register(${JSON.stringify(this._name)}, ${JSON.stringify( - this._version || "0" - )}, ${ - this._eager - ? runtimeTemplate.syncModuleFactory({ - dependency: this.dependencies[0], - chunkGraph, - request: this._request, - runtimeRequirements - }) - : runtimeTemplate.asyncModuleFactory({ - block: this.blocks[0], - chunkGraph, - request: this._request, - runtimeRequirements - }) - }${this._eager ? ", 1" : ""});`; - const sources = new Map(); - const data = new Map(); - data.set("share-init", [ - { - shareScope: this._shareScope, - initStage: 10, - init: code +/** + * @typedef {Object} SerializeResult + * @property {string | false} name + * @property {number} size + * @property {Promise=} backgroundJob + */ + +/** + * @param {FileMiddleware} middleware this + * @param {BufferSerializableType[] | Promise} data data to be serialized + * @param {string | boolean} name file base name + * @param {function(string | false, Buffer[]): Promise} writeFile writes a file + * @param {string | Hash} hashFunction hash function to use + * @returns {Promise} resulting file pointer and promise + */ +const serialize = async ( + middleware, + data, + name, + writeFile, + hashFunction = "md4" +) => { + /** @type {(Buffer[] | Buffer | SerializeResult | Promise)[]} */ + const processedData = []; + /** @type {WeakMap>} */ + const resultToLazy = new WeakMap(); + /** @type {Buffer[]} */ + let lastBuffers = undefined; + for (const item of await data) { + if (typeof item === "function") { + if (!SerializerMiddleware.isLazy(item)) + throw new Error("Unexpected function"); + if (!SerializerMiddleware.isLazy(item, middleware)) { + throw new Error( + "Unexpected lazy value with non-this target (can't pass through lazy values)" + ); } - ]); - return { sources, data, runtimeRequirements }; + lastBuffers = undefined; + const serializedInfo = SerializerMiddleware.getLazySerializedValue(item); + if (serializedInfo) { + if (typeof serializedInfo === "function") { + throw new Error( + "Unexpected lazy value with non-this target (can't pass through lazy values)" + ); + } else { + processedData.push(serializedInfo); + } + } else { + const content = item(); + if (content) { + const options = SerializerMiddleware.getLazyOptions(item); + processedData.push( + serialize( + middleware, + content, + (options && options.name) || true, + writeFile, + hashFunction + ).then(result => { + /** @type {any} */ (item).options.size = result.size; + resultToLazy.set(result, item); + return result; + }) + ); + } else { + throw new Error( + "Unexpected falsy value returned by lazy value function" + ); + } + } + } else if (item) { + if (lastBuffers) { + lastBuffers.push(item); + } else { + lastBuffers = [item]; + processedData.push(lastBuffers); + } + } else { + throw new Error("Unexpected falsy value in items array"); + } } + /** @type {Promise[]} */ + const backgroundJobs = []; + const resolvedData = ( + await Promise.all( + /** @type {Promise[]} */ ( + processedData + ) + ) + ).map(item => { + if (Array.isArray(item) || Buffer.isBuffer(item)) return item; - serialize(context) { - const { write } = context; - write(this._shareScope); - write(this._name); - write(this._version); - write(this._request); - write(this._eager); - super.serialize(context); + backgroundJobs.push(item.backgroundJob); + // create pointer buffer from size and name + const name = /** @type {string} */ (item.name); + const nameBuffer = Buffer.from(name); + const buf = Buffer.allocUnsafe(8 + nameBuffer.length); + writeUInt64LE(buf, item.size, 0); + nameBuffer.copy(buf, 8, 0); + const lazy = resultToLazy.get(item); + SerializerMiddleware.setLazySerializedValue(lazy, buf); + return buf; + }); + const lengths = []; + for (const item of resolvedData) { + if (Array.isArray(item)) { + let l = 0; + for (const b of item) l += b.length; + while (l > 0x7fffffff) { + lengths.push(0x7fffffff); + l -= 0x7fffffff; + } + lengths.push(l); + } else if (item) { + lengths.push(-item.length); + } else { + throw new Error("Unexpected falsy value in resolved data " + item); + } } - - static deserialize(context) { - const { read } = context; - const obj = new ProvideSharedModule(read(), read(), read(), read(), read()); - obj.deserialize(context); - return obj; + const header = Buffer.allocUnsafe(8 + lengths.length * 4); + header.writeUInt32LE(VERSION, 0); + header.writeUInt32LE(lengths.length, 4); + for (let i = 0; i < lengths.length; i++) { + header.writeInt32LE(lengths[i], 8 + i * 4); } -} - -makeSerializable( - ProvideSharedModule, - "webpack/lib/sharing/ProvideSharedModule" -); - -module.exports = ProvideSharedModule; - - -/***/ }), - -/***/ 89859: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra and Zackary Jackson @ScriptedAlchemy -*/ - - - -const ModuleFactory = __webpack_require__(61574); -const ProvideSharedModule = __webpack_require__(65945); - -/** @typedef {import("../ModuleFactory").ModuleFactoryCreateData} ModuleFactoryCreateData */ -/** @typedef {import("../ModuleFactory").ModuleFactoryResult} ModuleFactoryResult */ -/** @typedef {import("./ProvideSharedDependency")} ProvideSharedDependency */ - -class ProvideSharedModuleFactory extends ModuleFactory { - /** - * @param {ModuleFactoryCreateData} data data object - * @param {function(Error=, ModuleFactoryResult=): void} callback callback - * @returns {void} - */ - create(data, callback) { - const dep = /** @type {ProvideSharedDependency} */ (data.dependencies[0]); - callback(null, { - module: new ProvideSharedModule( - dep.shareScope, - dep.name, - dep.version, - dep.request, - dep.eager - ) - }); + const buf = [header]; + for (const item of resolvedData) { + if (Array.isArray(item)) { + for (const b of item) buf.push(b); + } else if (item) { + buf.push(item); + } } -} - -module.exports = ProvideSharedModuleFactory; - - -/***/ }), - -/***/ 42672: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra and Zackary Jackson @ScriptedAlchemy -*/ - - - -const WebpackError = __webpack_require__(68422); -const { parseOptions } = __webpack_require__(56084); -const createSchemaValidation = __webpack_require__(77695); -const ProvideForSharedDependency = __webpack_require__(40235); -const ProvideSharedDependency = __webpack_require__(99355); -const ProvideSharedModuleFactory = __webpack_require__(89859); - -/** @typedef {import("../../declarations/plugins/sharing/ProvideSharedPlugin").ProvideSharedPluginOptions} ProvideSharedPluginOptions */ -/** @typedef {import("../Compilation")} Compilation */ -/** @typedef {import("../Compiler")} Compiler */ - -const validate = createSchemaValidation( - __webpack_require__(31011), - () => __webpack_require__(12287), - { - name: "Provide Shared Plugin", - baseDataPath: "options" + if (name === true) { + name = hashForName(buf, hashFunction); } -); + backgroundJobs.push(writeFile(name, buf)); + let size = 0; + for (const b of buf) size += b.length; + return { + size, + name, + backgroundJob: + backgroundJobs.length === 1 + ? backgroundJobs[0] + : Promise.all(backgroundJobs) + }; +}; /** - * @typedef {Object} ProvideOptions - * @property {string} shareKey - * @property {string} shareScope - * @property {string | undefined | false} version - * @property {boolean} eager + * @param {FileMiddleware} middleware this + * @param {string | false} name filename + * @param {function(string | false): Promise} readFile read content of a file + * @returns {Promise} deserialized data */ - -/** @typedef {Map} ResolvedProvideMap */ - -class ProvideSharedPlugin { - /** - * @param {ProvideSharedPluginOptions} options options - */ - constructor(options) { - validate(options); - - /** @type {[string, ProvideOptions][]} */ - this._provides = parseOptions( - options.provides, - item => { - if (Array.isArray(item)) - throw new Error("Unexpected array of provides"); - /** @type {ProvideOptions} */ - const result = { - shareKey: item, - version: undefined, - shareScope: options.shareScope || "default", - eager: false - }; - return result; - }, - item => ({ - shareKey: item.shareKey, - version: item.version, - shareScope: item.shareScope || options.shareScope || "default", - eager: !!item.eager - }) - ); - this._provides.sort(([a], [b]) => { - if (a < b) return -1; - if (b < a) return 1; - return 0; - }); - } - - /** - * Apply the plugin - * @param {Compiler} compiler the compiler instance - * @returns {void} - */ - apply(compiler) { - /** @type {WeakMap} */ - const compilationData = new WeakMap(); - - compiler.hooks.compilation.tap( - "ProvideSharedPlugin", - (compilation, { normalModuleFactory }) => { - /** @type {ResolvedProvideMap} */ - const resolvedProvideMap = new Map(); - /** @type {Map} */ - const matchProvides = new Map(); - /** @type {Map} */ - const prefixMatchProvides = new Map(); - for (const [request, config] of this._provides) { - if (/^(\/|[A-Za-z]:\\|\\\\|\.\.?(\/|$))/.test(request)) { - // relative request - resolvedProvideMap.set(request, { - config, - version: config.version - }); - } else if (/^(\/|[A-Za-z]:\\|\\\\)/.test(request)) { - // absolute path - resolvedProvideMap.set(request, { - config, - version: config.version - }); - } else if (request.endsWith("/")) { - // module request prefix - prefixMatchProvides.set(request, config); - } else { - // module request - matchProvides.set(request, config); - } +const deserialize = async (middleware, name, readFile) => { + const contents = await readFile(name); + if (contents.length === 0) throw new Error("Empty file " + name); + let contentsIndex = 0; + let contentItem = contents[0]; + let contentItemLength = contentItem.length; + let contentPosition = 0; + if (contentItemLength === 0) throw new Error("Empty file " + name); + const nextContent = () => { + contentsIndex++; + contentItem = contents[contentsIndex]; + contentItemLength = contentItem.length; + contentPosition = 0; + }; + const ensureData = n => { + if (contentPosition === contentItemLength) { + nextContent(); + } + while (contentItemLength - contentPosition < n) { + const remaining = contentItem.slice(contentPosition); + let lengthFromNext = n - remaining.length; + const buffers = [remaining]; + for (let i = contentsIndex + 1; i < contents.length; i++) { + const l = contents[i].length; + if (l > lengthFromNext) { + buffers.push(contents[i].slice(0, lengthFromNext)); + contents[i] = contents[i].slice(lengthFromNext); + lengthFromNext = 0; + break; + } else { + buffers.push(contents[i]); + contentsIndex = i; + lengthFromNext -= l; } - compilationData.set(compilation, resolvedProvideMap); - const provideSharedModule = ( - key, - config, - resource, - resourceResolveData - ) => { - let version = config.version; - if (version === undefined) { - let details = ""; - if (!resourceResolveData) { - details = `No resolve data provided from resolver.`; - } else { - const descriptionFileData = - resourceResolveData.descriptionFileData; - if (!descriptionFileData) { - details = - "No description file (usually package.json) found. Add description file with name and version, or manually specify version in shared config."; - } else if (!descriptionFileData.version) { - details = - "No version in description file (usually package.json). Add version to description file, or manually specify version in shared config."; - } else { - version = descriptionFileData.version; - } - } - if (!version) { - const error = new WebpackError( - `No version specified and unable to automatically determine one. ${details}` - ); - error.file = `shared module ${key} -> ${resource}`; - compilation.warnings.push(error); - } - } - resolvedProvideMap.set(resource, { - config, - version - }); - }; - normalModuleFactory.hooks.module.tap( - "ProvideSharedPlugin", - (module, { resource, resourceResolveData }, resolveData) => { - if (resolvedProvideMap.has(resource)) { - return module; - } - const { request } = resolveData; - { - const config = matchProvides.get(request); - if (config !== undefined) { - provideSharedModule( - request, - config, - resource, - resourceResolveData - ); - resolveData.cacheable = false; - } - } - for (const [prefix, config] of prefixMatchProvides) { - if (request.startsWith(prefix)) { - const remainder = request.slice(prefix.length); - provideSharedModule( - resource, - { - ...config, - shareKey: config.shareKey + remainder - }, - resource, - resourceResolveData - ); - resolveData.cacheable = false; - } - } - return module; - } - ); } - ); - compiler.hooks.finishMake.tapPromise("ProvideSharedPlugin", compilation => { - const resolvedProvideMap = compilationData.get(compilation); - if (!resolvedProvideMap) return Promise.resolve(); - return Promise.all( - Array.from( - resolvedProvideMap, - ([resource, { config, version }]) => - new Promise((resolve, reject) => { - compilation.addInclude( - compiler.context, - new ProvideSharedDependency( - config.shareScope, - config.shareKey, - version || false, - resource, - config.eager - ), - { - name: undefined - }, - err => { - if (err) return reject(err); - resolve(); - } - ); - }) + if (lengthFromNext > 0) throw new Error("Unexpected end of data"); + contentItem = Buffer.concat(buffers, n); + contentItemLength = n; + contentPosition = 0; + } + }; + const readUInt32LE = () => { + ensureData(4); + const value = contentItem.readUInt32LE(contentPosition); + contentPosition += 4; + return value; + }; + const readInt32LE = () => { + ensureData(4); + const value = contentItem.readInt32LE(contentPosition); + contentPosition += 4; + return value; + }; + const readSlice = l => { + ensureData(l); + if (contentPosition === 0 && contentItemLength === l) { + const result = contentItem; + if (contentsIndex + 1 < contents.length) { + nextContent(); + } else { + contentPosition = l; + } + return result; + } + const result = contentItem.slice(contentPosition, contentPosition + l); + contentPosition += l; + // we clone the buffer here to allow the original content to be garbage collected + return l * 2 < contentItem.buffer.byteLength ? Buffer.from(result) : result; + }; + const version = readUInt32LE(); + if (version !== VERSION) { + throw new Error("Invalid file version"); + } + const sectionCount = readUInt32LE(); + const lengths = []; + let lastLengthPositive = false; + for (let i = 0; i < sectionCount; i++) { + const value = readInt32LE(); + const valuePositive = value >= 0; + if (lastLengthPositive && valuePositive) { + lengths[lengths.length - 1] += value; + } else { + lengths.push(value); + lastLengthPositive = valuePositive; + } + } + const result = []; + for (let length of lengths) { + if (length < 0) { + const slice = readSlice(-length); + const size = Number(readUInt64LE(slice, 0)); + const nameBuffer = slice.slice(8); + const name = nameBuffer.toString(); + result.push( + SerializerMiddleware.createLazy( + memoize(() => deserialize(middleware, name, readFile)), + middleware, + { + name, + size + }, + slice ) - ).then(() => {}); - }); - - compiler.hooks.compilation.tap( - "ProvideSharedPlugin", - (compilation, { normalModuleFactory }) => { - compilation.dependencyFactories.set( - ProvideForSharedDependency, - normalModuleFactory - ); - - compilation.dependencyFactories.set( - ProvideSharedDependency, - new ProvideSharedModuleFactory() - ); + ); + } else { + if (contentPosition === contentItemLength) { + nextContent(); + } else if (contentPosition !== 0) { + if (length <= contentItemLength - contentPosition) { + result.push( + Buffer.from( + contentItem.buffer, + contentItem.byteOffset + contentPosition, + length + ) + ); + contentPosition += length; + length = 0; + } else { + const l = contentItemLength - contentPosition; + result.push( + Buffer.from( + contentItem.buffer, + contentItem.byteOffset + contentPosition, + l + ) + ); + length -= l; + contentPosition = contentItemLength; + } + } else { + if (length >= contentItemLength) { + result.push(contentItem); + length -= contentItemLength; + contentPosition = contentItemLength; + } else { + result.push( + Buffer.from(contentItem.buffer, contentItem.byteOffset, length) + ); + contentPosition += length; + length = 0; + } + } + while (length > 0) { + nextContent(); + if (length >= contentItemLength) { + result.push(contentItem); + length -= contentItemLength; + contentPosition = contentItemLength; + } else { + result.push( + Buffer.from(contentItem.buffer, contentItem.byteOffset, length) + ); + contentPosition += length; + length = 0; + } } - ); + } } -} - -module.exports = ProvideSharedPlugin; - - -/***/ }), - -/***/ 25790: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra and Zackary Jackson @ScriptedAlchemy -*/ - - - -const { parseOptions } = __webpack_require__(56084); -const ConsumeSharedPlugin = __webpack_require__(19984); -const ProvideSharedPlugin = __webpack_require__(42672); -const { isRequiredVersion } = __webpack_require__(58854); - -/** @typedef {import("../../declarations/plugins/sharing/ConsumeSharedPlugin").ConsumeSharedPluginOptions} ConsumeSharedPluginOptions */ -/** @typedef {import("../../declarations/plugins/sharing/ConsumeSharedPlugin").ConsumesConfig} ConsumesConfig */ -/** @typedef {import("../../declarations/plugins/sharing/ProvideSharedPlugin").ProvideSharedPluginOptions} ProvideSharedPluginOptions */ -/** @typedef {import("../../declarations/plugins/sharing/ProvideSharedPlugin").ProvidesConfig} ProvidesConfig */ -/** @typedef {import("../../declarations/plugins/sharing/SharePlugin").SharePluginOptions} SharePluginOptions */ -/** @typedef {import("../../declarations/plugins/sharing/SharePlugin").SharedConfig} SharedConfig */ -/** @typedef {import("../Compiler")} Compiler */ + return result; +}; -class SharePlugin { +/** + * @typedef {BufferSerializableType[]} DeserializedType + * @typedef {true} SerializedType + * @extends {SerializerMiddleware} + */ +class FileMiddleware extends SerializerMiddleware { /** - * @param {SharePluginOptions} options options + * @param {IntermediateFileSystem} fs filesystem + * @param {string | Hash} hashFunction hash function to use */ - constructor(options) { - /** @type {[string, SharedConfig][]} */ - const sharedOptions = parseOptions( - options.shared, - (item, key) => { - if (typeof item !== "string") - throw new Error("Unexpected array in shared"); - /** @type {SharedConfig} */ - const config = - item === key || !isRequiredVersion(item) - ? { - import: item - } - : { - import: key, - requiredVersion: item - }; - return config; - }, - item => item - ); - /** @type {Record[]} */ - const consumes = sharedOptions.map(([key, options]) => ({ - [key]: { - import: options.import, - shareKey: options.shareKey || key, - shareScope: options.shareScope, - requiredVersion: options.requiredVersion, - strictVersion: options.strictVersion, - singleton: options.singleton, - packageName: options.packageName, - eager: options.eager - } - })); - /** @type {Record[]} */ - const provides = sharedOptions - .filter(([, options]) => options.import !== false) - .map(([key, options]) => ({ - [options.import || key]: { - shareKey: options.shareKey || key, - shareScope: options.shareScope, - version: options.version, - eager: options.eager - } - })); - this._shareScope = options.shareScope; - this._consumes = consumes; - this._provides = provides; + constructor(fs, hashFunction = "md4") { + super(); + this.fs = fs; + this._hashFunction = hashFunction; } - /** - * Apply the plugin - * @param {Compiler} compiler the compiler instance - * @returns {void} + * @param {DeserializedType} data data + * @param {Object} context context object + * @returns {SerializedType|Promise} serialized data */ - apply(compiler) { - new ConsumeSharedPlugin({ - shareScope: this._shareScope, - consumes: this._consumes - }).apply(compiler); - new ProvideSharedPlugin({ - shareScope: this._shareScope, - provides: this._provides - }).apply(compiler); - } -} - -module.exports = SharePlugin; - - -/***/ }), - -/***/ 97207: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + serialize(data, context) { + const { filename, extension = "" } = context; + return new Promise((resolve, reject) => { + mkdirp(this.fs, dirname(this.fs, filename), err => { + if (err) return reject(err); -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ + // It's important that we don't touch existing files during serialization + // because serialize may read existing files (when deserializing) + const allWrittenFiles = new Set(); + const writeFile = async (name, content) => { + const file = name + ? join(this.fs, filename, `../${name}${extension}`) + : filename; + await new Promise((resolve, reject) => { + let stream = this.fs.createWriteStream(file + "_"); + let compression; + if (file.endsWith(".gz")) { + compression = createGzip({ + chunkSize: COMPRESSION_CHUNK_SIZE, + level: zConstants.Z_BEST_SPEED + }); + } else if (file.endsWith(".br")) { + compression = createBrotliCompress({ + chunkSize: COMPRESSION_CHUNK_SIZE, + params: { + [zConstants.BROTLI_PARAM_MODE]: zConstants.BROTLI_MODE_TEXT, + [zConstants.BROTLI_PARAM_QUALITY]: 2, + [zConstants.BROTLI_PARAM_DISABLE_LITERAL_CONTEXT_MODELING]: true, + [zConstants.BROTLI_PARAM_SIZE_HINT]: content.reduce( + (size, b) => size + b.length, + 0 + ) + } + }); + } + if (compression) { + pipeline(compression, stream, reject); + stream = compression; + stream.on("finish", () => resolve()); + } else { + stream.on("error", err => reject(err)); + stream.on("finish", () => resolve()); + } + for (const b of content) stream.write(b); + stream.end(); + }); + if (name) allWrittenFiles.add(file); + }; + resolve( + serialize(this, data, false, writeFile, this._hashFunction).then( + async ({ backgroundJob }) => { + await backgroundJob; + // Rename the index file to disallow access during inconsistent file state + await new Promise(resolve => + this.fs.rename(filename, filename + ".old", err => { + resolve(); + }) + ); -const RuntimeGlobals = __webpack_require__(49404); -const RuntimeModule = __webpack_require__(61439); -const Template = __webpack_require__(92066); -const { - compareModulesByIdentifier, - compareStrings -} = __webpack_require__(26296); + // update all written files + await Promise.all( + Array.from( + allWrittenFiles, + file => + new Promise((resolve, reject) => { + this.fs.rename(file + "_", file, err => { + if (err) return reject(err); + resolve(); + }); + }) + ) + ); -class ShareRuntimeModule extends RuntimeModule { - constructor() { - super("sharing"); + // As final step automatically update the index file to have a consistent pack again + await new Promise(resolve => { + this.fs.rename(filename + "_", filename, err => { + if (err) return reject(err); + resolve(); + }); + }); + return /** @type {true} */ (true); + } + ) + ); + }); + }); } /** - * @returns {string} runtime code + * @param {SerializedType} data data + * @param {Object} context context object + * @returns {DeserializedType|Promise} deserialized data */ - generate() { - const { compilation, chunkGraph } = this; - const { - runtimeTemplate, - codeGenerationResults, - outputOptions: { uniqueName } - } = compilation; - /** @type {Map>>} */ - const initCodePerScope = new Map(); - for (const chunk of this.chunk.getAllReferencedChunks()) { - const modules = chunkGraph.getOrderedChunkModulesIterableBySourceType( - chunk, - "share-init", - compareModulesByIdentifier - ); - if (!modules) continue; - for (const m of modules) { - const data = codeGenerationResults.getData( - m, - chunk.runtime, - "share-init" - ); - if (!data) continue; - for (const item of data) { - const { shareScope, initStage, init } = item; - let stages = initCodePerScope.get(shareScope); - if (stages === undefined) { - initCodePerScope.set(shareScope, (stages = new Map())); + deserialize(data, context) { + const { filename, extension = "" } = context; + const readFile = name => + new Promise((resolve, reject) => { + const file = name + ? join(this.fs, filename, `../${name}${extension}`) + : filename; + this.fs.stat(file, (err, stats) => { + if (err) { + reject(err); + return; } - let list = stages.get(initStage || 0); - if (list === undefined) { - stages.set(initStage || 0, (list = new Set())); + let remaining = /** @type {number} */ (stats.size); + let currentBuffer; + let currentBufferUsed; + const buf = []; + let decompression; + if (file.endsWith(".gz")) { + decompression = createGunzip({ + chunkSize: DECOMPRESSION_CHUNK_SIZE + }); + } else if (file.endsWith(".br")) { + decompression = createBrotliDecompress({ + chunkSize: DECOMPRESSION_CHUNK_SIZE + }); } - list.add(init); - } - } - } - return Template.asString([ - `${RuntimeGlobals.shareScopeMap} = {};`, - "var initPromises = {};", - "var initTokens = {};", - `${RuntimeGlobals.initializeSharing} = ${runtimeTemplate.basicFunction( - "name, initScope", - [ - "if(!initScope) initScope = [];", - "// handling circular init calls", - "var initToken = initTokens[name];", - "if(!initToken) initToken = initTokens[name] = {};", - "if(initScope.indexOf(initToken) >= 0) return;", - "initScope.push(initToken);", - "// only runs once", - "if(initPromises[name]) return initPromises[name];", - "// creates a new share scope if needed", - `if(!${RuntimeGlobals.hasOwnProperty}(${RuntimeGlobals.shareScopeMap}, name)) ${RuntimeGlobals.shareScopeMap}[name] = {};`, - "// runs all init snippets from all modules reachable", - `var scope = ${RuntimeGlobals.shareScopeMap}[name];`, - `var warn = ${runtimeTemplate.returningFunction( - 'typeof console !== "undefined" && console.warn && console.warn(msg)', - "msg" - )};`, - `var uniqueName = ${JSON.stringify(uniqueName || undefined)};`, - `var register = ${runtimeTemplate.basicFunction( - "name, version, factory, eager", - [ - "var versions = scope[name] = scope[name] || {};", - "var activeVersion = versions[version];", - "if(!activeVersion || (!activeVersion.loaded && (!eager != !activeVersion.eager ? eager : uniqueName > activeVersion.from))) versions[version] = { get: factory, from: uniqueName, eager: !!eager };" - ] - )};`, - `var initExternal = ${runtimeTemplate.basicFunction("id", [ - `var handleError = ${runtimeTemplate.expressionFunction( - 'warn("Initialization of sharing external failed: " + err)', - "err" - )};`, - "try {", - Template.indent([ - "var module = __webpack_require__(id);", - "if(!module) return;", - `var initFn = ${runtimeTemplate.returningFunction( - `module && module.init && module.init(${RuntimeGlobals.shareScopeMap}[name], initScope)`, - "module" - )}`, - "if(module.then) return promises.push(module.then(initFn, handleError));", - "var initResult = initFn(module);", - "if(initResult && initResult.then) return promises.push(initResult['catch'](handleError));" - ]), - "} catch(err) { handleError(err); }" - ])}`, - "var promises = [];", - "switch(name) {", - ...Array.from(initCodePerScope) - .sort(([a], [b]) => compareStrings(a, b)) - .map(([name, stages]) => - Template.indent([ - `case ${JSON.stringify(name)}: {`, - Template.indent( - Array.from(stages) - .sort(([a], [b]) => a - b) - .map(([, initCode]) => - Template.asString(Array.from(initCode)) - ) - ), - "}", - "break;" - ]) - ), - "}", - "if(!promises.length) return initPromises[name] = 1;", - `return initPromises[name] = Promise.all(promises).then(${runtimeTemplate.returningFunction( - "initPromises[name] = 1" - )});` - ] - )};` - ]); - } -} - -module.exports = ShareRuntimeModule; - - -/***/ }), - -/***/ 18436: -/***/ (function(__unused_webpack_module, exports, __webpack_require__) { - -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ - - - -const ModuleNotFoundError = __webpack_require__(82908); -const LazySet = __webpack_require__(59534); - -/** @typedef {import("../Compilation")} Compilation */ -/** @typedef {import("../ResolverFactory").ResolveOptionsWithDependencyType} ResolveOptionsWithDependencyType */ - -/** - * @template T - * @typedef {Object} MatchedConfigs - * @property {Map} resolved - * @property {Map} unresolved - * @property {Map} prefixed - */ - -/** @type {ResolveOptionsWithDependencyType} */ -const RESOLVE_OPTIONS = { dependencyType: "esm" }; - -/** - * @template T - * @param {Compilation} compilation the compilation - * @param {[string, T][]} configs to be processed configs - * @returns {Promise>} resolved matchers - */ -exports.resolveMatchedConfigs = (compilation, configs) => { - /** @type {Map} */ - const resolved = new Map(); - /** @type {Map} */ - const unresolved = new Map(); - /** @type {Map} */ - const prefixed = new Map(); - const resolveContext = { - /** @type {LazySet} */ - fileDependencies: new LazySet(), - /** @type {LazySet} */ - contextDependencies: new LazySet(), - /** @type {LazySet} */ - missingDependencies: new LazySet() - }; - const resolver = compilation.resolverFactory.get("normal", RESOLVE_OPTIONS); - const context = compilation.compiler.context; - - return Promise.all( - configs.map(([request, config]) => { - if (/^\.\.?(\/|$)/.test(request)) { - // relative request - return new Promise(resolve => { - resolver.resolve( - {}, - context, - request, - resolveContext, - (err, result) => { - if (err || result === false) { - err = err || new Error(`Can't resolve ${request}`); - compilation.errors.push( - new ModuleNotFoundError(null, err, { - name: `shared module ${request}` - }) + if (decompression) { + let newResolve, newReject; + resolve( + Promise.all([ + new Promise((rs, rj) => { + newResolve = rs; + newReject = rj; + }), + new Promise((resolve, reject) => { + decompression.on("data", chunk => buf.push(chunk)); + decompression.on("end", () => resolve()); + decompression.on("error", err => reject(err)); + }) + ]).then(() => buf) + ); + resolve = newResolve; + reject = newReject; + } + this.fs.open(file, "r", (err, fd) => { + if (err) { + reject(err); + return; + } + const read = () => { + if (currentBuffer === undefined) { + currentBuffer = Buffer.allocUnsafeSlow( + Math.min( + constants.MAX_LENGTH, + remaining, + decompression ? DECOMPRESSION_CHUNK_SIZE : Infinity + ) ); - return resolve(); + currentBufferUsed = 0; } - resolved.set(result, config); - resolve(); - } - ); + let readBuffer = currentBuffer; + let readOffset = currentBufferUsed; + let readLength = currentBuffer.length - currentBufferUsed; + // values passed to fs.read must be valid int32 values + if (readOffset > 0x7fffffff) { + readBuffer = currentBuffer.slice(readOffset); + readOffset = 0; + } + if (readLength > 0x7fffffff) { + readLength = 0x7fffffff; + } + this.fs.read( + fd, + readBuffer, + readOffset, + readLength, + null, + (err, bytesRead) => { + if (err) { + this.fs.close(fd, () => { + reject(err); + }); + return; + } + currentBufferUsed += bytesRead; + remaining -= bytesRead; + if (currentBufferUsed === currentBuffer.length) { + if (decompression) { + decompression.write(currentBuffer); + } else { + buf.push(currentBuffer); + } + currentBuffer = undefined; + if (remaining === 0) { + if (decompression) { + decompression.end(); + } + this.fs.close(fd, err => { + if (err) { + reject(err); + return; + } + resolve(buf); + }); + return; + } + } + read(); + } + ); + }; + read(); + }); }); - } else if (/^(\/|[A-Za-z]:\\|\\\\)/.test(request)) { - // absolute path - resolved.set(request, config); - } else if (request.endsWith("/")) { - // module request prefix - prefixed.set(request, config); - } else { - // module request - unresolved.set(request, config); - } - }) - ).then(() => { - compilation.contextDependencies.addAll(resolveContext.contextDependencies); - compilation.fileDependencies.addAll(resolveContext.fileDependencies); - compilation.missingDependencies.addAll(resolveContext.missingDependencies); - return { resolved, unresolved, prefixed }; - }); -}; + }); + return deserialize(this, false, readFile); + } +} + +module.exports = FileMiddleware; /***/ }), -/***/ 58854: -/***/ (function(__unused_webpack_module, exports, __webpack_require__) { +/***/ 82547: +/***/ (function(module) { "use strict"; /* MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra */ -const { join, dirname, readJson } = __webpack_require__(93204); - -/** @typedef {import("../util/fs").InputFileSystem} InputFileSystem */ - -/** - * @param {string} str maybe required version - * @returns {boolean} true, if it looks like a version - */ -exports.isRequiredVersion = str => { - return /^([\d^=v<>~]|[*xX]$)/.test(str); -}; - -/** - * - * @param {InputFileSystem} fs file system - * @param {string} directory directory to start looking into - * @param {string[]} descriptionFiles possible description filenames - * @param {function(Error=, {data: object, path: string}=): void} callback callback - */ -const getDescriptionFile = (fs, directory, descriptionFiles, callback) => { - let i = 0; - const tryLoadCurrent = () => { - if (i >= descriptionFiles.length) { - const parentDirectory = dirname(fs, directory); - if (!parentDirectory || parentDirectory === directory) return callback(); - return getDescriptionFile( - fs, - parentDirectory, - descriptionFiles, - callback - ); +class MapObjectSerializer { + serialize(obj, { write }) { + write(obj.size); + for (const key of obj.keys()) { + write(key); + } + for (const value of obj.values()) { + write(value); } - const filePath = join(fs, directory, descriptionFiles[i]); - readJson(fs, filePath, (err, data) => { - if (err) { - if ("code" in err && err.code === "ENOENT") { - i++; - return tryLoadCurrent(); - } - return callback(err); - } - if (!data || typeof data !== "object" || Array.isArray(data)) { - return callback( - new Error(`Description file ${filePath} is not an object`) - ); - } - callback(null, { data, path: filePath }); - }); - }; - tryLoadCurrent(); -}; -exports.getDescriptionFile = getDescriptionFile; - -exports.getRequiredVersionFromDescriptionFile = (data, packageName) => { - if ( - data.optionalDependencies && - typeof data.optionalDependencies === "object" && - packageName in data.optionalDependencies - ) { - return data.optionalDependencies[packageName]; - } - if ( - data.dependencies && - typeof data.dependencies === "object" && - packageName in data.dependencies - ) { - return data.dependencies[packageName]; - } - if ( - data.peerDependencies && - typeof data.peerDependencies === "object" && - packageName in data.peerDependencies - ) { - return data.peerDependencies[packageName]; } - if ( - data.devDependencies && - typeof data.devDependencies === "object" && - packageName in data.devDependencies - ) { - return data.devDependencies[packageName]; + deserialize({ read }) { + let size = read(); + const map = new Map(); + const keys = []; + for (let i = 0; i < size; i++) { + keys.push(read()); + } + for (let i = 0; i < size; i++) { + map.set(keys[i], read()); + } + return map; } -}; +} + +module.exports = MapObjectSerializer; /***/ }), -/***/ 91293: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { +/***/ 52985: +/***/ (function(module) { "use strict"; /* MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra */ -const util = __webpack_require__(31669); -const ModuleDependency = __webpack_require__(80944); -const formatLocation = __webpack_require__(57261); -const { LogType } = __webpack_require__(54667); -const AggressiveSplittingPlugin = __webpack_require__(10055); -const SizeLimitsPlugin = __webpack_require__(64025); -const { countIterable } = __webpack_require__(31065); -const { - compareLocations, - compareChunksById, - compareNumbers, - compareIds, - concatComparators, - compareSelect, - compareModulesByIdentifier -} = __webpack_require__(26296); -const { makePathsRelative, parseResource } = __webpack_require__(96236); - -/** @typedef {import("webpack-sources").Source} Source */ -/** @typedef {import("../Chunk")} Chunk */ -/** @typedef {import("../ChunkGroup")} ChunkGroup */ -/** @typedef {import("../ChunkGroup").OriginRecord} OriginRecord */ -/** @typedef {import("../Compilation")} Compilation */ -/** @typedef {import("../Compilation").Asset} Asset */ -/** @typedef {import("../Compilation").AssetInfo} AssetInfo */ -/** @typedef {import("../Compilation").NormalizedStatsOptions} NormalizedStatsOptions */ -/** @typedef {import("../Compiler")} Compiler */ -/** @typedef {import("../Dependency")} Dependency */ -/** @typedef {import("../Dependency").DependencyLocation} DependencyLocation */ -/** @typedef {import("../Module")} Module */ -/** @typedef {import("../ModuleGraphConnection")} ModuleGraphConnection */ -/** @typedef {import("../ModuleProfile")} ModuleProfile */ -/** @typedef {import("../RequestShortener")} RequestShortener */ -/** @typedef {import("../WebpackError")} WebpackError */ -/** @template T @typedef {import("../util/comparators").Comparator} Comparator */ -/** @typedef {import("../util/runtime").RuntimeSpec} RuntimeSpec */ -/** @typedef {import("../util/smartGrouping").GroupConfig} GroupConfig */ -/** @typedef {import("./StatsFactory")} StatsFactory */ -/** @typedef {import("./StatsFactory").StatsFactoryContext} StatsFactoryContext */ +class NullPrototypeObjectSerializer { + serialize(obj, { write }) { + const keys = Object.keys(obj); + for (const key of keys) { + write(key); + } + write(null); + for (const key of keys) { + write(obj[key]); + } + } + deserialize({ read }) { + const obj = Object.create(null); + const keys = []; + let key = read(); + while (key !== null) { + keys.push(key); + key = read(); + } + for (const key of keys) { + obj[key] = read(); + } + return obj; + } +} -/** @typedef {KnownStatsCompilation & Record} StatsCompilation */ -/** - * @typedef {Object} KnownStatsCompilation - * @property {any=} env - * @property {string=} name - * @property {string=} hash - * @property {string=} version - * @property {number=} time - * @property {number=} builtAt - * @property {boolean=} needAdditionalPass - * @property {string=} publicPath - * @property {string=} outputPath - * @property {Record=} assetsByChunkName - * @property {StatsAsset[]=} assets - * @property {number=} filteredAssets - * @property {StatsChunk[]=} chunks - * @property {StatsModule[]=} modules - * @property {number=} filteredModules - * @property {Record=} entrypoints - * @property {Record=} namedChunkGroups - * @property {StatsError[]=} errors - * @property {number=} errorsCount - * @property {StatsError[]=} warnings - * @property {number=} warningsCount - * @property {StatsCompilation[]=} children - * @property {Record=} logging - */ +module.exports = NullPrototypeObjectSerializer; -/** @typedef {KnownStatsLogging & Record} StatsLogging */ -/** - * @typedef {Object} KnownStatsLogging - * @property {StatsLoggingEntry[]} entries - * @property {number} filteredEntries - * @property {boolean} debug - */ -/** @typedef {KnownStatsLoggingEntry & Record} StatsLoggingEntry */ -/** - * @typedef {Object} KnownStatsLoggingEntry - * @property {string} type - * @property {string} message - * @property {string[]=} trace - * @property {StatsLoggingEntry[]=} children - * @property {any[]=} args - * @property {number=} time - */ +/***/ }), -/** @typedef {KnownStatsAsset & Record} StatsAsset */ -/** - * @typedef {Object} KnownStatsAsset - * @property {string} type - * @property {string} name - * @property {AssetInfo} info - * @property {number} size - * @property {boolean} emitted - * @property {boolean} comparedForEmit - * @property {boolean} cached - * @property {StatsAsset[]=} related - * @property {(string|number)[]=} chunkNames - * @property {(string|number)[]=} chunkIdHints - * @property {(string|number)[]=} chunks - * @property {(string|number)[]=} auxiliaryChunkNames - * @property {(string|number)[]=} auxiliaryChunks - * @property {(string|number)[]=} auxiliaryChunkIdHints - * @property {number=} filteredRelated - * @property {boolean=} isOverSizeLimit - */ +/***/ 77815: +/***/ (function(module, exports, __webpack_require__) { -/** @typedef {KnownStatsChunkGroup & Record} StatsChunkGroup */ -/** - * @typedef {Object} KnownStatsChunkGroup - * @property {string=} name - * @property {(string|number)[]=} chunks - * @property {({ name: string, size?: number })[]=} assets - * @property {number=} filteredAssets - * @property {number=} assetsSize - * @property {({ name: string, size?: number })[]=} auxiliaryAssets - * @property {number=} filteredAuxiliaryAssets - * @property {number=} auxiliaryAssetsSize - * @property {{ [x: string]: StatsChunkGroup[] }=} children - * @property {{ [x: string]: string[] }=} childAssets - * @property {boolean=} isOverSizeLimit - */ +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php +*/ -/** @typedef {KnownStatsModule & Record} StatsModule */ -/** - * @typedef {Object} KnownStatsModule - * @property {string=} type - * @property {string=} moduleType - * @property {string=} layer - * @property {string=} identifier - * @property {string=} name - * @property {string=} nameForCondition - * @property {number=} index - * @property {number=} preOrderIndex - * @property {number=} index2 - * @property {number=} postOrderIndex - * @property {number=} size - * @property {{[x: string]: number}=} sizes - * @property {boolean=} cacheable - * @property {boolean=} built - * @property {boolean=} codeGenerated - * @property {boolean=} buildTimeExecuted - * @property {boolean=} cached - * @property {boolean=} optional - * @property {boolean=} orphan - * @property {string|number=} id - * @property {string|number=} issuerId - * @property {(string|number)[]=} chunks - * @property {(string|number)[]=} assets - * @property {boolean=} dependent - * @property {string=} issuer - * @property {string=} issuerName - * @property {StatsModuleIssuer[]=} issuerPath - * @property {boolean=} failed - * @property {number=} errors - * @property {number=} warnings - * @property {StatsProfile=} profile - * @property {StatsModuleReason[]=} reasons - * @property {(boolean | string[])=} usedExports - * @property {string[]=} providedExports - * @property {string[]=} optimizationBailout - * @property {number=} depth - * @property {StatsModule[]=} modules - * @property {number=} filteredModules - * @property {ReturnType=} source - */ -/** @typedef {KnownStatsProfile & Record} StatsProfile */ -/** - * @typedef {Object} KnownStatsProfile - * @property {number} total - * @property {number} resolving - * @property {number} restoring - * @property {number} building - * @property {number} integration - * @property {number} storing - * @property {number} additionalResolving - * @property {number} additionalIntegration - * @property {number} factory - * @property {number} dependencies - */ -/** @typedef {KnownStatsModuleIssuer & Record} StatsModuleIssuer */ -/** - * @typedef {Object} KnownStatsModuleIssuer - * @property {string=} identifier - * @property {string=} name - * @property {(string|number)=} id - * @property {StatsProfile=} profile - */ +const createHash = __webpack_require__(24123); +const ArraySerializer = __webpack_require__(80573); +const DateObjectSerializer = __webpack_require__(32973); +const ErrorObjectSerializer = __webpack_require__(60252); +const MapObjectSerializer = __webpack_require__(82547); +const NullPrototypeObjectSerializer = __webpack_require__(52985); +const PlainObjectSerializer = __webpack_require__(24298); +const RegExpObjectSerializer = __webpack_require__(90410); +const SerializerMiddleware = __webpack_require__(37063); +const SetObjectSerializer = __webpack_require__(85199); -/** @typedef {KnownStatsModuleReason & Record} StatsModuleReason */ -/** - * @typedef {Object} KnownStatsModuleReason - * @property {string=} moduleIdentifier - * @property {string=} module - * @property {string=} moduleName - * @property {string=} resolvedModuleIdentifier - * @property {string=} resolvedModule - * @property {string=} type - * @property {boolean} active - * @property {string=} explanation - * @property {string=} userRequest - * @property {string=} loc - * @property {(string|number)=} moduleId - * @property {(string|number)=} resolvedModuleId - */ +/** @typedef {typeof import("../util/Hash")} Hash */ +/** @typedef {import("./types").ComplexSerializableType} ComplexSerializableType */ +/** @typedef {import("./types").PrimitiveSerializableType} PrimitiveSerializableType */ -/** @typedef {KnownStatsChunk & Record} StatsChunk */ -/** - * @typedef {Object} KnownStatsChunk - * @property {boolean} rendered - * @property {boolean} initial - * @property {boolean} entry - * @property {boolean} recorded - * @property {string=} reason - * @property {number} size - * @property {Record=} sizes - * @property {string[]=} names - * @property {string[]=} idHints - * @property {string[]=} runtime - * @property {string[]=} files - * @property {string[]=} auxiliaryFiles - * @property {string} hash - * @property {Record=} childrenByOrder - * @property {(string|number)=} id - * @property {(string|number)[]=} siblings - * @property {(string|number)[]=} parents - * @property {(string|number)[]=} children - * @property {StatsModule[]=} modules - * @property {number=} filteredModules - * @property {StatsChunkOrigin[]=} origins - */ +/** @typedef {new (...params: any[]) => any} Constructor */ -/** @typedef {KnownStatsChunkOrigin & Record} StatsChunkOrigin */ -/** - * @typedef {Object} KnownStatsChunkOrigin - * @property {string=} module - * @property {string=} moduleIdentifier - * @property {string=} moduleName - * @property {string=} loc - * @property {string=} request - * @property {(string|number)=} moduleId - */ +/* -/** @typedef {KnownStatsModuleTraceItem & Record} StatsModuleTraceItem */ -/** - * @typedef {Object} KnownStatsModuleTraceItem - * @property {string=} originIdentifier - * @property {string=} originName - * @property {string=} moduleIdentifier - * @property {string=} moduleName - * @property {StatsModuleTraceDependency[]=} dependencies - * @property {(string|number)=} originId - * @property {(string|number)=} moduleId - */ +Format: -/** @typedef {KnownStatsModuleTraceDependency & Record} StatsModuleTraceDependency */ -/** - * @typedef {Object} KnownStatsModuleTraceDependency - * @property {string=} loc - */ +File -> Section* +Section -> ObjectSection | ReferenceSection | EscapeSection | OtherSection -/** @typedef {KnownStatsError & Record} StatsError */ -/** - * @typedef {Object} KnownStatsError - * @property {string} message - * @property {string=} chunkName - * @property {boolean=} chunkEntry - * @property {boolean=} chunkInitial - * @property {string=} file - * @property {string=} moduleIdentifier - * @property {string=} moduleName - * @property {string=} loc - * @property {string|number=} chunkId - * @property {string|number=} moduleId - * @property {StatsModuleTraceItem[]=} moduleTrace - * @property {any=} details - * @property {string=} stack - */ +ObjectSection -> ESCAPE ( + number:relativeOffset (number > 0) | + string:request (string|null):export +) Section:value* ESCAPE ESCAPE_END_OBJECT +ReferenceSection -> ESCAPE number:relativeOffset (number < 0) +EscapeSection -> ESCAPE ESCAPE_ESCAPE_VALUE (escaped value ESCAPE) +EscapeSection -> ESCAPE ESCAPE_UNDEFINED (escaped value ESCAPE) +OtherSection -> any (except ESCAPE) -/** @typedef {Asset & { type: string, related: PreprocessedAsset[] }} PreprocessedAsset */ +Why using null as escape value? +Multiple null values can merged by the BinaryMiddleware, which makes it very efficient +Technically any value can be used. -/** - * @template T - * @template O - * @typedef {Record void>} ExtractorsByOption - */ +*/ /** - * @typedef {Object} SimpleExtractors - * @property {ExtractorsByOption} compilation - * @property {ExtractorsByOption} asset - * @property {ExtractorsByOption} asset$visible - * @property {ExtractorsByOption<{ name: string, chunkGroup: ChunkGroup }, StatsChunkGroup>} chunkGroup - * @property {ExtractorsByOption} module - * @property {ExtractorsByOption} module$visible - * @property {ExtractorsByOption} moduleIssuer - * @property {ExtractorsByOption} profile - * @property {ExtractorsByOption} moduleReason - * @property {ExtractorsByOption} chunk - * @property {ExtractorsByOption} chunkOrigin - * @property {ExtractorsByOption} error - * @property {ExtractorsByOption} warning - * @property {ExtractorsByOption<{ origin: Module, module: Module }, StatsModuleTraceItem>} moduleTraceItem - * @property {ExtractorsByOption} moduleTraceDependency + * @typedef {Object} ObjectSerializerContext + * @property {function(any): void} write */ /** - * @template T - * @template I - * @param {Iterable} items items to select from - * @param {function(T): Iterable} selector selector function to select values from item - * @returns {I[]} array of values + * @typedef {Object} ObjectDeserializerContext + * @property {function(): any} read */ -const uniqueArray = (items, selector) => { - /** @type {Set} */ - const set = new Set(); - for (const item of items) { - for (const i of selector(item)) { - set.add(i); + +/** + * @typedef {Object} ObjectSerializer + * @property {function(any, ObjectSerializerContext): void} serialize + * @property {function(ObjectDeserializerContext): any} deserialize + */ + +const setSetSize = (set, size) => { + let i = 0; + for (const item of set) { + if (i++ >= size) { + set.delete(item); + } + } +}; + +const setMapSize = (map, size) => { + let i = 0; + for (const item of map.keys()) { + if (i++ >= size) { + map.delete(item); } } - return Array.from(set); }; /** - * @template T - * @template I - * @param {Iterable} items items to select from - * @param {function(T): Iterable} selector selector function to select values from item - * @param {Comparator} comparator comparator function - * @returns {I[]} array of values + * @param {Buffer} buffer buffer + * @param {string | Hash} hashFunction hash function to use + * @returns {string} hash */ -const uniqueOrderedArray = (items, selector, comparator) => { - return uniqueArray(items, selector).sort(comparator); +const toHash = (buffer, hashFunction) => { + const hash = createHash(hashFunction); + hash.update(buffer); + return /** @type {string} */ (hash.digest("latin1")); }; -/** @template T @template R @typedef {{ [P in keyof T]: R }} MappedValues */ +const ESCAPE = null; +const ESCAPE_ESCAPE_VALUE = null; +const ESCAPE_END_OBJECT = true; +const ESCAPE_UNDEFINED = false; -/** - * @template T - * @template R - * @param {T} obj object to be mapped - * @param {function(T[keyof T], keyof T): R} fn mapping function - * @returns {MappedValues} mapped object - */ -const mapObject = (obj, fn) => { - const newObj = Object.create(null); - for (const key of Object.keys(obj)) { - newObj[key] = fn(obj[key], /** @type {keyof T} */ (key)); +const CURRENT_VERSION = 2; + +const serializers = new Map(); +const serializerInversed = new Map(); + +const loadedRequests = new Set(); + +const NOT_SERIALIZABLE = {}; + +const jsTypes = new Map(); +jsTypes.set(Object, new PlainObjectSerializer()); +jsTypes.set(Array, new ArraySerializer()); +jsTypes.set(null, new NullPrototypeObjectSerializer()); +jsTypes.set(Map, new MapObjectSerializer()); +jsTypes.set(Set, new SetObjectSerializer()); +jsTypes.set(Date, new DateObjectSerializer()); +jsTypes.set(RegExp, new RegExpObjectSerializer()); +jsTypes.set(Error, new ErrorObjectSerializer(Error)); +jsTypes.set(EvalError, new ErrorObjectSerializer(EvalError)); +jsTypes.set(RangeError, new ErrorObjectSerializer(RangeError)); +jsTypes.set(ReferenceError, new ErrorObjectSerializer(ReferenceError)); +jsTypes.set(SyntaxError, new ErrorObjectSerializer(SyntaxError)); +jsTypes.set(TypeError, new ErrorObjectSerializer(TypeError)); + +// If in a sandboxed environment (e. g. jest), this escapes the sandbox and registers +// real Object and Array types to. These types may occur in the wild too, e. g. when +// using Structured Clone in postMessage. +if (exports.constructor !== Object) { + const Obj = /** @type {typeof Object} */ (exports.constructor); + const Fn = /** @type {typeof Function} */ (Obj.constructor); + for (const [type, config] of Array.from(jsTypes)) { + if (type) { + const Type = new Fn(`return ${type.name};`)(); + jsTypes.set(Type, config); + } } - return newObj; -}; +} + +{ + let i = 1; + for (const [type, serializer] of jsTypes) { + serializers.set(type, { + request: "", + name: i++, + serializer + }); + } +} + +for (const { request, name, serializer } of serializers.values()) { + serializerInversed.set(`${request}/${name}`, serializer); +} + +/** @type {Map boolean>} */ +const loaders = new Map(); /** - * @param {Compilation} compilation the compilation - * @param {function(Compilation, string): any[]} getItems get items - * @returns {number} total number + * @typedef {ComplexSerializableType[]} DeserializedType + * @typedef {PrimitiveSerializableType[]} SerializedType + * @extends {SerializerMiddleware} */ -const countWithChildren = (compilation, getItems) => { - let count = getItems(compilation, "").length; - for (const child of compilation.children) { - count += countWithChildren(child, (c, type) => - getItems(c, `.children[].compilation${type}`) - ); +class ObjectMiddleware extends SerializerMiddleware { + /** + * @param {function(any): void} extendContext context extensions + * @param {string | Hash} hashFunction hash function to use + */ + constructor(extendContext, hashFunction = "md4") { + super(); + this.extendContext = extendContext; + this._hashFunction = hashFunction; + } + /** + * @param {RegExp} regExp RegExp for which the request is tested + * @param {function(string): boolean} loader loader to load the request, returns true when successful + * @returns {void} + */ + static registerLoader(regExp, loader) { + loaders.set(regExp, loader); } - return count; -}; -/** @type {ExtractorsByOption} */ -const EXTRACT_ERROR = { - _: (object, error, context, { requestShortener }) => { - // TODO webpack 6 disallow strings in the errors/warnings list - if (typeof error === "string") { - object.message = error; - } else { - if (error.chunk) { - object.chunkName = error.chunk.name; - object.chunkEntry = error.chunk.hasRuntime(); - object.chunkInitial = error.chunk.canBeInitial(); - } - if (error.file) { - object.file = error.file; - } - if (error.module) { - object.moduleIdentifier = error.module.identifier(); - object.moduleName = error.module.readableIdentifier(requestShortener); - } - if (error.loc) { - object.loc = formatLocation(error.loc); - } - object.message = error.message; - } - }, - ids: (object, error, { compilation: { chunkGraph } }) => { - if (typeof error !== "string") { - if (error.chunk) { - object.chunkId = error.chunk.id; - } - if (error.module) { - object.moduleId = chunkGraph.getModuleId(error.module); - } - } - }, - moduleTrace: (object, error, context, options, factory) => { - if (typeof error !== "string" && error.module) { - const { - type, - compilation: { moduleGraph } - } = context; - /** @type {Set} */ - const visitedModules = new Set(); - const moduleTrace = []; - let current = error.module; - while (current) { - if (visitedModules.has(current)) break; // circular (technically impossible, but how knows) - visitedModules.add(current); - const origin = moduleGraph.getIssuer(current); - if (!origin) break; - moduleTrace.push({ origin, module: current }); - current = origin; - } - object.moduleTrace = factory.create( - `${type}.moduleTrace`, - moduleTrace, - context + /** + * @param {Constructor} Constructor the constructor + * @param {string} request the request which will be required when deserializing + * @param {string} name the name to make multiple serializer unique when sharing a request + * @param {ObjectSerializer} serializer the serializer + * @returns {void} + */ + static register(Constructor, request, name, serializer) { + const key = request + "/" + name; + + if (serializers.has(Constructor)) { + throw new Error( + `ObjectMiddleware.register: serializer for ${Constructor.name} is already registered` ); } - }, - errorDetails: ( - object, - error, - { type, compilation, cachedGetErrors, cachedGetWarnings }, - { errorDetails } - ) => { - if ( - typeof error !== "string" && - (errorDetails === true || - (type.endsWith(".error") && cachedGetErrors(compilation).length < 3)) - ) { - object.details = error.details; + + if (serializerInversed.has(key)) { + throw new Error( + `ObjectMiddleware.register: serializer for ${key} is already registered` + ); } - }, - errorStack: (object, error) => { - if (typeof error !== "string") { - object.stack = error.stack; + + serializers.set(Constructor, { + request, + name, + serializer + }); + + serializerInversed.set(key, serializer); + } + + /** + * @param {Constructor} Constructor the constructor + * @returns {void} + */ + static registerNotSerializable(Constructor) { + if (serializers.has(Constructor)) { + throw new Error( + `ObjectMiddleware.registerNotSerializable: serializer for ${Constructor.name} is already registered` + ); } + + serializers.set(Constructor, NOT_SERIALIZABLE); } -}; -/** @type {SimpleExtractors} */ -const SIMPLE_EXTRACTORS = { - compilation: { - _: (object, compilation, context, options) => { - if (!context.makePathsRelative) { - context.makePathsRelative = makePathsRelative.bindContextCache( - compilation.compiler.context, - compilation.compiler.root + static getSerializerFor(object) { + const proto = Object.getPrototypeOf(object); + let c; + if (proto === null) { + // Object created with Object.create(null) + c = null; + } else { + c = proto.constructor; + if (!c) { + throw new Error( + "Serialization of objects with prototype without valid constructor property not possible" ); } - if (!context.cachedGetErrors) { - const map = new WeakMap(); - context.cachedGetErrors = compilation => { - return ( - map.get(compilation) || - (errors => (map.set(compilation, errors), errors))( - compilation.getErrors() - ) - ); - }; - } - if (!context.cachedGetWarnings) { - const map = new WeakMap(); - context.cachedGetWarnings = compilation => { - return ( - map.get(compilation) || - (warnings => (map.set(compilation, warnings), warnings))( - compilation.getWarnings() - ) - ); - }; - } - if (compilation.name) { - object.name = compilation.name; - } - if (compilation.needAdditionalPass) { - object.needAdditionalPass = true; - } + } + const config = serializers.get(c); - const { logging, loggingDebug, loggingTrace } = options; - if (logging || (loggingDebug && loggingDebug.length > 0)) { - const util = __webpack_require__(31669); - object.logging = {}; - let acceptedTypes; - let collapsedGroups = false; - switch (logging) { - default: - acceptedTypes = new Set(); - break; - case "error": - acceptedTypes = new Set([LogType.error]); - break; - case "warn": - acceptedTypes = new Set([LogType.error, LogType.warn]); - break; - case "info": - acceptedTypes = new Set([ - LogType.error, - LogType.warn, - LogType.info - ]); - break; - case "log": - acceptedTypes = new Set([ - LogType.error, - LogType.warn, - LogType.info, - LogType.log, - LogType.group, - LogType.groupEnd, - LogType.groupCollapsed, - LogType.clear - ]); - break; - case "verbose": - acceptedTypes = new Set([ - LogType.error, - LogType.warn, - LogType.info, - LogType.log, - LogType.group, - LogType.groupEnd, - LogType.groupCollapsed, - LogType.profile, - LogType.profileEnd, - LogType.time, - LogType.status, - LogType.clear - ]); - collapsedGroups = true; - break; - } - const cachedMakePathsRelative = makePathsRelative.bindContextCache( - options.context, - compilation.compiler.root - ); - let depthInCollapsedGroup = 0; - for (const [origin, logEntries] of compilation.logging) { - const debugMode = loggingDebug.some(fn => fn(origin)); - if (logging === false && !debugMode) continue; - /** @type {KnownStatsLoggingEntry[]} */ - const groupStack = []; - /** @type {KnownStatsLoggingEntry[]} */ - const rootList = []; - let currentList = rootList; - let processedLogEntries = 0; - for (const entry of logEntries) { - let type = entry.type; - if (!debugMode && !acceptedTypes.has(type)) continue; + if (!config) throw new Error(`No serializer registered for ${c.name}`); + if (config === NOT_SERIALIZABLE) throw NOT_SERIALIZABLE; - // Expand groups in verbose and debug modes - if ( - type === LogType.groupCollapsed && - (debugMode || collapsedGroups) - ) - type = LogType.group; + return config; + } - if (depthInCollapsedGroup === 0) { - processedLogEntries++; - } + static getDeserializerFor(request, name) { + const key = request + "/" + name; + const serializer = serializerInversed.get(key); - if (type === LogType.groupEnd) { - groupStack.pop(); - if (groupStack.length > 0) { - currentList = groupStack[groupStack.length - 1].children; - } else { - currentList = rootList; - } - if (depthInCollapsedGroup > 0) depthInCollapsedGroup--; - continue; + if (serializer === undefined) { + throw new Error(`No deserializer registered for ${key}`); + } + + return serializer; + } + + static _getDeserializerForWithoutError(request, name) { + const key = request + "/" + name; + const serializer = serializerInversed.get(key); + return serializer; + } + + /** + * @param {DeserializedType} data data + * @param {Object} context context object + * @returns {SerializedType|Promise} serialized data + */ + serialize(data, context) { + /** @type {any[]} */ + let result = [CURRENT_VERSION]; + let currentPos = 0; + let referenceable = new Map(); + const addReferenceable = item => { + referenceable.set(item, currentPos++); + }; + let bufferDedupeMap = new Map(); + const dedupeBuffer = buf => { + const len = buf.length; + const entry = bufferDedupeMap.get(len); + if (entry === undefined) { + bufferDedupeMap.set(len, buf); + return buf; + } + if (Buffer.isBuffer(entry)) { + if (len < 32) { + if (buf.equals(entry)) { + return entry; + } + bufferDedupeMap.set(len, [entry, buf]); + return buf; + } else { + const hash = toHash(entry, this._hashFunction); + const newMap = new Map(); + newMap.set(hash, entry); + bufferDedupeMap.set(len, newMap); + const hashBuf = toHash(buf, this._hashFunction); + if (hash === hashBuf) { + return entry; + } + return buf; + } + } else if (Array.isArray(entry)) { + if (entry.length < 16) { + for (const item of entry) { + if (buf.equals(item)) { + return item; } - let message = undefined; - if (entry.type === LogType.time) { - message = `${entry.args[0]}: ${ - entry.args[1] * 1000 + entry.args[2] / 1000000 - } ms`; - } else if (entry.args && entry.args.length > 0) { - message = util.format(entry.args[0], ...entry.args.slice(1)); + } + entry.push(buf); + return buf; + } else { + const newMap = new Map(); + const hash = toHash(buf, this._hashFunction); + let found; + for (const item of entry) { + const itemHash = toHash(item, this._hashFunction); + newMap.set(itemHash, item); + if (found === undefined && itemHash === hash) found = item; + } + bufferDedupeMap.set(len, newMap); + if (found === undefined) { + newMap.set(hash, buf); + return buf; + } else { + return found; + } + } + } else { + const hash = toHash(buf, this._hashFunction); + const item = entry.get(hash); + if (item !== undefined) { + return item; + } + entry.set(hash, buf); + return buf; + } + }; + let currentPosTypeLookup = 0; + let objectTypeLookup = new Map(); + const cycleStack = new Set(); + const stackToString = item => { + const arr = Array.from(cycleStack); + arr.push(item); + return arr + .map(item => { + if (typeof item === "string") { + if (item.length > 100) { + return `String ${JSON.stringify(item.slice(0, 100)).slice( + 0, + -1 + )}..."`; } - /** @type {KnownStatsLoggingEntry} */ - const newEntry = { - ...entry, - type, - message, - trace: loggingTrace ? entry.trace : undefined, - children: - type === LogType.group || type === LogType.groupCollapsed - ? [] - : undefined - }; - currentList.push(newEntry); - if (newEntry.children) { - groupStack.push(newEntry); - currentList = newEntry.children; - if (depthInCollapsedGroup > 0) { - depthInCollapsedGroup++; - } else if (type === LogType.groupCollapsed) { - depthInCollapsedGroup = 1; - } + return `String ${JSON.stringify(item)}`; + } + try { + const { request, name } = ObjectMiddleware.getSerializerFor(item); + if (request) { + return `${request}${name ? `.${name}` : ""}`; } + } catch (e) { + // ignore -> fallback } - let name = cachedMakePathsRelative(origin).replace(/\|/g, " "); - if (name in object.logging) { - let i = 1; - while (`${name}#${i}` in object.logging) { - i++; + if (typeof item === "object" && item !== null) { + if (item.constructor) { + if (item.constructor === Object) + return `Object { ${Object.keys(item).join(", ")} }`; + if (item.constructor === Map) return `Map { ${item.size} items }`; + if (item.constructor === Array) + return `Array { ${item.length} items }`; + if (item.constructor === Set) return `Set { ${item.size} items }`; + if (item.constructor === RegExp) return item.toString(); + return `${item.constructor.name}`; } - name = `${name}#${i}`; + return `Object [null prototype] { ${Object.keys(item).join( + ", " + )} }`; } - object.logging[name] = { - entries: rootList, - filteredEntries: logEntries.length - processedLogEntries, - debug: debugMode - }; - } - } - }, - hash: (object, compilation) => { - object.hash = compilation.hash; - }, - version: object => { - object.version = __webpack_require__(87168)/* .version */ .i8; - }, - env: (object, compilation, context, { _env }) => { - object.env = _env; - }, - timings: (object, compilation) => { - object.time = compilation.endTime - compilation.startTime; - }, - builtAt: (object, compilation) => { - object.builtAt = compilation.endTime; - }, - publicPath: (object, compilation) => { - object.publicPath = compilation.getPath( - compilation.outputOptions.publicPath - ); - }, - outputPath: (object, compilation) => { - object.outputPath = compilation.outputOptions.path; - }, - assets: (object, compilation, context, options, factory) => { - const { type } = context; - /** @type {Map} */ - const compilationFileToChunks = new Map(); - /** @type {Map} */ - const compilationAuxiliaryFileToChunks = new Map(); - for (const chunk of compilation.chunks) { - for (const file of chunk.files) { - let array = compilationFileToChunks.get(file); - if (array === undefined) { - array = []; - compilationFileToChunks.set(file, array); + try { + return `${item}`; + } catch (e) { + return `(${e.message})`; } - array.push(chunk); - } - for (const file of chunk.auxiliaryFiles) { - let array = compilationAuxiliaryFileToChunks.get(file); - if (array === undefined) { - array = []; - compilationAuxiliaryFileToChunks.set(file, array); + }) + .join(" -> "); + }; + let hasDebugInfoAttached; + let ctx = { + write(value, key) { + try { + process(value); + } catch (e) { + if (e !== NOT_SERIALIZABLE) { + if (hasDebugInfoAttached === undefined) + hasDebugInfoAttached = new WeakSet(); + if (!hasDebugInfoAttached.has(e)) { + e.message += `\nwhile serializing ${stackToString(value)}`; + hasDebugInfoAttached.add(e); + } } - array.push(chunk); + throw e; } - } - /** @type {Map} */ - const assetMap = new Map(); - /** @type {Set} */ - const assets = new Set(); - for (const asset of compilation.getAssets()) { - /** @type {PreprocessedAsset} */ - const item = { - ...asset, - type: "asset", - related: undefined + }, + setCircularReference(ref) { + addReferenceable(ref); + }, + snapshot() { + return { + length: result.length, + cycleStackSize: cycleStack.size, + referenceableSize: referenceable.size, + currentPos, + objectTypeLookupSize: objectTypeLookup.size, + currentPosTypeLookup }; - assets.add(item); - assetMap.set(asset.name, item); - } - for (const item of assetMap.values()) { - const related = item.info.related; - if (!related) continue; - for (const type of Object.keys(related)) { - const relatedEntry = related[type]; - const deps = Array.isArray(relatedEntry) - ? relatedEntry - : [relatedEntry]; - for (const dep of deps) { - const depItem = assetMap.get(dep); - if (!depItem) continue; - assets.delete(depItem); - depItem.type = type; - item.related = item.related || []; - item.related.push(depItem); + }, + rollback(snapshot) { + result.length = snapshot.length; + setSetSize(cycleStack, snapshot.cycleStackSize); + setMapSize(referenceable, snapshot.referenceableSize); + currentPos = snapshot.currentPos; + setMapSize(objectTypeLookup, snapshot.objectTypeLookupSize); + currentPosTypeLookup = snapshot.currentPosTypeLookup; + }, + ...context + }; + this.extendContext(ctx); + const process = item => { + if (Buffer.isBuffer(item)) { + // check if we can emit a reference + const ref = referenceable.get(item); + if (ref !== undefined) { + result.push(ESCAPE, ref - currentPos); + return; + } + const alreadyUsedBuffer = dedupeBuffer(item); + if (alreadyUsedBuffer !== item) { + const ref = referenceable.get(alreadyUsedBuffer); + if (ref !== undefined) { + referenceable.set(item, ref); + result.push(ESCAPE, ref - currentPos); + return; } + item = alreadyUsedBuffer; } - } + addReferenceable(item); - object.assetsByChunkName = {}; - for (const [file, chunks] of compilationFileToChunks) { - for (const chunk of chunks) { - const name = chunk.name; - if (!name) continue; - if ( - !Object.prototype.hasOwnProperty.call( - object.assetsByChunkName, - name - ) - ) { - object.assetsByChunkName[name] = []; - } - object.assetsByChunkName[name].push(file); + result.push(item); + } else if (item === ESCAPE) { + result.push(ESCAPE, ESCAPE_ESCAPE_VALUE); + } else if ( + typeof item === "object" + // We don't have to check for null as ESCAPE is null and this has been checked before + ) { + // check if we can emit a reference + const ref = referenceable.get(item); + if (ref !== undefined) { + result.push(ESCAPE, ref - currentPos); + return; } - } - const groupedAssets = factory.create( - `${type}.assets`, - Array.from(assets), - { - ...context, - compilationFileToChunks, - compilationAuxiliaryFileToChunks + if (cycleStack.has(item)) { + throw new Error( + `This is a circular references. To serialize circular references use 'setCircularReference' somewhere in the circle during serialize and deserialize.` + ); } - ); - const limited = spaceLimited(groupedAssets, options.assetsSpace); - object.assets = limited.children; - object.filteredAssets = limited.filteredChildren; - }, - chunks: (object, compilation, context, options, factory) => { - const { type } = context; - object.chunks = factory.create( - `${type}.chunks`, - Array.from(compilation.chunks), - context - ); - }, - modules: (object, compilation, context, options, factory) => { - const { type } = context; - const array = Array.from(compilation.modules); - const groupedModules = factory.create(`${type}.modules`, array, context); - const limited = spaceLimited(groupedModules, options.modulesSpace); - object.modules = limited.children; - object.filteredModules = limited.filteredChildren; - }, - entrypoints: ( - object, - compilation, - context, - { entrypoints, chunkGroups, chunkGroupAuxiliary, chunkGroupChildren }, - factory - ) => { - const { type } = context; - const array = Array.from(compilation.entrypoints, ([key, value]) => ({ - name: key, - chunkGroup: value - })); - if (entrypoints === "auto" && !chunkGroups) { - if (array.length > 5) return; - if ( - !chunkGroupChildren && - array.every(({ chunkGroup }) => { - if (chunkGroup.chunks.length !== 1) return false; - const chunk = chunkGroup.chunks[0]; - return ( - chunk.files.size === 1 && - (!chunkGroupAuxiliary || chunk.auxiliaryFiles.size === 0) - ); - }) - ) { - return; + + const { request, name, serializer } = + ObjectMiddleware.getSerializerFor(item); + const key = `${request}/${name}`; + const lastIndex = objectTypeLookup.get(key); + + if (lastIndex === undefined) { + objectTypeLookup.set(key, currentPosTypeLookup++); + + result.push(ESCAPE, request, name); + } else { + result.push(ESCAPE, currentPosTypeLookup - lastIndex); } - } - object.entrypoints = factory.create( - `${type}.entrypoints`, - array, - context - ); - }, - chunkGroups: (object, compilation, context, options, factory) => { - const { type } = context; - const array = Array.from( - compilation.namedChunkGroups, - ([key, value]) => ({ - name: key, - chunkGroup: value - }) - ); - object.namedChunkGroups = factory.create( - `${type}.namedChunkGroups`, - array, - context - ); - }, - errors: (object, compilation, context, options, factory) => { - const { type, cachedGetErrors } = context; - object.errors = factory.create( - `${type}.errors`, - cachedGetErrors(compilation), - context - ); - }, - errorsCount: (object, compilation, { cachedGetErrors }) => { - object.errorsCount = countWithChildren(compilation, c => - cachedGetErrors(c) - ); - }, - warnings: (object, compilation, context, options, factory) => { - const { type, cachedGetWarnings } = context; - object.warnings = factory.create( - `${type}.warnings`, - cachedGetWarnings(compilation), - context - ); - }, - warningsCount: ( - object, - compilation, - context, - { warningsFilter }, - factory - ) => { - const { type, cachedGetWarnings } = context; - object.warningsCount = countWithChildren(compilation, (c, childType) => { - if (!warningsFilter && warningsFilter.length === 0) - return cachedGetWarnings(c); - return factory - .create(`${type}${childType}.warnings`, cachedGetWarnings(c), context) - .filter(warning => { - const warningString = Object.keys(warning) - .map(key => `${warning[key]}`) - .join("\n"); - return !warningsFilter.some(filter => - filter(warning, warningString) - ); - }); - }); - }, - errorDetails: ( - object, - compilation, - { cachedGetErrors, cachedGetWarnings }, - { errorDetails, errors, warnings } - ) => { - if (errorDetails === "auto") { - if (warnings) { - const warnings = cachedGetWarnings(compilation); - object.filteredWarningDetailsCount = warnings - .map(e => typeof e !== "string" && e.details) - .filter(Boolean).length; + + cycleStack.add(item); + + try { + serializer.serialize(item, ctx); + } finally { + cycleStack.delete(item); } - if (errors) { - const errors = cachedGetErrors(compilation); - if (errors.length >= 3) { - object.filteredErrorDetailsCount = errors - .map(e => typeof e !== "string" && e.details) - .filter(Boolean).length; + + result.push(ESCAPE, ESCAPE_END_OBJECT); + + addReferenceable(item); + } else if (typeof item === "string") { + if (item.length > 1) { + // short strings are shorter when not emitting a reference (this saves 1 byte per empty string) + // check if we can emit a reference + const ref = referenceable.get(item); + if (ref !== undefined) { + result.push(ESCAPE, ref - currentPos); + return; } + addReferenceable(item); } - } - }, - children: (object, compilation, context, options, factory) => { - const { type } = context; - object.children = factory.create( - `${type}.children`, - compilation.children, - context - ); - } - }, - asset: { - _: (object, asset, context, options, factory) => { - const { compilation } = context; - object.type = asset.type; - object.name = asset.name; - object.size = asset.source.size(); - object.emitted = compilation.emittedAssets.has(asset.name); - object.comparedForEmit = compilation.comparedForEmitAssets.has( - asset.name - ); - const cached = !object.emitted && !object.comparedForEmit; - object.cached = cached; - object.info = asset.info; - if (!cached || options.cachedAssets) { - Object.assign( - object, - factory.create(`${context.type}$visible`, asset, context) - ); - } - } - }, - asset$visible: { - _: ( - object, - asset, - { compilation, compilationFileToChunks, compilationAuxiliaryFileToChunks } - ) => { - const chunks = compilationFileToChunks.get(asset.name) || []; - const auxiliaryChunks = - compilationAuxiliaryFileToChunks.get(asset.name) || []; - object.chunkNames = uniqueOrderedArray( - chunks, - c => (c.name ? [c.name] : []), - compareIds - ); - object.chunkIdHints = uniqueOrderedArray( - chunks, - c => Array.from(c.idNameHints), - compareIds - ); - object.auxiliaryChunkNames = uniqueOrderedArray( - auxiliaryChunks, - c => (c.name ? [c.name] : []), - compareIds - ); - object.auxiliaryChunkIdHints = uniqueOrderedArray( - auxiliaryChunks, - c => Array.from(c.idNameHints), - compareIds - ); - object.filteredRelated = asset.related ? asset.related.length : undefined; - }, - relatedAssets: (object, asset, context, options, factory) => { - const { type } = context; - object.related = factory.create( - `${type.slice(0, -8)}.related`, - asset.related, - context - ); - object.filteredRelated = asset.related - ? asset.related.length - object.related.length - : undefined; - }, - ids: ( - object, - asset, - { compilationFileToChunks, compilationAuxiliaryFileToChunks } - ) => { - const chunks = compilationFileToChunks.get(asset.name) || []; - const auxiliaryChunks = - compilationAuxiliaryFileToChunks.get(asset.name) || []; - object.chunks = uniqueOrderedArray(chunks, c => c.ids, compareIds); - object.auxiliaryChunks = uniqueOrderedArray( - auxiliaryChunks, - c => c.ids, - compareIds - ); - }, - performance: (object, asset) => { - object.isOverSizeLimit = SizeLimitsPlugin.isOverSizeLimit(asset.source); + + if (item.length > 102400 && context.logger) { + context.logger.warn( + `Serializing big strings (${Math.round( + item.length / 1024 + )}kiB) impacts deserialization performance (consider using Buffer instead and decode when needed)` + ); + } + + result.push(item); + } else if (typeof item === "function") { + if (!SerializerMiddleware.isLazy(item)) + throw new Error("Unexpected function " + item); + /** @type {SerializedType} */ + const serializedData = + SerializerMiddleware.getLazySerializedValue(item); + if (serializedData !== undefined) { + if (typeof serializedData === "function") { + result.push(serializedData); + } else { + throw new Error("Not implemented"); + } + } else if (SerializerMiddleware.isLazy(item, this)) { + throw new Error("Not implemented"); + } else { + const data = SerializerMiddleware.serializeLazy(item, data => + this.serialize([data], context) + ); + SerializerMiddleware.setLazySerializedValue(item, data); + result.push(data); + } + } else if (item === undefined) { + result.push(ESCAPE, ESCAPE_UNDEFINED); + } else { + result.push(item); + } + }; + + try { + for (const item of data) { + process(item); + } + return result; + } catch (e) { + if (e === NOT_SERIALIZABLE) return null; + + throw e; + } finally { + // Get rid of these references to avoid leaking memory + // This happens because the optimized code v8 generates + // is optimized for our "ctx.write" method so it will reference + // it from e. g. Dependency.prototype.serialize -(IC)-> ctx.write + data = + result = + referenceable = + bufferDedupeMap = + objectTypeLookup = + ctx = + undefined; } - }, - chunkGroup: { - _: ( - object, - { name, chunkGroup }, - { compilation, compilation: { moduleGraph, chunkGraph } }, - { ids, chunkGroupAuxiliary, chunkGroupChildren, chunkGroupMaxAssets } - ) => { - const children = - chunkGroupChildren && - chunkGroup.getChildrenByOrders(moduleGraph, chunkGraph); - /** - * @param {string} name Name - * @returns {{ name: string, size: number }} Asset object - */ - const toAsset = name => { - const asset = compilation.getAsset(name); - return { - name, - size: asset ? asset.info.size : -1 - }; - }; - /** @type {(total: number, asset: { size: number }) => number} */ - const sizeReducer = (total, { size }) => total + size; - const assets = uniqueArray(chunkGroup.chunks, c => c.files).map(toAsset); - const auxiliaryAssets = uniqueOrderedArray( - chunkGroup.chunks, - c => c.auxiliaryFiles, - compareIds - ).map(toAsset); - const assetsSize = assets.reduce(sizeReducer, 0); - const auxiliaryAssetsSize = auxiliaryAssets.reduce(sizeReducer, 0); - /** @type {KnownStatsChunkGroup} */ - const statsChunkGroup = { - name, - chunks: ids ? chunkGroup.chunks.map(c => c.id) : undefined, - assets: assets.length <= chunkGroupMaxAssets ? assets : undefined, - filteredAssets: - assets.length <= chunkGroupMaxAssets ? 0 : assets.length, - assetsSize, - auxiliaryAssets: - chunkGroupAuxiliary && auxiliaryAssets.length <= chunkGroupMaxAssets - ? auxiliaryAssets - : undefined, - filteredAuxiliaryAssets: - chunkGroupAuxiliary && auxiliaryAssets.length <= chunkGroupMaxAssets - ? 0 - : auxiliaryAssets.length, - auxiliaryAssetsSize, - children: children - ? mapObject(children, groups => - groups.map(group => { - const assets = uniqueArray(group.chunks, c => c.files).map( - toAsset - ); - const auxiliaryAssets = uniqueOrderedArray( - group.chunks, - c => c.auxiliaryFiles, - compareIds - ).map(toAsset); + } - /** @type {KnownStatsChunkGroup} */ - const childStatsChunkGroup = { - name: group.name, - chunks: ids ? group.chunks.map(c => c.id) : undefined, - assets: - assets.length <= chunkGroupMaxAssets ? assets : undefined, - filteredAssets: - assets.length <= chunkGroupMaxAssets ? 0 : assets.length, - auxiliaryAssets: - chunkGroupAuxiliary && - auxiliaryAssets.length <= chunkGroupMaxAssets - ? auxiliaryAssets - : undefined, - filteredAuxiliaryAssets: - chunkGroupAuxiliary && - auxiliaryAssets.length <= chunkGroupMaxAssets - ? 0 - : auxiliaryAssets.length - }; + /** + * @param {SerializedType} data data + * @param {Object} context context object + * @returns {DeserializedType|Promise} deserialized data + */ + deserialize(data, context) { + let currentDataPos = 0; + const read = () => { + if (currentDataPos >= data.length) + throw new Error("Unexpected end of stream"); - return childStatsChunkGroup; - }) - ) - : undefined, - childAssets: children - ? mapObject(children, groups => { - /** @type {Set} */ - const set = new Set(); - for (const group of groups) { - for (const chunk of group.chunks) { - for (const asset of chunk.files) { - set.add(asset); + return data[currentDataPos++]; + }; + + if (read() !== CURRENT_VERSION) + throw new Error("Version mismatch, serializer changed"); + + let currentPos = 0; + let referenceable = []; + const addReferenceable = item => { + referenceable.push(item); + currentPos++; + }; + let currentPosTypeLookup = 0; + let objectTypeLookup = []; + let result = []; + let ctx = { + read() { + return decodeValue(); + }, + setCircularReference(ref) { + addReferenceable(ref); + }, + ...context + }; + this.extendContext(ctx); + const decodeValue = () => { + const item = read(); + + if (item === ESCAPE) { + const nextItem = read(); + + if (nextItem === ESCAPE_ESCAPE_VALUE) { + return ESCAPE; + } else if (nextItem === ESCAPE_UNDEFINED) { + return undefined; + } else if (nextItem === ESCAPE_END_OBJECT) { + throw new Error( + `Unexpected end of object at position ${currentDataPos - 1}` + ); + } else { + const request = nextItem; + let serializer; + + if (typeof request === "number") { + if (request < 0) { + // relative reference + return referenceable[currentPos + request]; + } + serializer = objectTypeLookup[currentPosTypeLookup - request]; + } else { + if (typeof request !== "string") { + throw new Error( + `Unexpected type (${typeof request}) of request ` + + `at position ${currentDataPos - 1}` + ); + } + const name = read(); + + serializer = ObjectMiddleware._getDeserializerForWithoutError( + request, + name + ); + + if (serializer === undefined) { + if (request && !loadedRequests.has(request)) { + let loaded = false; + for (const [regExp, loader] of loaders) { + if (regExp.test(request)) { + if (loader(request)) { + loaded = true; + break; + } } } + if (!loaded) { + require(request); + } + + loadedRequests.add(request); } - return Array.from(set); - }) - : undefined - }; - Object.assign(object, statsChunkGroup); - }, - performance: (object, { chunkGroup }) => { - object.isOverSizeLimit = SizeLimitsPlugin.isOverSizeLimit(chunkGroup); - } - }, - module: { - _: (object, module, context, options, factory) => { - const { compilation, type } = context; - const built = compilation.builtModules.has(module); - const codeGenerated = compilation.codeGeneratedModules.has(module); - const buildTimeExecuted = - compilation.buildTimeExecutedModules.has(module); - /** @type {{[x: string]: number}} */ - const sizes = {}; - for (const sourceType of module.getSourceTypes()) { - sizes[sourceType] = module.size(sourceType); - } - /** @type {KnownStatsModule} */ - const statsModule = { - type: "module", - moduleType: module.type, - layer: module.layer, - size: module.size(), - sizes, - built, - codeGenerated, - buildTimeExecuted, - cached: !built && !codeGenerated - }; - Object.assign(object, statsModule); - if (built || codeGenerated || options.cachedModules) { - Object.assign( - object, - factory.create(`${type}$visible`, module, context) - ); - } - } - }, - module$visible: { - _: (object, module, context, { requestShortener }, factory) => { - const { compilation, type, rootModules } = context; - const { moduleGraph } = compilation; - /** @type {Module[]} */ - const path = []; - const issuer = moduleGraph.getIssuer(module); - let current = issuer; - while (current) { - path.push(current); - current = moduleGraph.getIssuer(current); - } - path.reverse(); - const profile = moduleGraph.getProfile(module); - const errors = module.getErrors(); - const errorsCount = errors !== undefined ? countIterable(errors) : 0; - const warnings = module.getWarnings(); - const warningsCount = - warnings !== undefined ? countIterable(warnings) : 0; - /** @type {{[x: string]: number}} */ - const sizes = {}; - for (const sourceType of module.getSourceTypes()) { - sizes[sourceType] = module.size(sourceType); - } - /** @type {KnownStatsModule} */ - const statsModule = { - identifier: module.identifier(), - name: module.readableIdentifier(requestShortener), - nameForCondition: module.nameForCondition(), - index: moduleGraph.getPreOrderIndex(module), - preOrderIndex: moduleGraph.getPreOrderIndex(module), - index2: moduleGraph.getPostOrderIndex(module), - postOrderIndex: moduleGraph.getPostOrderIndex(module), - cacheable: module.buildInfo.cacheable, - optional: module.isOptional(moduleGraph), - orphan: - !type.endsWith("module.modules[].module$visible") && - compilation.chunkGraph.getNumberOfModuleChunks(module) === 0, - dependent: rootModules ? !rootModules.has(module) : undefined, - issuer: issuer && issuer.identifier(), - issuerName: issuer && issuer.readableIdentifier(requestShortener), - issuerPath: - issuer && - factory.create(`${type.slice(0, -8)}.issuerPath`, path, context), - failed: errorsCount > 0, - errors: errorsCount, - warnings: warningsCount - }; - Object.assign(object, statsModule); - if (profile) { - object.profile = factory.create( - `${type.slice(0, -8)}.profile`, - profile, - context + serializer = ObjectMiddleware.getDeserializerFor(request, name); + } + + objectTypeLookup.push(serializer); + currentPosTypeLookup++; + } + try { + const item = serializer.deserialize(ctx); + const end1 = read(); + + if (end1 !== ESCAPE) { + throw new Error("Expected end of object"); + } + + const end2 = read(); + + if (end2 !== ESCAPE_END_OBJECT) { + throw new Error("Expected end of object"); + } + + addReferenceable(item); + + return item; + } catch (err) { + // As this is only for error handling, we omit creating a Map for + // faster access to this information, as this would affect performance + // in the good case + let serializerEntry; + for (const entry of serializers) { + if (entry[1].serializer === serializer) { + serializerEntry = entry; + break; + } + } + const name = !serializerEntry + ? "unknown" + : !serializerEntry[1].request + ? serializerEntry[0].name + : serializerEntry[1].name + ? `${serializerEntry[1].request} ${serializerEntry[1].name}` + : serializerEntry[1].request; + err.message += `\n(during deserialization of ${name})`; + throw err; + } + } + } else if (typeof item === "string") { + if (item.length > 1) { + addReferenceable(item); + } + + return item; + } else if (Buffer.isBuffer(item)) { + addReferenceable(item); + + return item; + } else if (typeof item === "function") { + return SerializerMiddleware.deserializeLazy( + item, + data => this.deserialize(data, context)[0] ); - } - }, - ids: (object, module, { compilation: { chunkGraph, moduleGraph } }) => { - object.id = chunkGraph.getModuleId(module); - const issuer = moduleGraph.getIssuer(module); - object.issuerId = issuer && chunkGraph.getModuleId(issuer); - object.chunks = Array.from( - chunkGraph.getOrderedModuleChunksIterable(module, compareChunksById), - chunk => chunk.id - ); - }, - moduleAssets: (object, module) => { - object.assets = module.buildInfo.assets - ? Object.keys(module.buildInfo.assets) - : []; - }, - reasons: (object, module, context, options, factory) => { - const { - type, - compilation: { moduleGraph } - } = context; - const groupsReasons = factory.create( - `${type.slice(0, -8)}.reasons`, - Array.from(moduleGraph.getIncomingConnections(module)), - context - ); - const limited = spaceLimited(groupsReasons, options.reasonsSpace); - object.reasons = limited.children; - object.filteredReasons = limited.filteredChildren; - }, - usedExports: ( - object, - module, - { runtime, compilation: { moduleGraph } } - ) => { - const usedExports = moduleGraph.getUsedExports(module, runtime); - if (usedExports === null) { - object.usedExports = null; - } else if (typeof usedExports === "boolean") { - object.usedExports = usedExports; } else { - object.usedExports = Array.from(usedExports); + return item; } - }, - providedExports: (object, module, { compilation: { moduleGraph } }) => { - const providedExports = moduleGraph.getProvidedExports(module); - object.providedExports = Array.isArray(providedExports) - ? providedExports - : null; - }, - optimizationBailout: ( - object, - module, - { compilation: { moduleGraph } }, - { requestShortener } - ) => { - object.optimizationBailout = moduleGraph - .getOptimizationBailout(module) - .map(item => { - if (typeof item === "function") return item(requestShortener); - return item; - }); - }, - depth: (object, module, { compilation: { moduleGraph } }) => { - object.depth = moduleGraph.getDepth(module); - }, - nestedModules: (object, module, context, options, factory) => { - const { type } = context; - const innerModules = /** @type {Module & { modules?: Module[] }} */ ( - module - ).modules; - if (Array.isArray(innerModules)) { - const groupedModules = factory.create( - `${type.slice(0, -8)}.modules`, - innerModules, - context - ); - const limited = spaceLimited( - groupedModules, - options.nestedModulesSpace - ); - object.modules = limited.children; - object.filteredModules = limited.filteredChildren; + }; + + try { + while (currentDataPos < data.length) { + result.push(decodeValue()); + } + return result; + } finally { + // Get rid of these references to avoid leaking memory + // This happens because the optimized code v8 generates + // is optimized for our "ctx.read" method so it will reference + // it from e. g. Dependency.prototype.deserialize -(IC)-> ctx.read + result = referenceable = data = objectTypeLookup = ctx = undefined; + } + } +} + +module.exports = ObjectMiddleware; +module.exports.NOT_SERIALIZABLE = NOT_SERIALIZABLE; + + +/***/ }), + +/***/ 24298: +/***/ (function(module) { + +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php +*/ + + + +const cache = new WeakMap(); + +class ObjectStructure { + constructor() { + this.keys = undefined; + this.children = undefined; + } + + getKeys(keys) { + if (this.keys === undefined) this.keys = keys; + return this.keys; + } + + key(key) { + if (this.children === undefined) this.children = new Map(); + const child = this.children.get(key); + if (child !== undefined) return child; + const newChild = new ObjectStructure(); + this.children.set(key, newChild); + return newChild; + } +} + +const getCachedKeys = (keys, cacheAssoc) => { + let root = cache.get(cacheAssoc); + if (root === undefined) { + root = new ObjectStructure(); + cache.set(cacheAssoc, root); + } + let current = root; + for (const key of keys) { + current = current.key(key); + } + return current.getKeys(keys); +}; + +class PlainObjectSerializer { + serialize(obj, { write }) { + const keys = Object.keys(obj); + if (keys.length > 128) { + // Objects with so many keys are unlikely to share structure + // with other objects + write(keys); + for (const key of keys) { + write(obj[key]); } - }, - source: (object, module) => { - const originalSource = module.originalSource(); - if (originalSource) { - object.source = originalSource.source(); + } else if (keys.length > 1) { + write(getCachedKeys(keys, write)); + for (const key of keys) { + write(obj[key]); } + } else if (keys.length === 1) { + const key = keys[0]; + write(key); + write(obj[key]); + } else { + write(null); } - }, - profile: { - _: (object, profile) => { - /** @type {KnownStatsProfile} */ - const statsProfile = { - total: - profile.factory + - profile.restoring + - profile.integration + - profile.building + - profile.storing, - resolving: profile.factory, - restoring: profile.restoring, - building: profile.building, - integration: profile.integration, - storing: profile.storing, - additionalResolving: profile.additionalFactories, - additionalIntegration: profile.additionalIntegration, - // TODO remove this in webpack 6 - factory: profile.factory, - // TODO remove this in webpack 6 - dependencies: profile.additionalFactories - }; - Object.assign(object, statsProfile); - } - }, - moduleIssuer: { - _: (object, module, context, { requestShortener }, factory) => { - const { compilation, type } = context; - const { moduleGraph } = compilation; - const profile = moduleGraph.getProfile(module); - /** @type {KnownStatsModuleIssuer} */ - const statsModuleIssuer = { - identifier: module.identifier(), - name: module.readableIdentifier(requestShortener) - }; - Object.assign(object, statsModuleIssuer); - if (profile) { - object.profile = factory.create(`${type}.profile`, profile, context); + } + deserialize({ read }) { + const keys = read(); + const obj = {}; + if (Array.isArray(keys)) { + for (const key of keys) { + obj[key] = read(); } - }, - ids: (object, module, { compilation: { chunkGraph } }) => { - object.id = chunkGraph.getModuleId(module); + } else if (keys !== null) { + obj[keys] = read(); } - }, - moduleReason: { - _: (object, reason, { runtime }, { requestShortener }) => { - const dep = reason.dependency; - const moduleDep = - dep && dep instanceof ModuleDependency ? dep : undefined; - /** @type {KnownStatsModuleReason} */ - const statsModuleReason = { - moduleIdentifier: reason.originModule - ? reason.originModule.identifier() - : null, - module: reason.originModule - ? reason.originModule.readableIdentifier(requestShortener) - : null, - moduleName: reason.originModule - ? reason.originModule.readableIdentifier(requestShortener) - : null, - resolvedModuleIdentifier: reason.resolvedOriginModule - ? reason.resolvedOriginModule.identifier() - : null, - resolvedModule: reason.resolvedOriginModule - ? reason.resolvedOriginModule.readableIdentifier(requestShortener) - : null, - type: reason.dependency ? reason.dependency.type : null, - active: reason.isActive(runtime), - explanation: reason.explanation, - userRequest: (moduleDep && moduleDep.userRequest) || null - }; - Object.assign(object, statsModuleReason); - if (reason.dependency) { - const locInfo = formatLocation(reason.dependency.loc); - if (locInfo) { - object.loc = locInfo; + return obj; + } +} + +module.exports = PlainObjectSerializer; + + +/***/ }), + +/***/ 90410: +/***/ (function(module) { + +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php +*/ + + + +class RegExpObjectSerializer { + serialize(obj, { write }) { + write(obj.source); + write(obj.flags); + } + deserialize({ read }) { + return new RegExp(read(), read()); + } +} + +module.exports = RegExpObjectSerializer; + + +/***/ }), + +/***/ 24754: +/***/ (function(module) { + +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php +*/ + + + +class Serializer { + constructor(middlewares, context) { + this.serializeMiddlewares = middlewares.slice(); + this.deserializeMiddlewares = middlewares.slice().reverse(); + this.context = context; + } + + serialize(obj, context) { + const ctx = { ...context, ...this.context }; + let current = obj; + for (const middleware of this.serializeMiddlewares) { + if (current && typeof current.then === "function") { + current = current.then(data => data && middleware.serialize(data, ctx)); + } else if (current) { + try { + current = middleware.serialize(current, ctx); + } catch (err) { + current = Promise.reject(err); } + } else break; + } + return current; + } + + deserialize(value, context) { + const ctx = { ...context, ...this.context }; + /** @type {any} */ + let current = value; + for (const middleware of this.deserializeMiddlewares) { + if (current && typeof current.then === "function") { + current = current.then(data => middleware.deserialize(data, ctx)); + } else { + current = middleware.deserialize(current, ctx); } - }, - ids: (object, reason, { compilation: { chunkGraph } }) => { - object.moduleId = reason.originModule - ? chunkGraph.getModuleId(reason.originModule) - : null; - object.resolvedModuleId = reason.resolvedOriginModule - ? chunkGraph.getModuleId(reason.resolvedOriginModule) - : null; } - }, - chunk: { - _: (object, chunk, { makePathsRelative, compilation: { chunkGraph } }) => { - const childIdByOrder = chunk.getChildIdsByOrders(chunkGraph); + return current; + } +} - /** @type {KnownStatsChunk} */ - const statsChunk = { - rendered: chunk.rendered, - initial: chunk.canBeInitial(), - entry: chunk.hasRuntime(), - recorded: AggressiveSplittingPlugin.wasChunkRecorded(chunk), - reason: chunk.chunkReason, - size: chunkGraph.getChunkModulesSize(chunk), - sizes: chunkGraph.getChunkModulesSizes(chunk), - names: chunk.name ? [chunk.name] : [], - idHints: Array.from(chunk.idNameHints), - runtime: - chunk.runtime === undefined - ? undefined - : typeof chunk.runtime === "string" - ? [makePathsRelative(chunk.runtime)] - : Array.from(chunk.runtime.sort(), makePathsRelative), - files: Array.from(chunk.files), - auxiliaryFiles: Array.from(chunk.auxiliaryFiles).sort(compareIds), - hash: chunk.renderedHash, - childrenByOrder: childIdByOrder - }; - Object.assign(object, statsChunk); - }, - ids: (object, chunk) => { - object.id = chunk.id; - }, - chunkRelations: (object, chunk, { compilation: { chunkGraph } }) => { - /** @type {Set} */ - const parents = new Set(); - /** @type {Set} */ - const children = new Set(); - /** @type {Set} */ - const siblings = new Set(); +module.exports = Serializer; - for (const chunkGroup of chunk.groupsIterable) { - for (const parentGroup of chunkGroup.parentsIterable) { - for (const chunk of parentGroup.chunks) { - parents.add(chunk.id); - } - } - for (const childGroup of chunkGroup.childrenIterable) { - for (const chunk of childGroup.chunks) { - children.add(chunk.id); - } - } - for (const sibling of chunkGroup.chunks) { - if (sibling !== chunk) siblings.add(sibling.id); - } + +/***/ }), + +/***/ 37063: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php +*/ + + + +const memoize = __webpack_require__(84297); + +const LAZY_TARGET = Symbol("lazy serialization target"); +const LAZY_SERIALIZED_VALUE = Symbol("lazy serialization data"); + +/** + * @template DeserializedType + * @template SerializedType + */ +class SerializerMiddleware { + /* istanbul ignore next */ + /** + * @abstract + * @param {DeserializedType} data data + * @param {Object} context context object + * @returns {SerializedType|Promise} serialized data + */ + serialize(data, context) { + const AbstractMethodError = __webpack_require__(570); + throw new AbstractMethodError(); + } + + /* istanbul ignore next */ + /** + * @abstract + * @param {SerializedType} data data + * @param {Object} context context object + * @returns {DeserializedType|Promise} deserialized data + */ + deserialize(data, context) { + const AbstractMethodError = __webpack_require__(570); + throw new AbstractMethodError(); + } + + /** + * @param {any | function(): Promise | any} value contained value or function to value + * @param {SerializerMiddleware} target target middleware + * @param {object=} options lazy options + * @param {any=} serializedValue serialized value + * @returns {function(): Promise | any} lazy function + */ + static createLazy(value, target, options = {}, serializedValue) { + if (SerializerMiddleware.isLazy(value, target)) return value; + const fn = typeof value === "function" ? value : () => value; + fn[LAZY_TARGET] = target; + /** @type {any} */ (fn).options = options; + fn[LAZY_SERIALIZED_VALUE] = serializedValue; + return fn; + } + + /** + * @param {function(): Promise | any} fn lazy function + * @param {SerializerMiddleware=} target target middleware + * @returns {boolean} true, when fn is a lazy function (optionally of that target) + */ + static isLazy(fn, target) { + if (typeof fn !== "function") return false; + const t = fn[LAZY_TARGET]; + return target ? t === target : !!t; + } + + /** + * @param {function(): Promise | any} fn lazy function + * @returns {object} options + */ + static getLazyOptions(fn) { + if (typeof fn !== "function") return undefined; + return /** @type {any} */ (fn).options; + } + + /** + * @param {function(): Promise | any} fn lazy function + * @returns {any} serialized value + */ + static getLazySerializedValue(fn) { + if (typeof fn !== "function") return undefined; + return fn[LAZY_SERIALIZED_VALUE]; + } + + /** + * @param {function(): Promise | any} fn lazy function + * @param {any} value serialized value + * @returns {void} + */ + static setLazySerializedValue(fn, value) { + fn[LAZY_SERIALIZED_VALUE] = value; + } + + /** + * @param {function(): Promise | any} lazy lazy function + * @param {function(any): Promise | any} serialize serialize function + * @returns {function(): Promise | any} new lazy + */ + static serializeLazy(lazy, serialize) { + const fn = memoize(() => { + const r = lazy(); + if (r && typeof r.then === "function") { + return r.then(data => data && serialize(data)); } - object.siblings = Array.from(siblings).sort(compareIds); - object.parents = Array.from(parents).sort(compareIds); - object.children = Array.from(children).sort(compareIds); - }, - chunkModules: (object, chunk, context, options, factory) => { - const { - type, - compilation: { chunkGraph } - } = context; - const array = chunkGraph.getChunkModules(chunk); - const groupedModules = factory.create(`${type}.modules`, array, { - ...context, - runtime: chunk.runtime, - rootModules: new Set(chunkGraph.getChunkRootModules(chunk)) - }); - const limited = spaceLimited(groupedModules, options.chunkModulesSpace); - object.modules = limited.children; - object.filteredModules = limited.filteredChildren; - }, - chunkOrigins: (object, chunk, context, options, factory) => { - const { - type, - compilation: { chunkGraph } - } = context; - /** @type {Set} */ - const originsKeySet = new Set(); - const origins = []; - for (const g of chunk.groupsIterable) { - origins.push(...g.origins); + return serialize(r); + }); + fn[LAZY_TARGET] = lazy[LAZY_TARGET]; + /** @type {any} */ (fn).options = /** @type {any} */ (lazy).options; + lazy[LAZY_SERIALIZED_VALUE] = fn; + return fn; + } + + /** + * @param {function(): Promise | any} lazy lazy function + * @param {function(any): Promise | any} deserialize deserialize function + * @returns {function(): Promise | any} new lazy + */ + static deserializeLazy(lazy, deserialize) { + const fn = memoize(() => { + const r = lazy(); + if (r && typeof r.then === "function") { + return r.then(data => deserialize(data)); } - const array = origins.filter(origin => { - const key = [ - origin.module ? chunkGraph.getModuleId(origin.module) : undefined, - formatLocation(origin.loc), - origin.request - ].join(); - if (originsKeySet.has(key)) return false; - originsKeySet.add(key); - return true; - }); - object.origins = factory.create(`${type}.origins`, array, context); - } - }, - chunkOrigin: { - _: (object, origin, context, { requestShortener }) => { - /** @type {KnownStatsChunkOrigin} */ - const statsChunkOrigin = { - module: origin.module ? origin.module.identifier() : "", - moduleIdentifier: origin.module ? origin.module.identifier() : "", - moduleName: origin.module - ? origin.module.readableIdentifier(requestShortener) - : "", - loc: formatLocation(origin.loc), - request: origin.request - }; - Object.assign(object, statsChunkOrigin); - }, - ids: (object, origin, { compilation: { chunkGraph } }) => { - object.moduleId = origin.module - ? chunkGraph.getModuleId(origin.module) - : undefined; - } - }, - error: EXTRACT_ERROR, - warning: EXTRACT_ERROR, - moduleTraceItem: { - _: (object, { origin, module }, context, { requestShortener }, factory) => { - const { - type, - compilation: { moduleGraph } - } = context; - object.originIdentifier = origin.identifier(); - object.originName = origin.readableIdentifier(requestShortener); - object.moduleIdentifier = module.identifier(); - object.moduleName = module.readableIdentifier(requestShortener); - const dependencies = Array.from( - moduleGraph.getIncomingConnections(module) - ) - .filter(c => c.resolvedOriginModule === origin && c.dependency) - .map(c => c.dependency); - object.dependencies = factory.create( - `${type}.dependencies`, - Array.from(new Set(dependencies)), - context + return deserialize(r); + }); + fn[LAZY_TARGET] = lazy[LAZY_TARGET]; + /** @type {any} */ (fn).options = /** @type {any} */ (lazy).options; + fn[LAZY_SERIALIZED_VALUE] = lazy; + return fn; + } + + /** + * @param {function(): Promise | any} lazy lazy function + * @returns {function(): Promise | any} new lazy + */ + static unMemoizeLazy(lazy) { + if (!SerializerMiddleware.isLazy(lazy)) return lazy; + const fn = () => { + throw new Error( + "A lazy value that has been unmemorized can't be called again" ); - }, - ids: (object, { origin, module }, { compilation: { chunkGraph } }) => { - object.originId = chunkGraph.getModuleId(origin); - object.moduleId = chunkGraph.getModuleId(module); + }; + fn[LAZY_SERIALIZED_VALUE] = SerializerMiddleware.unMemoizeLazy( + lazy[LAZY_SERIALIZED_VALUE] + ); + fn[LAZY_TARGET] = lazy[LAZY_TARGET]; + fn.options = /** @type {any} */ (lazy).options; + return fn; + } +} + +module.exports = SerializerMiddleware; + + +/***/ }), + +/***/ 85199: +/***/ (function(module) { + +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php +*/ + + + +class SetObjectSerializer { + serialize(obj, { write }) { + write(obj.size); + for (const value of obj) { + write(value); } - }, - moduleTraceDependency: { - _: (object, dependency) => { - object.loc = formatLocation(dependency.loc); + } + deserialize({ read }) { + let size = read(); + const set = new Set(); + for (let i = 0; i < size; i++) { + set.add(read()); } + return set; } -}; +} -/** @type {Record boolean | undefined>>} */ -const FILTER = { - "module.reasons": { - "!orphanModules": (reason, { compilation: { chunkGraph } }) => { - if ( - reason.originModule && - chunkGraph.getNumberOfModuleChunks(reason.originModule) === 0 - ) { - return false; - } - } +module.exports = SetObjectSerializer; + + +/***/ }), + +/***/ 63340: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php +*/ + + + +const SerializerMiddleware = __webpack_require__(37063); + +/** + * @typedef {any} DeserializedType + * @typedef {any[]} SerializedType + * @extends {SerializerMiddleware} + */ +class SingleItemMiddleware extends SerializerMiddleware { + /** + * @param {DeserializedType} data data + * @param {Object} context context object + * @returns {SerializedType|Promise} serialized data + */ + serialize(data, context) { + return [data]; } -}; -/** @type {Record boolean | undefined>>} */ -const FILTER_RESULTS = { - "compilation.warnings": { - warningsFilter: util.deprecate( - (warning, context, { warningsFilter }) => { - const warningString = Object.keys(warning) - .map(key => `${warning[key]}`) - .join("\n"); - return !warningsFilter.some(filter => filter(warning, warningString)); - }, - "config.stats.warningsFilter is deprecated in favor of config.ignoreWarnings", - "DEP_WEBPACK_STATS_WARNINGS_FILTER" - ) + /** + * @param {SerializedType} data data + * @param {Object} context context object + * @returns {DeserializedType|Promise} deserialized data + */ + deserialize(data, context) { + return data[0]; } -}; +} -/** @type {Record void>} */ -const MODULES_SORTER = { - _: (comparators, { compilation: { moduleGraph } }) => { - comparators.push( - compareSelect( - /** - * @param {Module} m module - * @returns {number} depth - */ - m => moduleGraph.getDepth(m), - compareNumbers - ), - compareSelect( - /** - * @param {Module} m module - * @returns {number} index - */ - m => moduleGraph.getPreOrderIndex(m), - compareNumbers - ), - compareSelect( - /** - * @param {Module} m module - * @returns {string} identifier - */ - m => m.identifier(), - compareIds - ) - ); +module.exports = SingleItemMiddleware; + + +/***/ }), + +/***/ 90489: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ + + + +const ModuleDependency = __webpack_require__(80944); +const makeSerializable = __webpack_require__(26522); + +class ConsumeSharedFallbackDependency extends ModuleDependency { + constructor(request) { + super(request); } -}; -/** @type {Record void>>} */ -const SORTERS = { - "compilation.chunks": { - _: comparators => { - comparators.push(compareSelect(c => c.id, compareIds)); - } - }, - "compilation.modules": MODULES_SORTER, - "chunk.rootModules": MODULES_SORTER, - "chunk.modules": MODULES_SORTER, - "module.modules": MODULES_SORTER, - "module.reasons": { - _: (comparators, { compilation: { chunkGraph } }) => { - comparators.push( - compareSelect(x => x.originModule, compareModulesByIdentifier) - ); - comparators.push( - compareSelect(x => x.resolvedOriginModule, compareModulesByIdentifier) - ); - comparators.push( - compareSelect( - x => x.dependency, - concatComparators( - compareSelect( - /** - * @param {Dependency} x dependency - * @returns {DependencyLocation} location - */ - x => x.loc, - compareLocations - ), - compareSelect(x => x.type, compareIds) - ) - ) - ); - } - }, - "chunk.origins": { - _: (comparators, { compilation: { chunkGraph } }) => { - comparators.push( - compareSelect( - origin => - origin.module ? chunkGraph.getModuleId(origin.module) : undefined, - compareIds - ), - compareSelect(origin => formatLocation(origin.loc), compareIds), - compareSelect(origin => origin.request, compareIds) - ); - } + get type() { + return "consume shared fallback"; } -}; -const getItemSize = item => { - // Each item takes 1 line - // + the size of the children - // + 1 extra line when it has children and filteredChildren - return !item.children - ? 1 - : item.filteredChildren - ? 2 + getTotalSize(item.children) - : 1 + getTotalSize(item.children); -}; + get category() { + return "esm"; + } +} -const getTotalSize = children => { - let size = 0; - for (const child of children) { - size += getItemSize(child); +makeSerializable( + ConsumeSharedFallbackDependency, + "webpack/lib/sharing/ConsumeSharedFallbackDependency" +); + +module.exports = ConsumeSharedFallbackDependency; + + +/***/ }), + +/***/ 61474: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ + + + +const { RawSource } = __webpack_require__(96192); +const AsyncDependenciesBlock = __webpack_require__(11315); +const Module = __webpack_require__(85887); +const RuntimeGlobals = __webpack_require__(49404); +const makeSerializable = __webpack_require__(26522); +const { rangeToString, stringifyHoley } = __webpack_require__(60473); +const ConsumeSharedFallbackDependency = __webpack_require__(90489); + +/** @typedef {import("../../declarations/WebpackOptions").WebpackOptionsNormalized} WebpackOptions */ +/** @typedef {import("../ChunkGraph")} ChunkGraph */ +/** @typedef {import("../ChunkGroup")} ChunkGroup */ +/** @typedef {import("../Compilation")} Compilation */ +/** @typedef {import("../Dependency").UpdateHashContext} UpdateHashContext */ +/** @typedef {import("../Module").CodeGenerationContext} CodeGenerationContext */ +/** @typedef {import("../Module").CodeGenerationResult} CodeGenerationResult */ +/** @typedef {import("../Module").LibIdentOptions} LibIdentOptions */ +/** @typedef {import("../Module").NeedBuildContext} NeedBuildContext */ +/** @typedef {import("../RequestShortener")} RequestShortener */ +/** @typedef {import("../ResolverFactory").ResolverWithOptions} ResolverWithOptions */ +/** @typedef {import("../WebpackError")} WebpackError */ +/** @typedef {import("../util/Hash")} Hash */ +/** @typedef {import("../util/fs").InputFileSystem} InputFileSystem */ +/** @typedef {import("../util/semver").SemVerRange} SemVerRange */ + +/** + * @typedef {Object} ConsumeOptions + * @property {string=} import fallback request + * @property {string=} importResolved resolved fallback request + * @property {string} shareKey global share key + * @property {string} shareScope share scope + * @property {SemVerRange | false | undefined} requiredVersion version requirement + * @property {string} packageName package name to determine required version automatically + * @property {boolean} strictVersion don't use shared version even if version isn't valid + * @property {boolean} singleton use single global version + * @property {boolean} eager include the fallback module in a sync way + */ + +const TYPES = new Set(["consume-shared"]); + +class ConsumeSharedModule extends Module { + /** + * @param {string} context context + * @param {ConsumeOptions} options consume options + */ + constructor(context, options) { + super("consume-shared-module", context); + this.options = options; } - return size; -}; -const getTotalItems = children => { - let count = 0; - for (const child of children) { - if (!child.children && !child.filteredChildren) { - count++; - } else { - if (child.children) count += getTotalItems(child.children); - if (child.filteredChildren) count += child.filteredChildren; - } + /** + * @returns {string} a unique identifier of the module + */ + identifier() { + const { + shareKey, + shareScope, + importResolved, + requiredVersion, + strictVersion, + singleton, + eager + } = this.options; + return `consume-shared-module|${shareScope}|${shareKey}|${ + requiredVersion && rangeToString(requiredVersion) + }|${strictVersion}|${importResolved}|${singleton}|${eager}`; } - return count; -}; -const collapse = children => { - // After collapse each child must take exactly one line - const newChildren = []; - for (const child of children) { - if (child.children) { - let filteredChildren = child.filteredChildren || 0; - filteredChildren += getTotalItems(child.children); - newChildren.push({ - ...child, - children: undefined, - filteredChildren - }); - } else { - newChildren.push(child); + /** + * @param {RequestShortener} requestShortener the request shortener + * @returns {string} a user readable identifier of the module + */ + readableIdentifier(requestShortener) { + const { + shareKey, + shareScope, + importResolved, + requiredVersion, + strictVersion, + singleton, + eager + } = this.options; + return `consume shared module (${shareScope}) ${shareKey}@${ + requiredVersion ? rangeToString(requiredVersion) : "*" + }${strictVersion ? " (strict)" : ""}${singleton ? " (singleton)" : ""}${ + importResolved + ? ` (fallback: ${requestShortener.shorten(importResolved)})` + : "" + }${eager ? " (eager)" : ""}`; + } + + /** + * @param {LibIdentOptions} options options + * @returns {string | null} an identifier for library inclusion + */ + libIdent(options) { + const { shareKey, shareScope, import: request } = this.options; + return `webpack/sharing/consume/${shareScope}/${shareKey}${ + request ? `/${request}` : "" + }`; + } + + /** + * @param {NeedBuildContext} context context info + * @param {function(WebpackError=, boolean=): void} callback callback function, returns true, if the module needs a rebuild + * @returns {void} + */ + needBuild(context, callback) { + callback(null, !this.buildInfo); + } + + /** + * @param {WebpackOptions} options webpack options + * @param {Compilation} compilation the compilation + * @param {ResolverWithOptions} resolver the resolver + * @param {InputFileSystem} fs the file system + * @param {function(WebpackError=): void} callback callback function + * @returns {void} + */ + build(options, compilation, resolver, fs, callback) { + this.buildMeta = {}; + this.buildInfo = {}; + if (this.options.import) { + const dep = new ConsumeSharedFallbackDependency(this.options.import); + if (this.options.eager) { + this.addDependency(dep); + } else { + const block = new AsyncDependenciesBlock({}); + block.addDependency(dep); + this.addBlock(block); + } } + callback(); } - return newChildren; -}; -const spaceLimited = (itemsAndGroups, max) => { - /** @type {any[] | undefined} */ - let children = undefined; - /** @type {number | undefined} */ - let filteredChildren = undefined; - // This are the groups, which take 1+ lines each - const groups = itemsAndGroups.filter(c => c.children || c.filteredChildren); - // The sizes of the groups are stored in groupSizes - const groupSizes = groups.map(g => getItemSize(g)); - // This are the items, which take 1 line each - const items = itemsAndGroups.filter(c => !c.children && !c.filteredChildren); - // The total of group sizes - let groupsSize = groupSizes.reduce((a, b) => a + b, 0); - if (groupsSize + items.length <= max) { - // The total size in the current state fits into the max - // keep all - children = groups.concat(items); - } else if ( - groups.length > 0 && - groups.length + Math.min(1, items.length) < max - ) { - // If each group would take 1 line the total would be below the maximum - // collapse some groups, keep items - while (groupsSize + items.length + (filteredChildren ? 1 : 0) > max) { - // calculate how much we are over the size limit - // this allows to approach the limit faster - // it's always > 1 - const oversize = - items.length + groupsSize + (filteredChildren ? 1 : 0) - max; - // Find the maximum group and process only this one - const maxGroupSize = Math.max(...groupSizes); - if (maxGroupSize < items.length) { - filteredChildren = items.length; - items.length = 0; - continue; + /** + * @returns {Set} types available (do not mutate) + */ + getSourceTypes() { + return TYPES; + } + + /** + * @param {string=} type the source type for which the size should be estimated + * @returns {number} the estimated size of the module (must be non-zero) + */ + size(type) { + return 42; + } + + /** + * @param {Hash} hash the hash used to track dependencies + * @param {UpdateHashContext} context context + * @returns {void} + */ + updateHash(hash, context) { + hash.update(JSON.stringify(this.options)); + super.updateHash(hash, context); + } + + /** + * @param {CodeGenerationContext} context context for code generation + * @returns {CodeGenerationResult} result + */ + codeGeneration({ chunkGraph, moduleGraph, runtimeTemplate }) { + const runtimeRequirements = new Set([RuntimeGlobals.shareScopeMap]); + const { + shareScope, + shareKey, + strictVersion, + requiredVersion, + import: request, + singleton, + eager + } = this.options; + let fallbackCode; + if (request) { + if (eager) { + const dep = this.dependencies[0]; + fallbackCode = runtimeTemplate.syncModuleFactory({ + dependency: dep, + chunkGraph, + runtimeRequirements, + request: this.options.import + }); + } else { + const block = this.blocks[0]; + fallbackCode = runtimeTemplate.asyncModuleFactory({ + block, + chunkGraph, + runtimeRequirements, + request: this.options.import + }); } - for (let i = 0; i < groups.length; i++) { - if (groupSizes[i] === maxGroupSize) { - const group = groups[i]; - // run this algorithm recursively and limit the size of the children to - // current size - oversize / number of groups - // So it should always end up being smaller - const headerSize = !group.children - ? 0 - : group.filteredChildren - ? 2 - : 1; - const limited = spaceLimited( - group.children, - groupSizes[i] - headerSize - oversize / groups.length - ); - groups[i] = { - ...group, - children: limited.children, - filteredChildren: - (group.filteredChildren || 0) + limited.filteredChildren - }; - const newSize = getItemSize(groups[i]); - groupsSize -= groupSizes[i] - newSize; - groupSizes[i] = newSize; - break; - } + } + let fn = "load"; + const args = [JSON.stringify(shareScope), JSON.stringify(shareKey)]; + if (requiredVersion) { + if (strictVersion) { + fn += "Strict"; + } + if (singleton) { + fn += "Singleton"; } + args.push(stringifyHoley(requiredVersion)); + fn += "VersionCheck"; } - children = groups.concat(items); - } else if ( - groups.length > 0 && - groups.length + Math.min(1, items.length) <= max - ) { - // If we have only enough space to show one line per group and one line for the filtered items - // collapse all groups and items - children = groups.length ? collapse(groups) : undefined; - filteredChildren = items.length; - } else { - // If we have no space - // collapse complete group - filteredChildren = getTotalItems(itemsAndGroups); + if (fallbackCode) { + fn += "Fallback"; + args.push(fallbackCode); + } + const code = runtimeTemplate.returningFunction(`${fn}(${args.join(", ")})`); + const sources = new Map(); + sources.set("consume-shared", new RawSource(code)); + return { + runtimeRequirements, + sources + }; } - return { - children, - filteredChildren - }; -}; -const assetGroup = (children, assets) => { - let size = 0; - for (const asset of children) { - size += asset.size; + serialize(context) { + const { write } = context; + write(this.options); + super.serialize(context); } - return { - size - }; -}; -const moduleGroup = (children, modules) => { - let size = 0; - const sizes = {}; - for (const module of children) { - size += module.size; - for (const key of Object.keys(module.sizes)) { - sizes[key] = (sizes[key] || 0) + module.sizes[key]; - } + deserialize(context) { + const { read } = context; + this.options = read(); + super.deserialize(context); } - return { - size, - sizes - }; -}; +} -const reasonGroup = (children, reasons) => { - let active = false; - for (const reason of children) { - active = active || reason.active; +makeSerializable( + ConsumeSharedModule, + "webpack/lib/sharing/ConsumeSharedModule" +); + +module.exports = ConsumeSharedModule; + + +/***/ }), + +/***/ 19984: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ + + + +const ModuleNotFoundError = __webpack_require__(82908); +const RuntimeGlobals = __webpack_require__(49404); +const WebpackError = __webpack_require__(68422); +const { parseOptions } = __webpack_require__(56084); +const LazySet = __webpack_require__(59534); +const createSchemaValidation = __webpack_require__(77695); +const { parseRange } = __webpack_require__(60473); +const ConsumeSharedFallbackDependency = __webpack_require__(90489); +const ConsumeSharedModule = __webpack_require__(61474); +const ConsumeSharedRuntimeModule = __webpack_require__(830); +const ProvideForSharedDependency = __webpack_require__(40235); +const { resolveMatchedConfigs } = __webpack_require__(18436); +const { + isRequiredVersion, + getDescriptionFile, + getRequiredVersionFromDescriptionFile +} = __webpack_require__(58854); + +/** @typedef {import("../../declarations/plugins/sharing/ConsumeSharedPlugin").ConsumeSharedPluginOptions} ConsumeSharedPluginOptions */ +/** @typedef {import("../../declarations/plugins/sharing/ConsumeSharedPlugin").ConsumesConfig} ConsumesConfig */ +/** @typedef {import("../Compiler")} Compiler */ +/** @typedef {import("../ResolverFactory").ResolveOptionsWithDependencyType} ResolveOptionsWithDependencyType */ +/** @typedef {import("./ConsumeSharedModule").ConsumeOptions} ConsumeOptions */ + +const validate = createSchemaValidation( + __webpack_require__(64246), + () => __webpack_require__(9515), + { + name: "Consume Shared Plugin", + baseDataPath: "options" } - return { - active - }; -}; +); -/** @type {Record void>} */ -const ASSETS_GROUPERS = { - _: (groupConfigs, context, options) => { - const groupByFlag = (name, exclude) => { - groupConfigs.push({ - getKeys: asset => { - return asset[name] ? ["1"] : undefined; - }, - getOptions: () => { - return { - groupChildren: !exclude, - force: exclude - }; - }, - createGroup: (key, children, assets) => { - return exclude - ? { - type: "assets by status", - [name]: !!key, - filteredChildren: assets.length, - ...assetGroup(children, assets) +/** @type {ResolveOptionsWithDependencyType} */ +const RESOLVE_OPTIONS = { dependencyType: "esm" }; +const PLUGIN_NAME = "ConsumeSharedPlugin"; + +class ConsumeSharedPlugin { + /** + * @param {ConsumeSharedPluginOptions} options options + */ + constructor(options) { + if (typeof options !== "string") { + validate(options); + } + + /** @type {[string, ConsumeOptions][]} */ + this._consumes = parseOptions( + options.consumes, + (item, key) => { + if (Array.isArray(item)) throw new Error("Unexpected array in options"); + /** @type {ConsumeOptions} */ + let result = + item === key || !isRequiredVersion(item) + ? // item is a request/key + { + import: key, + shareScope: options.shareScope || "default", + shareKey: key, + requiredVersion: undefined, + packageName: undefined, + strictVersion: false, + singleton: false, + eager: false } - : { - type: "assets by status", - [name]: !!key, - children, - ...assetGroup(children, assets) + : // key is a request/key + // item is a version + { + import: key, + shareScope: options.shareScope || "default", + shareKey: key, + requiredVersion: parseRange(item), + strictVersion: true, + packageName: undefined, + singleton: false, + eager: false }; - } - }); - }; - const { - groupAssetsByEmitStatus, - groupAssetsByPath, - groupAssetsByExtension - } = options; - if (groupAssetsByEmitStatus) { - groupByFlag("emitted"); - groupByFlag("comparedForEmit"); - groupByFlag("isOverSizeLimit"); - } - if (groupAssetsByEmitStatus || !options.cachedAssets) { - groupByFlag("cached", !options.cachedAssets); - } - if (groupAssetsByPath || groupAssetsByExtension) { - groupConfigs.push({ - getKeys: asset => { - const extensionMatch = - groupAssetsByExtension && /(\.[^.]+)(?:\?.*|$)/.exec(asset.name); - const extension = extensionMatch ? extensionMatch[1] : ""; - const pathMatch = - groupAssetsByPath && /(.+)[/\\][^/\\]+(?:\?.*|$)/.exec(asset.name); - const path = pathMatch ? pathMatch[1].split(/[/\\]/) : []; - const keys = []; - if (groupAssetsByPath) { - keys.push("."); - if (extension) - keys.push( - path.length - ? `${path.join("/")}/*${extension}` - : `*${extension}` - ); - while (path.length > 0) { - keys.push(path.join("/") + "/"); - path.pop(); - } - } else { - if (extension) keys.push(`*${extension}`); - } - return keys; - }, - createGroup: (key, children, assets) => { - return { - type: groupAssetsByPath ? "assets by path" : "assets by extension", - name: key, - children, - ...assetGroup(children, assets) - }; - } - }); - } - }, - groupAssetsByInfo: (groupConfigs, context, options) => { - const groupByAssetInfoFlag = name => { - groupConfigs.push({ - getKeys: asset => { - return asset.info && asset.info[name] ? ["1"] : undefined; - }, - createGroup: (key, children, assets) => { - return { - type: "assets by info", - info: { - [name]: !!key - }, - children, - ...assetGroup(children, assets) - }; - } - }); - }; - groupByAssetInfoFlag("immutable"); - groupByAssetInfoFlag("development"); - groupByAssetInfoFlag("hotModuleReplacement"); - }, - groupAssetsByChunk: (groupConfigs, context, options) => { - const groupByNames = name => { - groupConfigs.push({ - getKeys: asset => { - return asset[name]; - }, - createGroup: (key, children, assets) => { - return { - type: "assets by chunk", - [name]: [key], - children, - ...assetGroup(children, assets) - }; - } - }); - }; - groupByNames("chunkNames"); - groupByNames("auxiliaryChunkNames"); - groupByNames("chunkIdHints"); - groupByNames("auxiliaryChunkIdHints"); - }, - excludeAssets: (groupConfigs, context, { excludeAssets }) => { - groupConfigs.push({ - getKeys: asset => { - const ident = asset.name; - const excluded = excludeAssets.some(fn => fn(ident, asset)); - if (excluded) return ["excluded"]; + return result; }, - getOptions: () => ({ - groupChildren: false, - force: true - }), - createGroup: (key, children, assets) => ({ - type: "hidden assets", - filteredChildren: assets.length, - ...assetGroup(children, assets) + (item, key) => ({ + import: item.import === false ? undefined : item.import || key, + shareScope: item.shareScope || options.shareScope || "default", + shareKey: item.shareKey || key, + requiredVersion: + typeof item.requiredVersion === "string" + ? parseRange(item.requiredVersion) + : item.requiredVersion, + strictVersion: + typeof item.strictVersion === "boolean" + ? item.strictVersion + : item.import !== false && !item.singleton, + packageName: item.packageName, + singleton: !!item.singleton, + eager: !!item.eager }) - }); + ); + } + + /** + * Apply the plugin + * @param {Compiler} compiler the compiler instance + * @returns {void} + */ + apply(compiler) { + compiler.hooks.thisCompilation.tap( + PLUGIN_NAME, + (compilation, { normalModuleFactory }) => { + compilation.dependencyFactories.set( + ConsumeSharedFallbackDependency, + normalModuleFactory + ); + + let unresolvedConsumes, resolvedConsumes, prefixedConsumes; + const promise = resolveMatchedConfigs(compilation, this._consumes).then( + ({ resolved, unresolved, prefixed }) => { + resolvedConsumes = resolved; + unresolvedConsumes = unresolved; + prefixedConsumes = prefixed; + } + ); + + const resolver = compilation.resolverFactory.get( + "normal", + RESOLVE_OPTIONS + ); + + /** + * @param {string} context issuer directory + * @param {string} request request + * @param {ConsumeOptions} config options + * @returns {Promise} create module + */ + const createConsumeSharedModule = (context, request, config) => { + const requiredVersionWarning = details => { + const error = new WebpackError( + `No required version specified and unable to automatically determine one. ${details}` + ); + error.file = `shared module ${request}`; + compilation.warnings.push(error); + }; + const directFallback = + config.import && + /^(\.\.?(\/|$)|\/|[A-Za-z]:|\\\\)/.test(config.import); + return Promise.all([ + new Promise(resolve => { + if (!config.import) return resolve(); + const resolveContext = { + /** @type {LazySet} */ + fileDependencies: new LazySet(), + /** @type {LazySet} */ + contextDependencies: new LazySet(), + /** @type {LazySet} */ + missingDependencies: new LazySet() + }; + resolver.resolve( + {}, + directFallback ? compiler.context : context, + config.import, + resolveContext, + (err, result) => { + compilation.contextDependencies.addAll( + resolveContext.contextDependencies + ); + compilation.fileDependencies.addAll( + resolveContext.fileDependencies + ); + compilation.missingDependencies.addAll( + resolveContext.missingDependencies + ); + if (err) { + compilation.errors.push( + new ModuleNotFoundError(null, err, { + name: `resolving fallback for shared module ${request}` + }) + ); + return resolve(); + } + resolve(result); + } + ); + }), + new Promise(resolve => { + if (config.requiredVersion !== undefined) + return resolve(config.requiredVersion); + let packageName = config.packageName; + if (packageName === undefined) { + if (/^(\/|[A-Za-z]:|\\\\)/.test(request)) { + // For relative or absolute requests we don't automatically use a packageName. + // If wished one can specify one with the packageName option. + return resolve(); + } + const match = /^((?:@[^\\/]+[\\/])?[^\\/]+)/.exec(request); + if (!match) { + requiredVersionWarning( + "Unable to extract the package name from request." + ); + return resolve(); + } + packageName = match[0]; + } + + getDescriptionFile( + compilation.inputFileSystem, + context, + ["package.json"], + (err, result) => { + if (err) { + requiredVersionWarning( + `Unable to read description file: ${err}` + ); + return resolve(); + } + const { data, path: descriptionPath } = result; + if (!data) { + requiredVersionWarning( + `Unable to find description file in ${context}.` + ); + return resolve(); + } + const requiredVersion = getRequiredVersionFromDescriptionFile( + data, + packageName + ); + if (typeof requiredVersion !== "string") { + requiredVersionWarning( + `Unable to find required version for "${packageName}" in description file (${descriptionPath}). It need to be in dependencies, devDependencies or peerDependencies.` + ); + return resolve(); + } + resolve(parseRange(requiredVersion)); + } + ); + }) + ]).then(([importResolved, requiredVersion]) => { + return new ConsumeSharedModule( + directFallback ? compiler.context : context, + { + ...config, + importResolved, + import: importResolved ? config.import : undefined, + requiredVersion + } + ); + }); + }; + + normalModuleFactory.hooks.factorize.tapPromise( + PLUGIN_NAME, + ({ context, request, dependencies }) => + // wait for resolving to be complete + promise.then(() => { + if ( + dependencies[0] instanceof ConsumeSharedFallbackDependency || + dependencies[0] instanceof ProvideForSharedDependency + ) { + return; + } + const match = unresolvedConsumes.get(request); + if (match !== undefined) { + return createConsumeSharedModule(context, request, match); + } + for (const [prefix, options] of prefixedConsumes) { + if (request.startsWith(prefix)) { + const remainder = request.slice(prefix.length); + return createConsumeSharedModule(context, request, { + ...options, + import: options.import + ? options.import + remainder + : undefined, + shareKey: options.shareKey + remainder + }); + } + } + }) + ); + normalModuleFactory.hooks.createModule.tapPromise( + PLUGIN_NAME, + ({ resource }, { context, dependencies }) => { + if ( + dependencies[0] instanceof ConsumeSharedFallbackDependency || + dependencies[0] instanceof ProvideForSharedDependency + ) { + return Promise.resolve(); + } + const options = resolvedConsumes.get(resource); + if (options !== undefined) { + return createConsumeSharedModule(context, resource, options); + } + return Promise.resolve(); + } + ); + compilation.hooks.additionalTreeRuntimeRequirements.tap( + PLUGIN_NAME, + (chunk, set) => { + set.add(RuntimeGlobals.module); + set.add(RuntimeGlobals.moduleCache); + set.add(RuntimeGlobals.moduleFactoriesAddOnly); + set.add(RuntimeGlobals.shareScopeMap); + set.add(RuntimeGlobals.initializeSharing); + set.add(RuntimeGlobals.hasOwnProperty); + compilation.addRuntimeModule( + chunk, + new ConsumeSharedRuntimeModule(set) + ); + } + ); + } + ); } -}; +} -/** @type {function("module" | "chunk" | "root-of-chunk" | "nested"): Record void>} */ -const MODULES_GROUPERS = type => ({ - _: (groupConfigs, context, options) => { - const groupByFlag = (name, type, exclude) => { - groupConfigs.push({ - getKeys: module => { - return module[name] ? ["1"] : undefined; - }, - getOptions: () => { - return { - groupChildren: !exclude, - force: exclude - }; - }, - createGroup: (key, children, modules) => { - return { - type, - [name]: !!key, - ...(exclude ? { filteredChildren: modules.length } : { children }), - ...moduleGroup(children, modules) - }; - } - }); +module.exports = ConsumeSharedPlugin; + + +/***/ }), + +/***/ 830: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ + + + +const RuntimeGlobals = __webpack_require__(49404); +const RuntimeModule = __webpack_require__(61439); +const Template = __webpack_require__(92066); +const { + parseVersionRuntimeCode, + versionLtRuntimeCode, + rangeToStringRuntimeCode, + satisfyRuntimeCode +} = __webpack_require__(60473); + +/** @typedef {import("webpack-sources").Source} Source */ +/** @typedef {import("../Chunk")} Chunk */ +/** @typedef {import("../Module")} Module */ +/** @typedef {import("./ConsumeSharedModule")} ConsumeSharedModule */ + +class ConsumeSharedRuntimeModule extends RuntimeModule { + constructor(runtimeRequirements) { + super("consumes", RuntimeModule.STAGE_ATTACH); + this._runtimeRequirements = runtimeRequirements; + } + + /** + * @returns {string} runtime code + */ + generate() { + const { compilation, chunkGraph } = this; + const { runtimeTemplate, codeGenerationResults } = compilation; + const chunkToModuleMapping = {}; + /** @type {Map} */ + const moduleIdToSourceMapping = new Map(); + const initialConsumes = []; + /** + * + * @param {Iterable} modules modules + * @param {Chunk} chunk the chunk + * @param {(string | number)[]} list list of ids + */ + const addModules = (modules, chunk, list) => { + for (const m of modules) { + const module = /** @type {ConsumeSharedModule} */ (m); + const id = chunkGraph.getModuleId(module); + list.push(id); + moduleIdToSourceMapping.set( + id, + codeGenerationResults.getSource( + module, + chunk.runtime, + "consume-shared" + ) + ); + } }; - const { - groupModulesByCacheStatus, - groupModulesByLayer, - groupModulesByAttributes, - groupModulesByType, - groupModulesByPath, - groupModulesByExtension - } = options; - if (groupModulesByAttributes) { - groupByFlag("errors", "modules with errors"); - groupByFlag("warnings", "modules with warnings"); - groupByFlag("assets", "modules with assets"); - groupByFlag("optional", "optional modules"); - } - if (groupModulesByCacheStatus) { - groupByFlag("cacheable", "cacheable modules"); - groupByFlag("built", "built modules"); - groupByFlag("codeGenerated", "code generated modules"); - } - if (groupModulesByCacheStatus || !options.cachedModules) { - groupByFlag("cached", "cached modules", !options.cachedModules); - } - if (groupModulesByAttributes || !options.orphanModules) { - groupByFlag("orphan", "orphan modules", !options.orphanModules); - } - if (groupModulesByAttributes || !options.dependentModules) { - groupByFlag("dependent", "dependent modules", !options.dependentModules); - } - if (groupModulesByType || !options.runtimeModules) { - groupConfigs.push({ - getKeys: module => { - if (!module.moduleType) return; - if (groupModulesByType) { - return [module.moduleType.split("/", 1)[0]]; - } else if (module.moduleType === "runtime") { - return ["runtime"]; - } - }, - getOptions: key => { - const exclude = key === "runtime" && !options.runtimeModules; - return { - groupChildren: !exclude, - force: exclude - }; - }, - createGroup: (key, children, modules) => { - const exclude = key === "runtime" && !options.runtimeModules; - return { - type: `${key} modules`, - moduleType: key, - ...(exclude ? { filteredChildren: modules.length } : { children }), - ...moduleGroup(children, modules) - }; - } - }); - } - if (groupModulesByLayer) { - groupConfigs.push({ - getKeys: module => { - return [module.layer]; - }, - createGroup: (key, children, modules) => { - return { - type: "modules by layer", - layer: key, - children, - ...moduleGroup(children, modules) - }; - } - }); + for (const chunk of this.chunk.getAllAsyncChunks()) { + const modules = chunkGraph.getChunkModulesIterableBySourceType( + chunk, + "consume-shared" + ); + if (!modules) continue; + addModules(modules, chunk, (chunkToModuleMapping[chunk.id] = [])); } - if (groupModulesByPath || groupModulesByExtension) { - groupConfigs.push({ - getKeys: module => { - if (!module.name) return; - const resource = parseResource(module.name.split("!").pop()).path; - const extensionMatch = - groupModulesByExtension && /(\.[^.]+)(?:\?.*|$)/.exec(resource); - const extension = extensionMatch ? extensionMatch[1] : ""; - const pathMatch = - groupModulesByPath && /(.+)[/\\][^/\\]+(?:\?.*|$)/.exec(resource); - const path = pathMatch ? pathMatch[1].split(/[/\\]/) : []; - const keys = []; - if (groupModulesByPath) { - if (extension) - keys.push( - path.length - ? `${path.join("/")}/*${extension}` - : `*${extension}` - ); - while (path.length > 0) { - keys.push(path.join("/") + "/"); - path.pop(); - } - } else { - if (extension) keys.push(`*${extension}`); - } - return keys; - }, - createGroup: (key, children, modules) => { - return { - type: groupModulesByPath - ? "modules by path" - : "modules by extension", - name: key, - children, - ...moduleGroup(children, modules) - }; - } - }); + for (const chunk of this.chunk.getAllInitialChunks()) { + const modules = chunkGraph.getChunkModulesIterableBySourceType( + chunk, + "consume-shared" + ); + if (!modules) continue; + addModules(modules, chunk, initialConsumes); } - }, - excludeModules: (groupConfigs, context, { excludeModules }) => { - groupConfigs.push({ - getKeys: module => { - const name = module.name; - if (name) { - const excluded = excludeModules.some(fn => fn(name, module, type)); - if (excluded) return ["1"]; - } - }, - getOptions: () => ({ - groupChildren: false, - force: true - }), - createGroup: (key, children, modules) => ({ - type: "hidden modules", - filteredChildren: children.length, - ...moduleGroup(children, modules) - }) - }); + if (moduleIdToSourceMapping.size === 0) return null; + return Template.asString([ + parseVersionRuntimeCode(runtimeTemplate), + versionLtRuntimeCode(runtimeTemplate), + rangeToStringRuntimeCode(runtimeTemplate), + satisfyRuntimeCode(runtimeTemplate), + `var ensureExistence = ${runtimeTemplate.basicFunction("scopeName, key", [ + `var scope = ${RuntimeGlobals.shareScopeMap}[scopeName];`, + `if(!scope || !${RuntimeGlobals.hasOwnProperty}(scope, key)) throw new Error("Shared module " + key + " doesn't exist in shared scope " + scopeName);`, + "return scope;" + ])};`, + `var findVersion = ${runtimeTemplate.basicFunction("scope, key", [ + "var versions = scope[key];", + `var key = Object.keys(versions).reduce(${runtimeTemplate.basicFunction( + "a, b", + ["return !a || versionLt(a, b) ? b : a;"] + )}, 0);`, + "return key && versions[key]" + ])};`, + `var findSingletonVersionKey = ${runtimeTemplate.basicFunction( + "scope, key", + [ + "var versions = scope[key];", + `return Object.keys(versions).reduce(${runtimeTemplate.basicFunction( + "a, b", + ["return !a || (!versions[a].loaded && versionLt(a, b)) ? b : a;"] + )}, 0);` + ] + )};`, + `var getInvalidSingletonVersionMessage = ${runtimeTemplate.basicFunction( + "key, version, requiredVersion", + [ + `return "Unsatisfied version " + version + " of shared singleton module " + key + " (required " + rangeToString(requiredVersion) + ")"` + ] + )};`, + `var getSingletonVersion = ${runtimeTemplate.basicFunction( + "scope, scopeName, key, requiredVersion", + [ + "var version = findSingletonVersionKey(scope, key);", + "if (!satisfy(requiredVersion, version)) " + + 'typeof console !== "undefined" && console.warn && console.warn(getInvalidSingletonVersionMessage(key, version, requiredVersion));', + "return get(scope[key][version]);" + ] + )};`, + `var getStrictSingletonVersion = ${runtimeTemplate.basicFunction( + "scope, scopeName, key, requiredVersion", + [ + "var version = findSingletonVersionKey(scope, key);", + "if (!satisfy(requiredVersion, version)) " + + "throw new Error(getInvalidSingletonVersionMessage(key, version, requiredVersion));", + "return get(scope[key][version]);" + ] + )};`, + `var findValidVersion = ${runtimeTemplate.basicFunction( + "scope, key, requiredVersion", + [ + "var versions = scope[key];", + `var key = Object.keys(versions).reduce(${runtimeTemplate.basicFunction( + "a, b", + [ + "if (!satisfy(requiredVersion, b)) return a;", + "return !a || versionLt(a, b) ? b : a;" + ] + )}, 0);`, + "return key && versions[key]" + ] + )};`, + `var getInvalidVersionMessage = ${runtimeTemplate.basicFunction( + "scope, scopeName, key, requiredVersion", + [ + "var versions = scope[key];", + 'return "No satisfying version (" + rangeToString(requiredVersion) + ") of shared module " + key + " found in shared scope " + scopeName + ".\\n" +', + `\t"Available versions: " + Object.keys(versions).map(${runtimeTemplate.basicFunction( + "key", + ['return key + " from " + versions[key].from;'] + )}).join(", ");` + ] + )};`, + `var getValidVersion = ${runtimeTemplate.basicFunction( + "scope, scopeName, key, requiredVersion", + [ + "var entry = findValidVersion(scope, key, requiredVersion);", + "if(entry) return get(entry);", + "throw new Error(getInvalidVersionMessage(scope, scopeName, key, requiredVersion));" + ] + )};`, + `var warnInvalidVersion = ${runtimeTemplate.basicFunction( + "scope, scopeName, key, requiredVersion", + [ + 'typeof console !== "undefined" && console.warn && console.warn(getInvalidVersionMessage(scope, scopeName, key, requiredVersion));' + ] + )};`, + `var get = ${runtimeTemplate.basicFunction("entry", [ + "entry.loaded = 1;", + "return entry.get()" + ])};`, + `var init = ${runtimeTemplate.returningFunction( + Template.asString([ + "function(scopeName, a, b, c) {", + Template.indent([ + `var promise = ${RuntimeGlobals.initializeSharing}(scopeName);`, + `if (promise && promise.then) return promise.then(fn.bind(fn, scopeName, ${RuntimeGlobals.shareScopeMap}[scopeName], a, b, c));`, + `return fn(scopeName, ${RuntimeGlobals.shareScopeMap}[scopeName], a, b, c);` + ]), + "}" + ]), + "fn" + )};`, + "", + `var load = /*#__PURE__*/ init(${runtimeTemplate.basicFunction( + "scopeName, scope, key", + [ + "ensureExistence(scopeName, key);", + "return get(findVersion(scope, key));" + ] + )});`, + `var loadFallback = /*#__PURE__*/ init(${runtimeTemplate.basicFunction( + "scopeName, scope, key, fallback", + [ + `return scope && ${RuntimeGlobals.hasOwnProperty}(scope, key) ? get(findVersion(scope, key)) : fallback();` + ] + )});`, + `var loadVersionCheck = /*#__PURE__*/ init(${runtimeTemplate.basicFunction( + "scopeName, scope, key, version", + [ + "ensureExistence(scopeName, key);", + "return get(findValidVersion(scope, key, version) || warnInvalidVersion(scope, scopeName, key, version) || findVersion(scope, key));" + ] + )});`, + `var loadSingletonVersionCheck = /*#__PURE__*/ init(${runtimeTemplate.basicFunction( + "scopeName, scope, key, version", + [ + "ensureExistence(scopeName, key);", + "return getSingletonVersion(scope, scopeName, key, version);" + ] + )});`, + `var loadStrictVersionCheck = /*#__PURE__*/ init(${runtimeTemplate.basicFunction( + "scopeName, scope, key, version", + [ + "ensureExistence(scopeName, key);", + "return getValidVersion(scope, scopeName, key, version);" + ] + )});`, + `var loadStrictSingletonVersionCheck = /*#__PURE__*/ init(${runtimeTemplate.basicFunction( + "scopeName, scope, key, version", + [ + "ensureExistence(scopeName, key);", + "return getStrictSingletonVersion(scope, scopeName, key, version);" + ] + )});`, + `var loadVersionCheckFallback = /*#__PURE__*/ init(${runtimeTemplate.basicFunction( + "scopeName, scope, key, version, fallback", + [ + `if(!scope || !${RuntimeGlobals.hasOwnProperty}(scope, key)) return fallback();`, + "return get(findValidVersion(scope, key, version) || warnInvalidVersion(scope, scopeName, key, version) || findVersion(scope, key));" + ] + )});`, + `var loadSingletonVersionCheckFallback = /*#__PURE__*/ init(${runtimeTemplate.basicFunction( + "scopeName, scope, key, version, fallback", + [ + `if(!scope || !${RuntimeGlobals.hasOwnProperty}(scope, key)) return fallback();`, + "return getSingletonVersion(scope, scopeName, key, version);" + ] + )});`, + `var loadStrictVersionCheckFallback = /*#__PURE__*/ init(${runtimeTemplate.basicFunction( + "scopeName, scope, key, version, fallback", + [ + `var entry = scope && ${RuntimeGlobals.hasOwnProperty}(scope, key) && findValidVersion(scope, key, version);`, + `return entry ? get(entry) : fallback();` + ] + )});`, + `var loadStrictSingletonVersionCheckFallback = /*#__PURE__*/ init(${runtimeTemplate.basicFunction( + "scopeName, scope, key, version, fallback", + [ + `if(!scope || !${RuntimeGlobals.hasOwnProperty}(scope, key)) return fallback();`, + "return getStrictSingletonVersion(scope, scopeName, key, version);" + ] + )});`, + "var installedModules = {};", + "var moduleToHandlerMapping = {", + Template.indent( + Array.from( + moduleIdToSourceMapping, + ([key, source]) => `${JSON.stringify(key)}: ${source.source()}` + ).join(",\n") + ), + "};", + + initialConsumes.length > 0 + ? Template.asString([ + `var initialConsumes = ${JSON.stringify(initialConsumes)};`, + `initialConsumes.forEach(${runtimeTemplate.basicFunction("id", [ + `${ + RuntimeGlobals.moduleFactories + }[id] = ${runtimeTemplate.basicFunction("module", [ + "// Handle case when module is used sync", + "installedModules[id] = 0;", + `delete ${RuntimeGlobals.moduleCache}[id];`, + "var factory = moduleToHandlerMapping[id]();", + 'if(typeof factory !== "function") throw new Error("Shared module is not available for eager consumption: " + id);', + `module.exports = factory();` + ])}` + ])});` + ]) + : "// no consumes in initial chunks", + this._runtimeRequirements.has(RuntimeGlobals.ensureChunkHandlers) + ? Template.asString([ + `var chunkMapping = ${JSON.stringify( + chunkToModuleMapping, + null, + "\t" + )};`, + `${ + RuntimeGlobals.ensureChunkHandlers + }.consumes = ${runtimeTemplate.basicFunction("chunkId, promises", [ + `if(${RuntimeGlobals.hasOwnProperty}(chunkMapping, chunkId)) {`, + Template.indent([ + `chunkMapping[chunkId].forEach(${runtimeTemplate.basicFunction( + "id", + [ + `if(${RuntimeGlobals.hasOwnProperty}(installedModules, id)) return promises.push(installedModules[id]);`, + `var onFactory = ${runtimeTemplate.basicFunction( + "factory", + [ + "installedModules[id] = 0;", + `${ + RuntimeGlobals.moduleFactories + }[id] = ${runtimeTemplate.basicFunction("module", [ + `delete ${RuntimeGlobals.moduleCache}[id];`, + "module.exports = factory();" + ])}` + ] + )};`, + `var onError = ${runtimeTemplate.basicFunction("error", [ + "delete installedModules[id];", + `${ + RuntimeGlobals.moduleFactories + }[id] = ${runtimeTemplate.basicFunction("module", [ + `delete ${RuntimeGlobals.moduleCache}[id];`, + "throw error;" + ])}` + ])};`, + "try {", + Template.indent([ + "var promise = moduleToHandlerMapping[id]();", + "if(promise.then) {", + Template.indent( + "promises.push(installedModules[id] = promise.then(onFactory)['catch'](onError));" + ), + "} else onFactory(promise);" + ]), + "} catch(e) { onError(e); }" + ] + )});` + ]), + "}" + ])}` + ]) + : "// no chunk loading of consumes" + ]); } -}); +} -/** @type {Record void>>} */ -const RESULT_GROUPERS = { - "compilation.assets": ASSETS_GROUPERS, - "asset.related": ASSETS_GROUPERS, - "compilation.modules": MODULES_GROUPERS("module"), - "chunk.modules": MODULES_GROUPERS("chunk"), - "chunk.rootModules": MODULES_GROUPERS("root-of-chunk"), - "module.modules": MODULES_GROUPERS("nested"), - "module.reasons": { - groupReasonsByOrigin: groupConfigs => { - groupConfigs.push({ - getKeys: reason => { - return [reason.module]; - }, - createGroup: (key, children, reasons) => { - return { - type: "from origin", - module: key, - children, - ...reasonGroup(children, reasons) - }; - } - }); - } - } -}; +module.exports = ConsumeSharedRuntimeModule; -// remove a prefixed "!" that can be specified to reverse sort order -const normalizeFieldKey = field => { - if (field[0] === "!") { - return field.substr(1); + +/***/ }), + +/***/ 40235: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ + + + +const ModuleDependency = __webpack_require__(80944); +const makeSerializable = __webpack_require__(26522); + +class ProvideForSharedDependency extends ModuleDependency { + /** + * + * @param {string} request request string + */ + constructor(request) { + super(request); } - return field; -}; -// if a field is prefixed by a "!" reverse sort order -const sortOrderRegular = field => { - if (field[0] === "!") { - return false; + get type() { + return "provide module for shared"; } - return true; -}; -/** - * @param {string} field field name - * @returns {function(Object, Object): number} comparators - */ -const sortByField = field => { - if (!field) { - /** - * @param {any} a first - * @param {any} b second - * @returns {-1|0|1} zero - */ - const noSort = (a, b) => 0; - return noSort; + get category() { + return "esm"; } +} - const fieldKey = normalizeFieldKey(field); +makeSerializable( + ProvideForSharedDependency, + "webpack/lib/sharing/ProvideForSharedDependency" +); - let sortFn = compareSelect(m => m[fieldKey], compareIds); +module.exports = ProvideForSharedDependency; - // if a field is prefixed with a "!" the sort is reversed! - const sortIsRegular = sortOrderRegular(field); - if (!sortIsRegular) { - const oldSortFn = sortFn; - sortFn = (a, b) => oldSortFn(b, a); +/***/ }), + +/***/ 99355: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ + + + +const Dependency = __webpack_require__(50384); +const makeSerializable = __webpack_require__(26522); + +class ProvideSharedDependency extends Dependency { + constructor(shareScope, name, version, request, eager) { + super(); + this.shareScope = shareScope; + this.name = name; + this.version = version; + this.request = request; + this.eager = eager; } - return sortFn; -}; + get type() { + return "provide shared module"; + } -const ASSET_SORTERS = { - /** @type {(comparators: Function[], context: StatsFactoryContext, options: NormalizedStatsOptions) => void} */ - assetsSort: (comparators, context, { assetsSort }) => { - comparators.push(sortByField(assetsSort)); - }, - _: comparators => { - comparators.push(compareSelect(a => a.name, compareIds)); + /** + * @returns {string | null} an identifier to merge equal requests + */ + getResourceIdentifier() { + return `provide module (${this.shareScope}) ${this.request} as ${ + this.name + } @ ${this.version}${this.eager ? " (eager)" : ""}`; } -}; -/** @type {Record void>>} */ -const RESULT_SORTERS = { - "compilation.chunks": { - chunksSort: (comparators, context, { chunksSort }) => { - comparators.push(sortByField(chunksSort)); - } - }, - "compilation.modules": { - modulesSort: (comparators, context, { modulesSort }) => { - comparators.push(sortByField(modulesSort)); - } - }, - "chunk.modules": { - chunkModulesSort: (comparators, context, { chunkModulesSort }) => { - comparators.push(sortByField(chunkModulesSort)); - } - }, - "module.modules": { - nestedModulesSort: (comparators, context, { nestedModulesSort }) => { - comparators.push(sortByField(nestedModulesSort)); - } - }, - "compilation.assets": ASSET_SORTERS, - "asset.related": ASSET_SORTERS -}; + serialize(context) { + context.write(this.shareScope); + context.write(this.name); + context.write(this.request); + context.write(this.version); + context.write(this.eager); + super.serialize(context); + } -/** - * @param {Record>} config the config see above - * @param {NormalizedStatsOptions} options stats options - * @param {function(string, Function): void} fn handler function called for every active line in config - * @returns {void} - */ -const iterateConfig = (config, options, fn) => { - for (const hookFor of Object.keys(config)) { - const subConfig = config[hookFor]; - for (const option of Object.keys(subConfig)) { - if (option !== "_") { - if (option.startsWith("!")) { - if (options[option.slice(1)]) continue; - } else { - const value = options[option]; - if ( - value === false || - value === undefined || - (Array.isArray(value) && value.length === 0) - ) - continue; - } - } - fn(hookFor, subConfig[option]); - } + static deserialize(context) { + const { read } = context; + const obj = new ProvideSharedDependency( + read(), + read(), + read(), + read(), + read() + ); + this.shareScope = context.read(); + obj.deserialize(context); + return obj; } -}; +} -/** @type {Record} */ -const ITEM_NAMES = { - "compilation.children[]": "compilation", - "compilation.modules[]": "module", - "compilation.entrypoints[]": "chunkGroup", - "compilation.namedChunkGroups[]": "chunkGroup", - "compilation.errors[]": "error", - "compilation.warnings[]": "warning", - "chunk.modules[]": "module", - "chunk.rootModules[]": "module", - "chunk.origins[]": "chunkOrigin", - "compilation.chunks[]": "chunk", - "compilation.assets[]": "asset", - "asset.related[]": "asset", - "module.issuerPath[]": "moduleIssuer", - "module.reasons[]": "moduleReason", - "module.modules[]": "module", - "module.children[]": "module", - "moduleTrace[]": "moduleTraceItem", - "moduleTraceItem.dependencies[]": "moduleTraceDependency" -}; +makeSerializable( + ProvideSharedDependency, + "webpack/lib/sharing/ProvideSharedDependency" +); -/** - * @param {Object[]} items items to be merged - * @returns {Object} an object - */ -const mergeToObject = items => { - const obj = Object.create(null); - for (const item of items) { - obj[item.name] = item; +module.exports = ProvideSharedDependency; + + +/***/ }), + +/***/ 65945: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra and Zackary Jackson @ScriptedAlchemy +*/ + + + +const AsyncDependenciesBlock = __webpack_require__(11315); +const Module = __webpack_require__(85887); +const RuntimeGlobals = __webpack_require__(49404); +const makeSerializable = __webpack_require__(26522); +const ProvideForSharedDependency = __webpack_require__(40235); + +/** @typedef {import("../../declarations/WebpackOptions").WebpackOptionsNormalized} WebpackOptions */ +/** @typedef {import("../Chunk")} Chunk */ +/** @typedef {import("../ChunkGraph")} ChunkGraph */ +/** @typedef {import("../ChunkGroup")} ChunkGroup */ +/** @typedef {import("../Compilation")} Compilation */ +/** @typedef {import("../Module").CodeGenerationContext} CodeGenerationContext */ +/** @typedef {import("../Module").CodeGenerationResult} CodeGenerationResult */ +/** @typedef {import("../Module").LibIdentOptions} LibIdentOptions */ +/** @typedef {import("../Module").NeedBuildContext} NeedBuildContext */ +/** @typedef {import("../RequestShortener")} RequestShortener */ +/** @typedef {import("../ResolverFactory").ResolverWithOptions} ResolverWithOptions */ +/** @typedef {import("../WebpackError")} WebpackError */ +/** @typedef {import("../util/Hash")} Hash */ +/** @typedef {import("../util/fs").InputFileSystem} InputFileSystem */ + +const TYPES = new Set(["share-init"]); + +class ProvideSharedModule extends Module { + /** + * @param {string} shareScope shared scope name + * @param {string} name shared key + * @param {string | false} version version + * @param {string} request request to the provided module + * @param {boolean} eager include the module in sync way + */ + constructor(shareScope, name, version, request, eager) { + super("provide-module"); + this._shareScope = shareScope; + this._name = name; + this._version = version; + this._request = request; + this._eager = eager; } - return obj; -}; -/** @type {Record any>} */ -const MERGER = { - "compilation.entrypoints": mergeToObject, - "compilation.namedChunkGroups": mergeToObject -}; + /** + * @returns {string} a unique identifier of the module + */ + identifier() { + return `provide module (${this._shareScope}) ${this._name}@${this._version} = ${this._request}`; + } -class DefaultStatsFactoryPlugin { /** - * Apply the plugin - * @param {Compiler} compiler the compiler instance + * @param {RequestShortener} requestShortener the request shortener + * @returns {string} a user readable identifier of the module + */ + readableIdentifier(requestShortener) { + return `provide shared module (${this._shareScope}) ${this._name}@${ + this._version + } = ${requestShortener.shorten(this._request)}`; + } + + /** + * @param {LibIdentOptions} options options + * @returns {string | null} an identifier for library inclusion + */ + libIdent(options) { + return `webpack/sharing/provide/${this._shareScope}/${this._name}`; + } + + /** + * @param {NeedBuildContext} context context info + * @param {function(WebpackError=, boolean=): void} callback callback function, returns true, if the module needs a rebuild * @returns {void} */ - apply(compiler) { - compiler.hooks.compilation.tap("DefaultStatsFactoryPlugin", compilation => { - compilation.hooks.statsFactory.tap( - "DefaultStatsFactoryPlugin", - (stats, options, context) => { - iterateConfig(SIMPLE_EXTRACTORS, options, (hookFor, fn) => { - stats.hooks.extract - .for(hookFor) - .tap("DefaultStatsFactoryPlugin", (obj, data, ctx) => - fn(obj, data, ctx, options, stats) - ); - }); - iterateConfig(FILTER, options, (hookFor, fn) => { - stats.hooks.filter - .for(hookFor) - .tap("DefaultStatsFactoryPlugin", (item, ctx, idx, i) => - fn(item, ctx, options, idx, i) - ); - }); - iterateConfig(FILTER_RESULTS, options, (hookFor, fn) => { - stats.hooks.filterResults - .for(hookFor) - .tap("DefaultStatsFactoryPlugin", (item, ctx, idx, i) => - fn(item, ctx, options, idx, i) - ); - }); - iterateConfig(SORTERS, options, (hookFor, fn) => { - stats.hooks.sort - .for(hookFor) - .tap("DefaultStatsFactoryPlugin", (comparators, ctx) => - fn(comparators, ctx, options) - ); - }); - iterateConfig(RESULT_SORTERS, options, (hookFor, fn) => { - stats.hooks.sortResults - .for(hookFor) - .tap("DefaultStatsFactoryPlugin", (comparators, ctx) => - fn(comparators, ctx, options) - ); - }); - iterateConfig(RESULT_GROUPERS, options, (hookFor, fn) => { - stats.hooks.groupResults - .for(hookFor) - .tap("DefaultStatsFactoryPlugin", (groupConfigs, ctx) => - fn(groupConfigs, ctx, options) - ); - }); - for (const key of Object.keys(ITEM_NAMES)) { - const itemName = ITEM_NAMES[key]; - stats.hooks.getItemName - .for(key) - .tap("DefaultStatsFactoryPlugin", () => itemName); - } - for (const key of Object.keys(MERGER)) { - const merger = MERGER[key]; - stats.hooks.merge.for(key).tap("DefaultStatsFactoryPlugin", merger); - } - if (options.children) { - if (Array.isArray(options.children)) { - stats.hooks.getItemFactory - .for("compilation.children[].compilation") - .tap("DefaultStatsFactoryPlugin", (comp, { _index: idx }) => { - if (idx < options.children.length) { - return compilation.createStatsFactory( - compilation.createStatsOptions( - options.children[idx], - context - ) - ); - } - }); - } else if (options.children !== true) { - const childFactory = compilation.createStatsFactory( - compilation.createStatsOptions(options.children, context) - ); - stats.hooks.getItemFactory - .for("compilation.children[].compilation") - .tap("DefaultStatsFactoryPlugin", () => { - return childFactory; - }); - } - } - } - ); + needBuild(context, callback) { + callback(null, !this.buildInfo); + } + + /** + * @param {WebpackOptions} options webpack options + * @param {Compilation} compilation the compilation + * @param {ResolverWithOptions} resolver the resolver + * @param {InputFileSystem} fs the file system + * @param {function(WebpackError=): void} callback callback function + * @returns {void} + */ + build(options, compilation, resolver, fs, callback) { + this.buildMeta = {}; + this.buildInfo = { + strict: true + }; + + this.clearDependenciesAndBlocks(); + const dep = new ProvideForSharedDependency(this._request); + if (this._eager) { + this.addDependency(dep); + } else { + const block = new AsyncDependenciesBlock({}); + block.addDependency(dep); + this.addBlock(block); + } + + callback(); + } + + /** + * @param {string=} type the source type for which the size should be estimated + * @returns {number} the estimated size of the module (must be non-zero) + */ + size(type) { + return 42; + } + + /** + * @returns {Set} types available (do not mutate) + */ + getSourceTypes() { + return TYPES; + } + + /** + * @param {CodeGenerationContext} context context for code generation + * @returns {CodeGenerationResult} result + */ + codeGeneration({ runtimeTemplate, moduleGraph, chunkGraph }) { + const runtimeRequirements = new Set([RuntimeGlobals.initializeSharing]); + const code = `register(${JSON.stringify(this._name)}, ${JSON.stringify( + this._version || "0" + )}, ${ + this._eager + ? runtimeTemplate.syncModuleFactory({ + dependency: this.dependencies[0], + chunkGraph, + request: this._request, + runtimeRequirements + }) + : runtimeTemplate.asyncModuleFactory({ + block: this.blocks[0], + chunkGraph, + request: this._request, + runtimeRequirements + }) + }${this._eager ? ", 1" : ""});`; + const sources = new Map(); + const data = new Map(); + data.set("share-init", [ + { + shareScope: this._shareScope, + initStage: 10, + init: code + } + ]); + return { sources, data, runtimeRequirements }; + } + + serialize(context) { + const { write } = context; + write(this._shareScope); + write(this._name); + write(this._version); + write(this._request); + write(this._eager); + super.serialize(context); + } + + static deserialize(context) { + const { read } = context; + const obj = new ProvideSharedModule(read(), read(), read(), read(), read()); + obj.deserialize(context); + return obj; + } +} + +makeSerializable( + ProvideSharedModule, + "webpack/lib/sharing/ProvideSharedModule" +); + +module.exports = ProvideSharedModule; + + +/***/ }), + +/***/ 89859: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra and Zackary Jackson @ScriptedAlchemy +*/ + + + +const ModuleFactory = __webpack_require__(61574); +const ProvideSharedModule = __webpack_require__(65945); + +/** @typedef {import("../ModuleFactory").ModuleFactoryCreateData} ModuleFactoryCreateData */ +/** @typedef {import("../ModuleFactory").ModuleFactoryResult} ModuleFactoryResult */ +/** @typedef {import("./ProvideSharedDependency")} ProvideSharedDependency */ + +class ProvideSharedModuleFactory extends ModuleFactory { + /** + * @param {ModuleFactoryCreateData} data data object + * @param {function(Error=, ModuleFactoryResult=): void} callback callback + * @returns {void} + */ + create(data, callback) { + const dep = /** @type {ProvideSharedDependency} */ (data.dependencies[0]); + callback(null, { + module: new ProvideSharedModule( + dep.shareScope, + dep.name, + dep.version, + dep.request, + dep.eager + ) }); } } -module.exports = DefaultStatsFactoryPlugin; + +module.exports = ProvideSharedModuleFactory; /***/ }), -/***/ 2130: +/***/ 42672: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; /* MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra + Author Tobias Koppers @sokra and Zackary Jackson @ScriptedAlchemy */ -const RequestShortener = __webpack_require__(43157); +const WebpackError = __webpack_require__(68422); +const { parseOptions } = __webpack_require__(56084); +const createSchemaValidation = __webpack_require__(77695); +const ProvideForSharedDependency = __webpack_require__(40235); +const ProvideSharedDependency = __webpack_require__(99355); +const ProvideSharedModuleFactory = __webpack_require__(89859); -/** @typedef {import("../../declarations/WebpackOptions").StatsOptions} StatsOptions */ +/** @typedef {import("../../declarations/plugins/sharing/ProvideSharedPlugin").ProvideSharedPluginOptions} ProvideSharedPluginOptions */ /** @typedef {import("../Compilation")} Compilation */ -/** @typedef {import("../Compilation").CreateStatsOptionsContext} CreateStatsOptionsContext */ /** @typedef {import("../Compiler")} Compiler */ -const applyDefaults = (options, defaults) => { - for (const key of Object.keys(defaults)) { - if (typeof options[key] === "undefined") { - options[key] = defaults[key]; - } +const validate = createSchemaValidation( + __webpack_require__(31011), + () => __webpack_require__(12287), + { + name: "Provide Shared Plugin", + baseDataPath: "options" } -}; +); -const NAMED_PRESETS = { - verbose: { - hash: true, - builtAt: true, - relatedAssets: true, - entrypoints: true, - chunkGroups: true, - ids: true, - modules: false, - chunks: true, - chunkRelations: true, - chunkModules: true, - dependentModules: true, - chunkOrigins: true, - depth: true, - env: true, - reasons: true, - usedExports: true, - providedExports: true, - optimizationBailout: true, - errorDetails: true, - errorStack: true, - publicPath: true, - logging: "verbose", - orphanModules: true, - runtimeModules: true, - exclude: false, - modulesSpace: Infinity, - chunkModulesSpace: Infinity, - assetsSpace: Infinity, - reasonsSpace: Infinity, - children: true - }, - detailed: { - hash: true, - builtAt: true, - relatedAssets: true, - entrypoints: true, - chunkGroups: true, - ids: true, - chunks: true, - chunkRelations: true, - chunkModules: false, - chunkOrigins: true, - depth: true, - usedExports: true, - providedExports: true, - optimizationBailout: true, - errorDetails: true, - publicPath: true, - logging: true, - runtimeModules: true, - exclude: false, - modulesSpace: 1000, - assetsSpace: 1000, - reasonsSpace: 1000 - }, - minimal: { - all: false, - version: true, - timings: true, - modules: true, - modulesSpace: 0, - assets: true, - assetsSpace: 0, - errors: true, - errorsCount: true, - warnings: true, - warningsCount: true, - logging: "warn" - }, - "errors-only": { - all: false, - errors: true, - errorsCount: true, - moduleTrace: true, - logging: "error" - }, - "errors-warnings": { - all: false, - errors: true, - errorsCount: true, - warnings: true, - warningsCount: true, - logging: "warn" - }, - summary: { - all: false, - version: true, - errorsCount: true, - warningsCount: true - }, - none: { - all: false - } -}; +/** + * @typedef {Object} ProvideOptions + * @property {string} shareKey + * @property {string} shareScope + * @property {string | undefined | false} version + * @property {boolean} eager + */ -const NORMAL_ON = ({ all }) => all !== false; -const NORMAL_OFF = ({ all }) => all === true; -const ON_FOR_TO_STRING = ({ all }, { forToString }) => - forToString ? all !== false : all === true; -const OFF_FOR_TO_STRING = ({ all }, { forToString }) => - forToString ? all === true : all !== false; -const AUTO_FOR_TO_STRING = ({ all }, { forToString }) => { - if (all === false) return false; - if (all === true) return true; - if (forToString) return "auto"; - return true; -}; +/** @typedef {Map} ResolvedProvideMap */ -/** @type {Record any>} */ -const DEFAULTS = { - context: (options, context, compilation) => compilation.compiler.context, - requestShortener: (options, context, compilation) => - compilation.compiler.context === options.context - ? compilation.requestShortener - : new RequestShortener(options.context, compilation.compiler.root), - performance: NORMAL_ON, - hash: OFF_FOR_TO_STRING, - env: NORMAL_OFF, - version: NORMAL_ON, - timings: NORMAL_ON, - builtAt: OFF_FOR_TO_STRING, - assets: NORMAL_ON, - entrypoints: AUTO_FOR_TO_STRING, - chunkGroups: OFF_FOR_TO_STRING, - chunkGroupAuxiliary: OFF_FOR_TO_STRING, - chunkGroupChildren: OFF_FOR_TO_STRING, - chunkGroupMaxAssets: (o, { forToString }) => (forToString ? 5 : Infinity), - chunks: OFF_FOR_TO_STRING, - chunkRelations: OFF_FOR_TO_STRING, - chunkModules: ({ all, modules }) => { - if (all === false) return false; - if (all === true) return true; - if (modules) return false; - return true; - }, - dependentModules: OFF_FOR_TO_STRING, - chunkOrigins: OFF_FOR_TO_STRING, - ids: OFF_FOR_TO_STRING, - modules: ({ all, chunks, chunkModules }, { forToString }) => { - if (all === false) return false; - if (all === true) return true; - if (forToString && chunks && chunkModules) return false; - return true; - }, - nestedModules: OFF_FOR_TO_STRING, - groupModulesByType: ON_FOR_TO_STRING, - groupModulesByCacheStatus: ON_FOR_TO_STRING, - groupModulesByLayer: ON_FOR_TO_STRING, - groupModulesByAttributes: ON_FOR_TO_STRING, - groupModulesByPath: ON_FOR_TO_STRING, - groupModulesByExtension: ON_FOR_TO_STRING, - modulesSpace: (o, { forToString }) => (forToString ? 15 : Infinity), - chunkModulesSpace: (o, { forToString }) => (forToString ? 10 : Infinity), - nestedModulesSpace: (o, { forToString }) => (forToString ? 10 : Infinity), - relatedAssets: OFF_FOR_TO_STRING, - groupAssetsByEmitStatus: ON_FOR_TO_STRING, - groupAssetsByInfo: ON_FOR_TO_STRING, - groupAssetsByPath: ON_FOR_TO_STRING, - groupAssetsByExtension: ON_FOR_TO_STRING, - groupAssetsByChunk: ON_FOR_TO_STRING, - assetsSpace: (o, { forToString }) => (forToString ? 15 : Infinity), - orphanModules: OFF_FOR_TO_STRING, - runtimeModules: ({ all, runtime }, { forToString }) => - runtime !== undefined - ? runtime - : forToString - ? all === true - : all !== false, - cachedModules: ({ all, cached }, { forToString }) => - cached !== undefined ? cached : forToString ? all === true : all !== false, - moduleAssets: OFF_FOR_TO_STRING, - depth: OFF_FOR_TO_STRING, - cachedAssets: OFF_FOR_TO_STRING, - reasons: OFF_FOR_TO_STRING, - reasonsSpace: (o, { forToString }) => (forToString ? 15 : Infinity), - groupReasonsByOrigin: ON_FOR_TO_STRING, - usedExports: OFF_FOR_TO_STRING, - providedExports: OFF_FOR_TO_STRING, - optimizationBailout: OFF_FOR_TO_STRING, - children: OFF_FOR_TO_STRING, - source: NORMAL_OFF, - moduleTrace: NORMAL_ON, - errors: NORMAL_ON, - errorsCount: NORMAL_ON, - errorDetails: AUTO_FOR_TO_STRING, - errorStack: OFF_FOR_TO_STRING, - warnings: NORMAL_ON, - warningsCount: NORMAL_ON, - publicPath: OFF_FOR_TO_STRING, - logging: ({ all }, { forToString }) => - forToString && all !== false ? "info" : false, - loggingDebug: () => [], - loggingTrace: OFF_FOR_TO_STRING, - excludeModules: () => [], - excludeAssets: () => [], - modulesSort: () => "depth", - chunkModulesSort: () => "name", - nestedModulesSort: () => false, - chunksSort: () => false, - assetsSort: () => "!size", - outputPath: OFF_FOR_TO_STRING, - colors: () => false -}; +class ProvideSharedPlugin { + /** + * @param {ProvideSharedPluginOptions} options options + */ + constructor(options) { + validate(options); -const normalizeFilter = item => { - if (typeof item === "string") { - const regExp = new RegExp( - `[\\\\/]${item.replace( - // eslint-disable-next-line no-useless-escape - /[-[\]{}()*+?.\\^$|]/g, - "\\$&" - )}([\\\\/]|$|!|\\?)` + /** @type {[string, ProvideOptions][]} */ + this._provides = parseOptions( + options.provides, + item => { + if (Array.isArray(item)) + throw new Error("Unexpected array of provides"); + /** @type {ProvideOptions} */ + const result = { + shareKey: item, + version: undefined, + shareScope: options.shareScope || "default", + eager: false + }; + return result; + }, + item => ({ + shareKey: item.shareKey, + version: item.version, + shareScope: item.shareScope || options.shareScope || "default", + eager: !!item.eager + }) ); - return ident => regExp.test(ident); - } - if (item && typeof item === "object" && typeof item.test === "function") { - return ident => item.test(ident); - } - if (typeof item === "function") { - return item; - } - if (typeof item === "boolean") { - return () => item; + this._provides.sort(([a], [b]) => { + if (a < b) return -1; + if (b < a) return 1; + return 0; + }); } -}; -const NORMALIZER = { - excludeModules: value => { - if (!Array.isArray(value)) { - value = value ? [value] : []; - } - return value.map(normalizeFilter); - }, - excludeAssets: value => { - if (!Array.isArray(value)) { - value = value ? [value] : []; - } - return value.map(normalizeFilter); - }, - warningsFilter: value => { - if (!Array.isArray(value)) { - value = value ? [value] : []; - } - return value.map(filter => { - if (typeof filter === "string") { - return (warning, warningString) => warningString.includes(filter); + /** + * Apply the plugin + * @param {Compiler} compiler the compiler instance + * @returns {void} + */ + apply(compiler) { + /** @type {WeakMap} */ + const compilationData = new WeakMap(); + + compiler.hooks.compilation.tap( + "ProvideSharedPlugin", + (compilation, { normalModuleFactory }) => { + /** @type {ResolvedProvideMap} */ + const resolvedProvideMap = new Map(); + /** @type {Map} */ + const matchProvides = new Map(); + /** @type {Map} */ + const prefixMatchProvides = new Map(); + for (const [request, config] of this._provides) { + if (/^(\/|[A-Za-z]:\\|\\\\|\.\.?(\/|$))/.test(request)) { + // relative request + resolvedProvideMap.set(request, { + config, + version: config.version + }); + } else if (/^(\/|[A-Za-z]:\\|\\\\)/.test(request)) { + // absolute path + resolvedProvideMap.set(request, { + config, + version: config.version + }); + } else if (request.endsWith("/")) { + // module request prefix + prefixMatchProvides.set(request, config); + } else { + // module request + matchProvides.set(request, config); + } + } + compilationData.set(compilation, resolvedProvideMap); + const provideSharedModule = ( + key, + config, + resource, + resourceResolveData + ) => { + let version = config.version; + if (version === undefined) { + let details = ""; + if (!resourceResolveData) { + details = `No resolve data provided from resolver.`; + } else { + const descriptionFileData = + resourceResolveData.descriptionFileData; + if (!descriptionFileData) { + details = + "No description file (usually package.json) found. Add description file with name and version, or manually specify version in shared config."; + } else if (!descriptionFileData.version) { + details = + "No version in description file (usually package.json). Add version to description file, or manually specify version in shared config."; + } else { + version = descriptionFileData.version; + } + } + if (!version) { + const error = new WebpackError( + `No version specified and unable to automatically determine one. ${details}` + ); + error.file = `shared module ${key} -> ${resource}`; + compilation.warnings.push(error); + } + } + resolvedProvideMap.set(resource, { + config, + version + }); + }; + normalModuleFactory.hooks.module.tap( + "ProvideSharedPlugin", + (module, { resource, resourceResolveData }, resolveData) => { + if (resolvedProvideMap.has(resource)) { + return module; + } + const { request } = resolveData; + { + const config = matchProvides.get(request); + if (config !== undefined) { + provideSharedModule( + request, + config, + resource, + resourceResolveData + ); + resolveData.cacheable = false; + } + } + for (const [prefix, config] of prefixMatchProvides) { + if (request.startsWith(prefix)) { + const remainder = request.slice(prefix.length); + provideSharedModule( + resource, + { + ...config, + shareKey: config.shareKey + remainder + }, + resource, + resourceResolveData + ); + resolveData.cacheable = false; + } + } + return module; + } + ); } - if (filter instanceof RegExp) { - return (warning, warningString) => filter.test(warningString); + ); + compiler.hooks.finishMake.tapPromise("ProvideSharedPlugin", compilation => { + const resolvedProvideMap = compilationData.get(compilation); + if (!resolvedProvideMap) return Promise.resolve(); + return Promise.all( + Array.from( + resolvedProvideMap, + ([resource, { config, version }]) => + new Promise((resolve, reject) => { + compilation.addInclude( + compiler.context, + new ProvideSharedDependency( + config.shareScope, + config.shareKey, + version || false, + resource, + config.eager + ), + { + name: undefined + }, + err => { + if (err) return reject(err); + resolve(); + } + ); + }) + ) + ).then(() => {}); + }); + + compiler.hooks.compilation.tap( + "ProvideSharedPlugin", + (compilation, { normalModuleFactory }) => { + compilation.dependencyFactories.set( + ProvideForSharedDependency, + normalModuleFactory + ); + + compilation.dependencyFactories.set( + ProvideSharedDependency, + new ProvideSharedModuleFactory() + ); } - if (typeof filter === "function") { - return filter; + ); + } +} + +module.exports = ProvideSharedPlugin; + + +/***/ }), + +/***/ 25790: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra and Zackary Jackson @ScriptedAlchemy +*/ + + + +const { parseOptions } = __webpack_require__(56084); +const ConsumeSharedPlugin = __webpack_require__(19984); +const ProvideSharedPlugin = __webpack_require__(42672); +const { isRequiredVersion } = __webpack_require__(58854); + +/** @typedef {import("../../declarations/plugins/sharing/ConsumeSharedPlugin").ConsumeSharedPluginOptions} ConsumeSharedPluginOptions */ +/** @typedef {import("../../declarations/plugins/sharing/ConsumeSharedPlugin").ConsumesConfig} ConsumesConfig */ +/** @typedef {import("../../declarations/plugins/sharing/ProvideSharedPlugin").ProvideSharedPluginOptions} ProvideSharedPluginOptions */ +/** @typedef {import("../../declarations/plugins/sharing/ProvideSharedPlugin").ProvidesConfig} ProvidesConfig */ +/** @typedef {import("../../declarations/plugins/sharing/SharePlugin").SharePluginOptions} SharePluginOptions */ +/** @typedef {import("../../declarations/plugins/sharing/SharePlugin").SharedConfig} SharedConfig */ +/** @typedef {import("../Compiler")} Compiler */ + +class SharePlugin { + /** + * @param {SharePluginOptions} options options + */ + constructor(options) { + /** @type {[string, SharedConfig][]} */ + const sharedOptions = parseOptions( + options.shared, + (item, key) => { + if (typeof item !== "string") + throw new Error("Unexpected array in shared"); + /** @type {SharedConfig} */ + const config = + item === key || !isRequiredVersion(item) + ? { + import: item + } + : { + import: key, + requiredVersion: item + }; + return config; + }, + item => item + ); + /** @type {Record[]} */ + const consumes = sharedOptions.map(([key, options]) => ({ + [key]: { + import: options.import, + shareKey: options.shareKey || key, + shareScope: options.shareScope, + requiredVersion: options.requiredVersion, + strictVersion: options.strictVersion, + singleton: options.singleton, + packageName: options.packageName, + eager: options.eager } - throw new Error( - `Can only filter warnings with Strings or RegExps. (Given: ${filter})` - ); - }); - }, - logging: value => { - if (value === true) value = "log"; - return value; - }, - loggingDebug: value => { - if (!Array.isArray(value)) { - value = value ? [value] : []; - } - return value.map(normalizeFilter); + })); + /** @type {Record[]} */ + const provides = sharedOptions + .filter(([, options]) => options.import !== false) + .map(([key, options]) => ({ + [options.import || key]: { + shareKey: options.shareKey || key, + shareScope: options.shareScope, + version: options.version, + eager: options.eager + } + })); + this._shareScope = options.shareScope; + this._consumes = consumes; + this._provides = provides; } -}; -class DefaultStatsPresetPlugin { /** * Apply the plugin * @param {Compiler} compiler the compiler instance * @returns {void} */ apply(compiler) { - compiler.hooks.compilation.tap("DefaultStatsPresetPlugin", compilation => { - for (const key of Object.keys(NAMED_PRESETS)) { - const defaults = NAMED_PRESETS[key]; - compilation.hooks.statsPreset - .for(key) - .tap("DefaultStatsPresetPlugin", (options, context) => { - applyDefaults(options, defaults); - }); - } - compilation.hooks.statsNormalize.tap( - "DefaultStatsPresetPlugin", - (options, context) => { - for (const key of Object.keys(DEFAULTS)) { - if (options[key] === undefined) - options[key] = DEFAULTS[key](options, context, compilation); - } - for (const key of Object.keys(NORMALIZER)) { - options[key] = NORMALIZER[key](options[key]); - } - } - ); - }); + new ConsumeSharedPlugin({ + shareScope: this._shareScope, + consumes: this._consumes + }).apply(compiler); + new ProvideSharedPlugin({ + shareScope: this._shareScope, + provides: this._provides + }).apply(compiler); } } -module.exports = DefaultStatsPresetPlugin; + +module.exports = SharePlugin; /***/ }), -/***/ 78303: +/***/ 97207: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; @@ -120445,2755 +119252,2703 @@ module.exports = DefaultStatsPresetPlugin; -/** @typedef {import("../Compiler")} Compiler */ -/** @typedef {import("./StatsPrinter")} StatsPrinter */ -/** @typedef {import("./StatsPrinter").StatsPrinterContext} StatsPrinterContext */ +const RuntimeGlobals = __webpack_require__(49404); +const RuntimeModule = __webpack_require__(61439); +const Template = __webpack_require__(92066); +const { + compareModulesByIdentifier, + compareStrings +} = __webpack_require__(26296); -const plural = (n, singular, plural) => (n === 1 ? singular : plural); +class ShareRuntimeModule extends RuntimeModule { + constructor() { + super("sharing"); + } -/** - * @param {Record} sizes sizes by source type - * @param {Object} options options - * @param {(number) => string=} options.formatSize size formatter - * @returns {string} text - */ -const printSizes = (sizes, { formatSize = n => `${n}` }) => { - const keys = Object.keys(sizes); - if (keys.length > 1) { - return keys.map(key => `${formatSize(sizes[key])} (${key})`).join(" "); - } else if (keys.length === 1) { - return formatSize(sizes[keys[0]]); + /** + * @returns {string} runtime code + */ + generate() { + const { compilation, chunkGraph } = this; + const { + runtimeTemplate, + codeGenerationResults, + outputOptions: { uniqueName } + } = compilation; + /** @type {Map>>} */ + const initCodePerScope = new Map(); + for (const chunk of this.chunk.getAllReferencedChunks()) { + const modules = chunkGraph.getOrderedChunkModulesIterableBySourceType( + chunk, + "share-init", + compareModulesByIdentifier + ); + if (!modules) continue; + for (const m of modules) { + const data = codeGenerationResults.getData( + m, + chunk.runtime, + "share-init" + ); + if (!data) continue; + for (const item of data) { + const { shareScope, initStage, init } = item; + let stages = initCodePerScope.get(shareScope); + if (stages === undefined) { + initCodePerScope.set(shareScope, (stages = new Map())); + } + let list = stages.get(initStage || 0); + if (list === undefined) { + stages.set(initStage || 0, (list = new Set())); + } + list.add(init); + } + } + } + return Template.asString([ + `${RuntimeGlobals.shareScopeMap} = {};`, + "var initPromises = {};", + "var initTokens = {};", + `${RuntimeGlobals.initializeSharing} = ${runtimeTemplate.basicFunction( + "name, initScope", + [ + "if(!initScope) initScope = [];", + "// handling circular init calls", + "var initToken = initTokens[name];", + "if(!initToken) initToken = initTokens[name] = {};", + "if(initScope.indexOf(initToken) >= 0) return;", + "initScope.push(initToken);", + "// only runs once", + "if(initPromises[name]) return initPromises[name];", + "// creates a new share scope if needed", + `if(!${RuntimeGlobals.hasOwnProperty}(${RuntimeGlobals.shareScopeMap}, name)) ${RuntimeGlobals.shareScopeMap}[name] = {};`, + "// runs all init snippets from all modules reachable", + `var scope = ${RuntimeGlobals.shareScopeMap}[name];`, + `var warn = ${runtimeTemplate.returningFunction( + 'typeof console !== "undefined" && console.warn && console.warn(msg)', + "msg" + )};`, + `var uniqueName = ${JSON.stringify(uniqueName || undefined)};`, + `var register = ${runtimeTemplate.basicFunction( + "name, version, factory, eager", + [ + "var versions = scope[name] = scope[name] || {};", + "var activeVersion = versions[version];", + "if(!activeVersion || (!activeVersion.loaded && (!eager != !activeVersion.eager ? eager : uniqueName > activeVersion.from))) versions[version] = { get: factory, from: uniqueName, eager: !!eager };" + ] + )};`, + `var initExternal = ${runtimeTemplate.basicFunction("id", [ + `var handleError = ${runtimeTemplate.expressionFunction( + 'warn("Initialization of sharing external failed: " + err)', + "err" + )};`, + "try {", + Template.indent([ + "var module = __webpack_require__(id);", + "if(!module) return;", + `var initFn = ${runtimeTemplate.returningFunction( + `module && module.init && module.init(${RuntimeGlobals.shareScopeMap}[name], initScope)`, + "module" + )}`, + "if(module.then) return promises.push(module.then(initFn, handleError));", + "var initResult = initFn(module);", + "if(initResult && initResult.then) return promises.push(initResult['catch'](handleError));" + ]), + "} catch(err) { handleError(err); }" + ])}`, + "var promises = [];", + "switch(name) {", + ...Array.from(initCodePerScope) + .sort(([a], [b]) => compareStrings(a, b)) + .map(([name, stages]) => + Template.indent([ + `case ${JSON.stringify(name)}: {`, + Template.indent( + Array.from(stages) + .sort(([a], [b]) => a - b) + .map(([, initCode]) => + Template.asString(Array.from(initCode)) + ) + ), + "}", + "break;" + ]) + ), + "}", + "if(!promises.length) return initPromises[name] = 1;", + `return initPromises[name] = Promise.all(promises).then(${runtimeTemplate.returningFunction( + "initPromises[name] = 1" + )});` + ] + )};` + ]); } -}; +} -const mapLines = (str, fn) => str.split("\n").map(fn).join("\n"); +module.exports = ShareRuntimeModule; + + +/***/ }), + +/***/ 18436: +/***/ (function(__unused_webpack_module, exports, __webpack_require__) { + +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ + + + +const ModuleNotFoundError = __webpack_require__(82908); +const LazySet = __webpack_require__(59534); + +/** @typedef {import("../Compilation")} Compilation */ +/** @typedef {import("../ResolverFactory").ResolveOptionsWithDependencyType} ResolveOptionsWithDependencyType */ /** - * @param {number} n a number - * @returns {string} number as two digit string, leading 0 + * @template T + * @typedef {Object} MatchedConfigs + * @property {Map} resolved + * @property {Map} unresolved + * @property {Map} prefixed */ -const twoDigit = n => (n >= 10 ? `${n}` : `0${n}`); - -const isValidId = id => { - return typeof id === "number" || id; -}; -/** @type {Record string | void>} */ -const SIMPLE_PRINTERS = { - "compilation.summary!": ( - _, - { - type, - bold, - green, - red, - yellow, - formatDateTime, - formatTime, - compilation: { - name, - hash, - version, - time, - builtAt, - errorsCount, - warningsCount - } - } - ) => { - const root = type === "compilation.summary!"; - const warningsMessage = - warningsCount > 0 - ? yellow( - `${warningsCount} ${plural(warningsCount, "warning", "warnings")}` - ) - : ""; - const errorsMessage = - errorsCount > 0 - ? red(`${errorsCount} ${plural(errorsCount, "error", "errors")}`) - : ""; - const timeMessage = root && time ? ` in ${formatTime(time)}` : ""; - const hashMessage = hash ? ` (${hash})` : ""; - const builtAtMessage = - root && builtAt ? `${formatDateTime(builtAt)}: ` : ""; - const versionMessage = root && version ? `webpack ${version}` : ""; - const nameMessage = - root && name - ? bold(name) - : name - ? `Child ${bold(name)}` - : root - ? "" - : "Child"; - const subjectMessage = - nameMessage && versionMessage - ? `${nameMessage} (${versionMessage})` - : versionMessage || nameMessage || "webpack"; - let statusMessage; - if (errorsMessage && warningsMessage) { - statusMessage = `compiled with ${errorsMessage} and ${warningsMessage}`; - } else if (errorsMessage) { - statusMessage = `compiled with ${errorsMessage}`; - } else if (warningsMessage) { - statusMessage = `compiled with ${warningsMessage}`; - } else if (errorsCount === 0 && warningsCount === 0) { - statusMessage = `compiled ${green("successfully")}`; - } else { - statusMessage = `compiled`; - } - if ( - builtAtMessage || - versionMessage || - errorsMessage || - warningsMessage || - (errorsCount === 0 && warningsCount === 0) || - timeMessage || - hashMessage - ) - return `${builtAtMessage}${subjectMessage} ${statusMessage}${timeMessage}${hashMessage}`; - }, - "compilation.filteredWarningDetailsCount": count => - count - ? `${count} ${plural( - count, - "warning has", - "warnings have" - )} detailed information that is not shown.\nUse 'stats.errorDetails: true' resp. '--stats-error-details' to show it.` - : undefined, - "compilation.filteredErrorDetailsCount": (count, { yellow }) => - count - ? yellow( - `${count} ${plural( - count, - "error has", - "errors have" - )} detailed information that is not shown.\nUse 'stats.errorDetails: true' resp. '--stats-error-details' to show it.` - ) - : undefined, - "compilation.env": (env, { bold }) => - env - ? `Environment (--env): ${bold(JSON.stringify(env, null, 2))}` - : undefined, - "compilation.publicPath": (publicPath, { bold }) => - `PublicPath: ${bold(publicPath || "(none)")}`, - "compilation.entrypoints": (entrypoints, context, printer) => - Array.isArray(entrypoints) - ? undefined - : printer.print(context.type, Object.values(entrypoints), { - ...context, - chunkGroupKind: "Entrypoint" - }), - "compilation.namedChunkGroups": (namedChunkGroups, context, printer) => { - if (!Array.isArray(namedChunkGroups)) { - const { - compilation: { entrypoints } - } = context; - let chunkGroups = Object.values(namedChunkGroups); - if (entrypoints) { - chunkGroups = chunkGroups.filter( - group => - !Object.prototype.hasOwnProperty.call(entrypoints, group.name) - ); - } - return printer.print(context.type, chunkGroups, { - ...context, - chunkGroupKind: "Chunk Group" - }); - } - }, - "compilation.assetsByChunkName": () => "", +/** @type {ResolveOptionsWithDependencyType} */ +const RESOLVE_OPTIONS = { dependencyType: "esm" }; - "compilation.filteredModules": filteredModules => - filteredModules > 0 - ? `${filteredModules} ${plural(filteredModules, "module", "modules")}` - : undefined, - "compilation.filteredAssets": (filteredAssets, { compilation: { assets } }) => - filteredAssets > 0 - ? `${filteredAssets} ${plural(filteredAssets, "asset", "assets")}` - : undefined, - "compilation.logging": (logging, context, printer) => - Array.isArray(logging) - ? undefined - : printer.print( - context.type, - Object.entries(logging).map(([name, value]) => ({ ...value, name })), - context - ), - "compilation.warningsInChildren!": (_, { yellow, compilation }) => { - if ( - !compilation.children && - compilation.warningsCount > 0 && - compilation.warnings - ) { - const childWarnings = - compilation.warningsCount - compilation.warnings.length; - if (childWarnings > 0) { - return yellow( - `${childWarnings} ${plural( - childWarnings, - "WARNING", - "WARNINGS" - )} in child compilations${ - compilation.children - ? "" - : " (Use 'stats.children: true' resp. '--stats-children' for more details)" - }` - ); - } - } - }, - "compilation.errorsInChildren!": (_, { red, compilation }) => { - if ( - !compilation.children && - compilation.errorsCount > 0 && - compilation.errors - ) { - const childErrors = compilation.errorsCount - compilation.errors.length; - if (childErrors > 0) { - return red( - `${childErrors} ${plural( - childErrors, - "ERROR", - "ERRORS" - )} in child compilations${ - compilation.children - ? "" - : " (Use 'stats.children: true' resp. '--stats-children' for more details)" - }` - ); +/** + * @template T + * @param {Compilation} compilation the compilation + * @param {[string, T][]} configs to be processed configs + * @returns {Promise>} resolved matchers + */ +exports.resolveMatchedConfigs = (compilation, configs) => { + /** @type {Map} */ + const resolved = new Map(); + /** @type {Map} */ + const unresolved = new Map(); + /** @type {Map} */ + const prefixed = new Map(); + const resolveContext = { + /** @type {LazySet} */ + fileDependencies: new LazySet(), + /** @type {LazySet} */ + contextDependencies: new LazySet(), + /** @type {LazySet} */ + missingDependencies: new LazySet() + }; + const resolver = compilation.resolverFactory.get("normal", RESOLVE_OPTIONS); + const context = compilation.compiler.context; + + return Promise.all( + configs.map(([request, config]) => { + if (/^\.\.?(\/|$)/.test(request)) { + // relative request + return new Promise(resolve => { + resolver.resolve( + {}, + context, + request, + resolveContext, + (err, result) => { + if (err || result === false) { + err = err || new Error(`Can't resolve ${request}`); + compilation.errors.push( + new ModuleNotFoundError(null, err, { + name: `shared module ${request}` + }) + ); + return resolve(); + } + resolved.set(result, config); + resolve(); + } + ); + }); + } else if (/^(\/|[A-Za-z]:\\|\\\\)/.test(request)) { + // absolute path + resolved.set(request, config); + } else if (request.endsWith("/")) { + // module request prefix + prefixed.set(request, config); + } else { + // module request + unresolved.set(request, config); } - } - }, + }) + ).then(() => { + compilation.contextDependencies.addAll(resolveContext.contextDependencies); + compilation.fileDependencies.addAll(resolveContext.fileDependencies); + compilation.missingDependencies.addAll(resolveContext.missingDependencies); + return { resolved, unresolved, prefixed }; + }); +}; - "asset.type": type => type, - "asset.name": (name, { formatFilename, asset: { isOverSizeLimit } }) => - formatFilename(name, isOverSizeLimit), - "asset.size": ( - size, - { asset: { isOverSizeLimit }, yellow, green, formatSize } - ) => (isOverSizeLimit ? yellow(formatSize(size)) : formatSize(size)), - "asset.emitted": (emitted, { green, formatFlag }) => - emitted ? green(formatFlag("emitted")) : undefined, - "asset.comparedForEmit": (comparedForEmit, { yellow, formatFlag }) => - comparedForEmit ? yellow(formatFlag("compared for emit")) : undefined, - "asset.cached": (cached, { green, formatFlag }) => - cached ? green(formatFlag("cached")) : undefined, - "asset.isOverSizeLimit": (isOverSizeLimit, { yellow, formatFlag }) => - isOverSizeLimit ? yellow(formatFlag("big")) : undefined, - "asset.info.immutable": (immutable, { green, formatFlag }) => - immutable ? green(formatFlag("immutable")) : undefined, - "asset.info.javascriptModule": (javascriptModule, { formatFlag }) => - javascriptModule ? formatFlag("javascript module") : undefined, - "asset.info.sourceFilename": (sourceFilename, { formatFlag }) => - sourceFilename - ? formatFlag( - sourceFilename === true - ? "from source file" - : `from: ${sourceFilename}` - ) - : undefined, - "asset.info.development": (development, { green, formatFlag }) => - development ? green(formatFlag("dev")) : undefined, - "asset.info.hotModuleReplacement": ( - hotModuleReplacement, - { green, formatFlag } - ) => (hotModuleReplacement ? green(formatFlag("hmr")) : undefined), - "asset.separator!": () => "\n", - "asset.filteredRelated": (filteredRelated, { asset: { related } }) => - filteredRelated > 0 - ? `${filteredRelated} related ${plural( - filteredRelated, - "asset", - "assets" - )}` - : undefined, - "asset.filteredChildren": filteredChildren => - filteredChildren > 0 - ? `${filteredChildren} ${plural(filteredChildren, "asset", "assets")}` - : undefined, +/***/ }), - assetChunk: (id, { formatChunkId }) => formatChunkId(id), +/***/ 58854: +/***/ (function(__unused_webpack_module, exports, __webpack_require__) { - assetChunkName: name => name, - assetChunkIdHint: name => name, +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ - "module.type": type => (type !== "module" ? type : undefined), - "module.id": (id, { formatModuleId }) => - isValidId(id) ? formatModuleId(id) : undefined, - "module.name": (name, { bold }) => { - const [, prefix, resource] = /^(.*!)?([^!]*)$/.exec(name); - return (prefix || "") + bold(resource); - }, - "module.identifier": identifier => undefined, - "module.layer": (layer, { formatLayer }) => - layer ? formatLayer(layer) : undefined, - "module.sizes": printSizes, - "module.chunks[]": (id, { formatChunkId }) => formatChunkId(id), - "module.depth": (depth, { formatFlag }) => - depth !== null ? formatFlag(`depth ${depth}`) : undefined, - "module.cacheable": (cacheable, { formatFlag, red }) => - cacheable === false ? red(formatFlag("not cacheable")) : undefined, - "module.orphan": (orphan, { formatFlag, yellow }) => - orphan ? yellow(formatFlag("orphan")) : undefined, - "module.runtime": (runtime, { formatFlag, yellow }) => - runtime ? yellow(formatFlag("runtime")) : undefined, - "module.optional": (optional, { formatFlag, yellow }) => - optional ? yellow(formatFlag("optional")) : undefined, - "module.dependent": (dependent, { formatFlag, cyan }) => - dependent ? cyan(formatFlag("dependent")) : undefined, - "module.built": (built, { formatFlag, yellow }) => - built ? yellow(formatFlag("built")) : undefined, - "module.codeGenerated": (codeGenerated, { formatFlag, yellow }) => - codeGenerated ? yellow(formatFlag("code generated")) : undefined, - "module.buildTimeExecuted": (buildTimeExecuted, { formatFlag, green }) => - buildTimeExecuted ? green(formatFlag("build time executed")) : undefined, - "module.cached": (cached, { formatFlag, green }) => - cached ? green(formatFlag("cached")) : undefined, - "module.assets": (assets, { formatFlag, magenta }) => - assets && assets.length - ? magenta( - formatFlag( - `${assets.length} ${plural(assets.length, "asset", "assets")}` - ) - ) - : undefined, - "module.warnings": (warnings, { formatFlag, yellow }) => - warnings === true - ? yellow(formatFlag("warnings")) - : warnings - ? yellow( - formatFlag(`${warnings} ${plural(warnings, "warning", "warnings")}`) - ) - : undefined, - "module.errors": (errors, { formatFlag, red }) => - errors === true - ? red(formatFlag("errors")) - : errors - ? red(formatFlag(`${errors} ${plural(errors, "error", "errors")}`)) - : undefined, - "module.providedExports": (providedExports, { formatFlag, cyan }) => { - if (Array.isArray(providedExports)) { - if (providedExports.length === 0) return cyan(formatFlag("no exports")); - return cyan(formatFlag(`exports: ${providedExports.join(", ")}`)); + + +const { join, dirname, readJson } = __webpack_require__(93204); + +/** @typedef {import("../util/fs").InputFileSystem} InputFileSystem */ + +/** + * @param {string} str maybe required version + * @returns {boolean} true, if it looks like a version + */ +exports.isRequiredVersion = str => { + return /^([\d^=v<>~]|[*xX]$)/.test(str); +}; + +/** + * + * @param {InputFileSystem} fs file system + * @param {string} directory directory to start looking into + * @param {string[]} descriptionFiles possible description filenames + * @param {function(Error=, {data: object, path: string}=): void} callback callback + */ +const getDescriptionFile = (fs, directory, descriptionFiles, callback) => { + let i = 0; + const tryLoadCurrent = () => { + if (i >= descriptionFiles.length) { + const parentDirectory = dirname(fs, directory); + if (!parentDirectory || parentDirectory === directory) return callback(); + return getDescriptionFile( + fs, + parentDirectory, + descriptionFiles, + callback + ); } - }, - "module.usedExports": (usedExports, { formatFlag, cyan, module }) => { - if (usedExports !== true) { - if (usedExports === null) return cyan(formatFlag("used exports unknown")); - if (usedExports === false) return cyan(formatFlag("module unused")); - if (Array.isArray(usedExports)) { - if (usedExports.length === 0) - return cyan(formatFlag("no exports used")); - const providedExportsCount = Array.isArray(module.providedExports) - ? module.providedExports.length - : null; - if ( - providedExportsCount !== null && - providedExportsCount === usedExports.length - ) { - return cyan(formatFlag("all exports used")); - } else { - return cyan( - formatFlag(`only some exports used: ${usedExports.join(", ")}`) - ); + const filePath = join(fs, directory, descriptionFiles[i]); + readJson(fs, filePath, (err, data) => { + if (err) { + if ("code" in err && err.code === "ENOENT") { + i++; + return tryLoadCurrent(); } + return callback(err); } - } - }, - "module.optimizationBailout[]": (optimizationBailout, { yellow }) => - yellow(optimizationBailout), - "module.issuerPath": (issuerPath, { module }) => - module.profile ? undefined : "", - "module.profile": profile => undefined, - "module.filteredModules": filteredModules => - filteredModules > 0 - ? `${filteredModules} nested ${plural( - filteredModules, - "module", - "modules" - )}` - : undefined, - "module.filteredReasons": filteredReasons => - filteredReasons > 0 - ? `${filteredReasons} ${plural(filteredReasons, "reason", "reasons")}` - : undefined, - "module.filteredChildren": filteredChildren => - filteredChildren > 0 - ? `${filteredChildren} ${plural(filteredChildren, "module", "modules")}` - : undefined, - "module.separator!": () => "\n", + if (!data || typeof data !== "object" || Array.isArray(data)) { + return callback( + new Error(`Description file ${filePath} is not an object`) + ); + } + callback(null, { data, path: filePath }); + }); + }; + tryLoadCurrent(); +}; +exports.getDescriptionFile = getDescriptionFile; - "moduleIssuer.id": (id, { formatModuleId }) => formatModuleId(id), - "moduleIssuer.profile.total": (value, { formatTime }) => formatTime(value), +exports.getRequiredVersionFromDescriptionFile = (data, packageName) => { + if ( + data.optionalDependencies && + typeof data.optionalDependencies === "object" && + packageName in data.optionalDependencies + ) { + return data.optionalDependencies[packageName]; + } + if ( + data.dependencies && + typeof data.dependencies === "object" && + packageName in data.dependencies + ) { + return data.dependencies[packageName]; + } + if ( + data.peerDependencies && + typeof data.peerDependencies === "object" && + packageName in data.peerDependencies + ) { + return data.peerDependencies[packageName]; + } + if ( + data.devDependencies && + typeof data.devDependencies === "object" && + packageName in data.devDependencies + ) { + return data.devDependencies[packageName]; + } +}; - "moduleReason.type": type => type, - "moduleReason.userRequest": (userRequest, { cyan }) => cyan(userRequest), - "moduleReason.moduleId": (moduleId, { formatModuleId }) => - isValidId(moduleId) ? formatModuleId(moduleId) : undefined, - "moduleReason.module": (module, { magenta }) => magenta(module), - "moduleReason.loc": loc => loc, - "moduleReason.explanation": (explanation, { cyan }) => cyan(explanation), - "moduleReason.active": (active, { formatFlag }) => - active ? undefined : formatFlag("inactive"), - "moduleReason.resolvedModule": (module, { magenta }) => magenta(module), - "moduleReason.filteredChildren": filteredChildren => - filteredChildren > 0 - ? `${filteredChildren} ${plural(filteredChildren, "reason", "reasons")}` - : undefined, - "module.profile.total": (value, { formatTime }) => formatTime(value), - "module.profile.resolving": (value, { formatTime }) => - `resolving: ${formatTime(value)}`, - "module.profile.restoring": (value, { formatTime }) => - `restoring: ${formatTime(value)}`, - "module.profile.integration": (value, { formatTime }) => - `integration: ${formatTime(value)}`, - "module.profile.building": (value, { formatTime }) => - `building: ${formatTime(value)}`, - "module.profile.storing": (value, { formatTime }) => - `storing: ${formatTime(value)}`, - "module.profile.additionalResolving": (value, { formatTime }) => - value ? `additional resolving: ${formatTime(value)}` : undefined, - "module.profile.additionalIntegration": (value, { formatTime }) => - value ? `additional integration: ${formatTime(value)}` : undefined, +/***/ }), - "chunkGroup.kind!": (_, { chunkGroupKind }) => chunkGroupKind, - "chunkGroup.separator!": () => "\n", - "chunkGroup.name": (name, { bold }) => bold(name), - "chunkGroup.isOverSizeLimit": (isOverSizeLimit, { formatFlag, yellow }) => - isOverSizeLimit ? yellow(formatFlag("big")) : undefined, - "chunkGroup.assetsSize": (size, { formatSize }) => - size ? formatSize(size) : undefined, - "chunkGroup.auxiliaryAssetsSize": (size, { formatSize }) => - size ? `(${formatSize(size)})` : undefined, - "chunkGroup.filteredAssets": n => - n > 0 ? `${n} ${plural(n, "asset", "assets")}` : undefined, - "chunkGroup.filteredAuxiliaryAssets": n => - n > 0 ? `${n} auxiliary ${plural(n, "asset", "assets")}` : undefined, - "chunkGroup.is!": () => "=", - "chunkGroupAsset.name": (asset, { green }) => green(asset), - "chunkGroupAsset.size": (size, { formatSize, chunkGroup }) => - chunkGroup.assets.length > 1 || - (chunkGroup.auxiliaryAssets && chunkGroup.auxiliaryAssets.length > 0) - ? formatSize(size) - : undefined, - "chunkGroup.children": (children, context, printer) => - Array.isArray(children) - ? undefined - : printer.print( - context.type, - Object.keys(children).map(key => ({ - type: key, - children: children[key] - })), - context - ), - "chunkGroupChildGroup.type": type => `${type}:`, - "chunkGroupChild.assets[]": (file, { formatFilename }) => - formatFilename(file), - "chunkGroupChild.chunks[]": (id, { formatChunkId }) => formatChunkId(id), - "chunkGroupChild.name": name => (name ? `(name: ${name})` : undefined), +/***/ 91293: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - "chunk.id": (id, { formatChunkId }) => formatChunkId(id), - "chunk.files[]": (file, { formatFilename }) => formatFilename(file), - "chunk.names[]": name => name, - "chunk.idHints[]": name => name, - "chunk.runtime[]": name => name, - "chunk.sizes": (sizes, context) => printSizes(sizes, context), - "chunk.parents[]": (parents, context) => - context.formatChunkId(parents, "parent"), - "chunk.siblings[]": (siblings, context) => - context.formatChunkId(siblings, "sibling"), - "chunk.children[]": (children, context) => - context.formatChunkId(children, "child"), - "chunk.childrenByOrder": (childrenByOrder, context, printer) => - Array.isArray(childrenByOrder) - ? undefined - : printer.print( - context.type, - Object.keys(childrenByOrder).map(key => ({ - type: key, - children: childrenByOrder[key] - })), - context - ), - "chunk.childrenByOrder[].type": type => `${type}:`, - "chunk.childrenByOrder[].children[]": (id, { formatChunkId }) => - isValidId(id) ? formatChunkId(id) : undefined, - "chunk.entry": (entry, { formatFlag, yellow }) => - entry ? yellow(formatFlag("entry")) : undefined, - "chunk.initial": (initial, { formatFlag, yellow }) => - initial ? yellow(formatFlag("initial")) : undefined, - "chunk.rendered": (rendered, { formatFlag, green }) => - rendered ? green(formatFlag("rendered")) : undefined, - "chunk.recorded": (recorded, { formatFlag, green }) => - recorded ? green(formatFlag("recorded")) : undefined, - "chunk.reason": (reason, { yellow }) => (reason ? yellow(reason) : undefined), - "chunk.filteredModules": filteredModules => - filteredModules > 0 - ? `${filteredModules} chunk ${plural( - filteredModules, - "module", - "modules" - )}` - : undefined, - "chunk.separator!": () => "\n", +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ + + + +const util = __webpack_require__(31669); +const ModuleDependency = __webpack_require__(80944); +const formatLocation = __webpack_require__(57261); +const { LogType } = __webpack_require__(54667); +const AggressiveSplittingPlugin = __webpack_require__(10055); +const SizeLimitsPlugin = __webpack_require__(64025); +const { countIterable } = __webpack_require__(31065); +const { + compareLocations, + compareChunksById, + compareNumbers, + compareIds, + concatComparators, + compareSelect, + compareModulesByIdentifier +} = __webpack_require__(26296); +const { makePathsRelative, parseResource } = __webpack_require__(96236); + +/** @typedef {import("webpack-sources").Source} Source */ +/** @typedef {import("../Chunk")} Chunk */ +/** @typedef {import("../ChunkGroup")} ChunkGroup */ +/** @typedef {import("../ChunkGroup").OriginRecord} OriginRecord */ +/** @typedef {import("../Compilation")} Compilation */ +/** @typedef {import("../Compilation").Asset} Asset */ +/** @typedef {import("../Compilation").AssetInfo} AssetInfo */ +/** @typedef {import("../Compilation").NormalizedStatsOptions} NormalizedStatsOptions */ +/** @typedef {import("../Compiler")} Compiler */ +/** @typedef {import("../Dependency")} Dependency */ +/** @typedef {import("../Dependency").DependencyLocation} DependencyLocation */ +/** @typedef {import("../Module")} Module */ +/** @typedef {import("../ModuleGraphConnection")} ModuleGraphConnection */ +/** @typedef {import("../ModuleProfile")} ModuleProfile */ +/** @typedef {import("../RequestShortener")} RequestShortener */ +/** @typedef {import("../WebpackError")} WebpackError */ +/** @template T @typedef {import("../util/comparators").Comparator} Comparator */ +/** @typedef {import("../util/runtime").RuntimeSpec} RuntimeSpec */ +/** @typedef {import("../util/smartGrouping").GroupConfig} GroupConfig */ +/** @typedef {import("./StatsFactory")} StatsFactory */ +/** @typedef {import("./StatsFactory").StatsFactoryContext} StatsFactoryContext */ + +/** @typedef {KnownStatsCompilation & Record} StatsCompilation */ +/** + * @typedef {Object} KnownStatsCompilation + * @property {any=} env + * @property {string=} name + * @property {string=} hash + * @property {string=} version + * @property {number=} time + * @property {number=} builtAt + * @property {boolean=} needAdditionalPass + * @property {string=} publicPath + * @property {string=} outputPath + * @property {Record=} assetsByChunkName + * @property {StatsAsset[]=} assets + * @property {number=} filteredAssets + * @property {StatsChunk[]=} chunks + * @property {StatsModule[]=} modules + * @property {number=} filteredModules + * @property {Record=} entrypoints + * @property {Record=} namedChunkGroups + * @property {StatsError[]=} errors + * @property {number=} errorsCount + * @property {StatsError[]=} warnings + * @property {number=} warningsCount + * @property {StatsCompilation[]=} children + * @property {Record=} logging + */ + +/** @typedef {KnownStatsLogging & Record} StatsLogging */ +/** + * @typedef {Object} KnownStatsLogging + * @property {StatsLoggingEntry[]} entries + * @property {number} filteredEntries + * @property {boolean} debug + */ + +/** @typedef {KnownStatsLoggingEntry & Record} StatsLoggingEntry */ +/** + * @typedef {Object} KnownStatsLoggingEntry + * @property {string} type + * @property {string} message + * @property {string[]=} trace + * @property {StatsLoggingEntry[]=} children + * @property {any[]=} args + * @property {number=} time + */ - "chunkOrigin.request": request => request, - "chunkOrigin.moduleId": (moduleId, { formatModuleId }) => - isValidId(moduleId) ? formatModuleId(moduleId) : undefined, - "chunkOrigin.moduleName": (moduleName, { bold }) => bold(moduleName), - "chunkOrigin.loc": loc => loc, +/** @typedef {KnownStatsAsset & Record} StatsAsset */ +/** + * @typedef {Object} KnownStatsAsset + * @property {string} type + * @property {string} name + * @property {AssetInfo} info + * @property {number} size + * @property {boolean} emitted + * @property {boolean} comparedForEmit + * @property {boolean} cached + * @property {StatsAsset[]=} related + * @property {(string|number)[]=} chunkNames + * @property {(string|number)[]=} chunkIdHints + * @property {(string|number)[]=} chunks + * @property {(string|number)[]=} auxiliaryChunkNames + * @property {(string|number)[]=} auxiliaryChunks + * @property {(string|number)[]=} auxiliaryChunkIdHints + * @property {number=} filteredRelated + * @property {boolean=} isOverSizeLimit + */ - "error.compilerPath": (compilerPath, { bold }) => - compilerPath ? bold(`(${compilerPath})`) : undefined, - "error.chunkId": (chunkId, { formatChunkId }) => - isValidId(chunkId) ? formatChunkId(chunkId) : undefined, - "error.chunkEntry": (chunkEntry, { formatFlag }) => - chunkEntry ? formatFlag("entry") : undefined, - "error.chunkInitial": (chunkInitial, { formatFlag }) => - chunkInitial ? formatFlag("initial") : undefined, - "error.file": (file, { bold }) => bold(file), - "error.moduleName": (moduleName, { bold }) => { - return moduleName.includes("!") - ? `${bold(moduleName.replace(/^(\s|\S)*!/, ""))} (${moduleName})` - : `${bold(moduleName)}`; - }, - "error.loc": (loc, { green }) => green(loc), - "error.message": (message, { bold, formatError }) => - message.includes("\u001b[") ? message : bold(formatError(message)), - "error.details": (details, { formatError }) => formatError(details), - "error.stack": stack => stack, - "error.moduleTrace": moduleTrace => undefined, - "error.separator!": () => "\n", +/** @typedef {KnownStatsChunkGroup & Record} StatsChunkGroup */ +/** + * @typedef {Object} KnownStatsChunkGroup + * @property {string=} name + * @property {(string|number)[]=} chunks + * @property {({ name: string, size?: number })[]=} assets + * @property {number=} filteredAssets + * @property {number=} assetsSize + * @property {({ name: string, size?: number })[]=} auxiliaryAssets + * @property {number=} filteredAuxiliaryAssets + * @property {number=} auxiliaryAssetsSize + * @property {{ [x: string]: StatsChunkGroup[] }=} children + * @property {{ [x: string]: string[] }=} childAssets + * @property {boolean=} isOverSizeLimit + */ - "loggingEntry(error).loggingEntry.message": (message, { red }) => - mapLines(message, x => ` ${red(x)}`), - "loggingEntry(warn).loggingEntry.message": (message, { yellow }) => - mapLines(message, x => ` ${yellow(x)}`), - "loggingEntry(info).loggingEntry.message": (message, { green }) => - mapLines(message, x => ` ${green(x)}`), - "loggingEntry(log).loggingEntry.message": (message, { bold }) => - mapLines(message, x => ` ${bold(x)}`), - "loggingEntry(debug).loggingEntry.message": message => - mapLines(message, x => ` ${x}`), - "loggingEntry(trace).loggingEntry.message": message => - mapLines(message, x => ` ${x}`), - "loggingEntry(status).loggingEntry.message": (message, { magenta }) => - mapLines(message, x => ` ${magenta(x)}`), - "loggingEntry(profile).loggingEntry.message": (message, { magenta }) => - mapLines(message, x => `

${magenta(x)}`), - "loggingEntry(profileEnd).loggingEntry.message": (message, { magenta }) => - mapLines(message, x => `

${magenta(x)}`), - "loggingEntry(time).loggingEntry.message": (message, { magenta }) => - mapLines(message, x => ` ${magenta(x)}`), - "loggingEntry(group).loggingEntry.message": (message, { cyan }) => - mapLines(message, x => `<-> ${cyan(x)}`), - "loggingEntry(groupCollapsed).loggingEntry.message": (message, { cyan }) => - mapLines(message, x => `<+> ${cyan(x)}`), - "loggingEntry(clear).loggingEntry": () => " -------", - "loggingEntry(groupCollapsed).loggingEntry.children": () => "", - "loggingEntry.trace[]": trace => - trace ? mapLines(trace, x => `| ${x}`) : undefined, +/** @typedef {KnownStatsModule & Record} StatsModule */ +/** + * @typedef {Object} KnownStatsModule + * @property {string=} type + * @property {string=} moduleType + * @property {string=} layer + * @property {string=} identifier + * @property {string=} name + * @property {string=} nameForCondition + * @property {number=} index + * @property {number=} preOrderIndex + * @property {number=} index2 + * @property {number=} postOrderIndex + * @property {number=} size + * @property {{[x: string]: number}=} sizes + * @property {boolean=} cacheable + * @property {boolean=} built + * @property {boolean=} codeGenerated + * @property {boolean=} buildTimeExecuted + * @property {boolean=} cached + * @property {boolean=} optional + * @property {boolean=} orphan + * @property {string|number=} id + * @property {string|number=} issuerId + * @property {(string|number)[]=} chunks + * @property {(string|number)[]=} assets + * @property {boolean=} dependent + * @property {string=} issuer + * @property {string=} issuerName + * @property {StatsModuleIssuer[]=} issuerPath + * @property {boolean=} failed + * @property {number=} errors + * @property {number=} warnings + * @property {StatsProfile=} profile + * @property {StatsModuleReason[]=} reasons + * @property {(boolean | string[])=} usedExports + * @property {string[]=} providedExports + * @property {string[]=} optimizationBailout + * @property {number=} depth + * @property {StatsModule[]=} modules + * @property {number=} filteredModules + * @property {ReturnType=} source + */ - "moduleTraceItem.originName": originName => originName, +/** @typedef {KnownStatsProfile & Record} StatsProfile */ +/** + * @typedef {Object} KnownStatsProfile + * @property {number} total + * @property {number} resolving + * @property {number} restoring + * @property {number} building + * @property {number} integration + * @property {number} storing + * @property {number} additionalResolving + * @property {number} additionalIntegration + * @property {number} factory + * @property {number} dependencies + */ - loggingGroup: loggingGroup => - loggingGroup.entries.length === 0 ? "" : undefined, - "loggingGroup.debug": (flag, { red }) => (flag ? red("DEBUG") : undefined), - "loggingGroup.name": (name, { bold }) => bold(`LOG from ${name}`), - "loggingGroup.separator!": () => "\n", - "loggingGroup.filteredEntries": filteredEntries => - filteredEntries > 0 ? `+ ${filteredEntries} hidden lines` : undefined, +/** @typedef {KnownStatsModuleIssuer & Record} StatsModuleIssuer */ +/** + * @typedef {Object} KnownStatsModuleIssuer + * @property {string=} identifier + * @property {string=} name + * @property {(string|number)=} id + * @property {StatsProfile=} profile + */ - "moduleTraceDependency.loc": loc => loc -}; +/** @typedef {KnownStatsModuleReason & Record} StatsModuleReason */ +/** + * @typedef {Object} KnownStatsModuleReason + * @property {string=} moduleIdentifier + * @property {string=} module + * @property {string=} moduleName + * @property {string=} resolvedModuleIdentifier + * @property {string=} resolvedModule + * @property {string=} type + * @property {boolean} active + * @property {string=} explanation + * @property {string=} userRequest + * @property {string=} loc + * @property {(string|number)=} moduleId + * @property {(string|number)=} resolvedModuleId + */ -/** @type {Record} */ -const ITEM_NAMES = { - "compilation.assets[]": "asset", - "compilation.modules[]": "module", - "compilation.chunks[]": "chunk", - "compilation.entrypoints[]": "chunkGroup", - "compilation.namedChunkGroups[]": "chunkGroup", - "compilation.errors[]": "error", - "compilation.warnings[]": "error", - "compilation.logging[]": "loggingGroup", - "compilation.children[]": "compilation", - "asset.related[]": "asset", - "asset.children[]": "asset", - "asset.chunks[]": "assetChunk", - "asset.auxiliaryChunks[]": "assetChunk", - "asset.chunkNames[]": "assetChunkName", - "asset.chunkIdHints[]": "assetChunkIdHint", - "asset.auxiliaryChunkNames[]": "assetChunkName", - "asset.auxiliaryChunkIdHints[]": "assetChunkIdHint", - "chunkGroup.assets[]": "chunkGroupAsset", - "chunkGroup.auxiliaryAssets[]": "chunkGroupAsset", - "chunkGroupChild.assets[]": "chunkGroupAsset", - "chunkGroupChild.auxiliaryAssets[]": "chunkGroupAsset", - "chunkGroup.children[]": "chunkGroupChildGroup", - "chunkGroupChildGroup.children[]": "chunkGroupChild", - "module.modules[]": "module", - "module.children[]": "module", - "module.reasons[]": "moduleReason", - "moduleReason.children[]": "moduleReason", - "module.issuerPath[]": "moduleIssuer", - "chunk.origins[]": "chunkOrigin", - "chunk.modules[]": "module", - "loggingGroup.entries[]": logEntry => - `loggingEntry(${logEntry.type}).loggingEntry`, - "loggingEntry.children[]": logEntry => - `loggingEntry(${logEntry.type}).loggingEntry`, - "error.moduleTrace[]": "moduleTraceItem", - "moduleTraceItem.dependencies[]": "moduleTraceDependency" -}; +/** @typedef {KnownStatsChunk & Record} StatsChunk */ +/** + * @typedef {Object} KnownStatsChunk + * @property {boolean} rendered + * @property {boolean} initial + * @property {boolean} entry + * @property {boolean} recorded + * @property {string=} reason + * @property {number} size + * @property {Record=} sizes + * @property {string[]=} names + * @property {string[]=} idHints + * @property {string[]=} runtime + * @property {string[]=} files + * @property {string[]=} auxiliaryFiles + * @property {string} hash + * @property {Record=} childrenByOrder + * @property {(string|number)=} id + * @property {(string|number)[]=} siblings + * @property {(string|number)[]=} parents + * @property {(string|number)[]=} children + * @property {StatsModule[]=} modules + * @property {number=} filteredModules + * @property {StatsChunkOrigin[]=} origins + */ -const ERROR_PREFERRED_ORDER = [ - "compilerPath", - "chunkId", - "chunkEntry", - "chunkInitial", - "file", - "separator!", - "moduleName", - "loc", - "separator!", - "message", - "separator!", - "details", - "separator!", - "stack", - "separator!", - "missing", - "separator!", - "moduleTrace" -]; +/** @typedef {KnownStatsChunkOrigin & Record} StatsChunkOrigin */ +/** + * @typedef {Object} KnownStatsChunkOrigin + * @property {string=} module + * @property {string=} moduleIdentifier + * @property {string=} moduleName + * @property {string=} loc + * @property {string=} request + * @property {(string|number)=} moduleId + */ -/** @type {Record} */ -const PREFERRED_ORDERS = { - compilation: [ - "name", - "hash", - "version", - "time", - "builtAt", - "env", - "publicPath", - "assets", - "filteredAssets", - "entrypoints", - "namedChunkGroups", - "chunks", - "modules", - "filteredModules", - "children", - "logging", - "warnings", - "warningsInChildren!", - "filteredWarningDetailsCount", - "errors", - "errorsInChildren!", - "filteredErrorDetailsCount", - "summary!", - "needAdditionalPass" - ], - asset: [ - "type", - "name", - "size", - "chunks", - "auxiliaryChunks", - "emitted", - "comparedForEmit", - "cached", - "info", - "isOverSizeLimit", - "chunkNames", - "auxiliaryChunkNames", - "chunkIdHints", - "auxiliaryChunkIdHints", - "related", - "filteredRelated", - "children", - "filteredChildren" - ], - "asset.info": [ - "immutable", - "sourceFilename", - "javascriptModule", - "development", - "hotModuleReplacement" - ], - chunkGroup: [ - "kind!", - "name", - "isOverSizeLimit", - "assetsSize", - "auxiliaryAssetsSize", - "is!", - "assets", - "filteredAssets", - "auxiliaryAssets", - "filteredAuxiliaryAssets", - "separator!", - "children" - ], - chunkGroupAsset: ["name", "size"], - chunkGroupChildGroup: ["type", "children"], - chunkGroupChild: ["assets", "chunks", "name"], - module: [ - "type", - "name", - "identifier", - "id", - "layer", - "sizes", - "chunks", - "depth", - "cacheable", - "orphan", - "runtime", - "optional", - "dependent", - "built", - "codeGenerated", - "cached", - "assets", - "failed", - "warnings", - "errors", - "children", - "filteredChildren", - "providedExports", - "usedExports", - "optimizationBailout", - "reasons", - "filteredReasons", - "issuerPath", - "profile", - "modules", - "filteredModules" - ], - moduleReason: [ - "active", - "type", - "userRequest", - "moduleId", - "module", - "resolvedModule", - "loc", - "explanation", - "children", - "filteredChildren" - ], - "module.profile": [ - "total", - "separator!", - "resolving", - "restoring", - "integration", - "building", - "storing", - "additionalResolving", - "additionalIntegration" - ], - chunk: [ - "id", - "runtime", - "files", - "names", - "idHints", - "sizes", - "parents", - "siblings", - "children", - "childrenByOrder", - "entry", - "initial", - "rendered", - "recorded", - "reason", - "separator!", - "origins", - "separator!", - "modules", - "separator!", - "filteredModules" - ], - chunkOrigin: ["request", "moduleId", "moduleName", "loc"], - error: ERROR_PREFERRED_ORDER, - warning: ERROR_PREFERRED_ORDER, - "chunk.childrenByOrder[]": ["type", "children"], - loggingGroup: [ - "debug", - "name", - "separator!", - "entries", - "separator!", - "filteredEntries" - ], - loggingEntry: ["message", "trace", "children"] -}; +/** @typedef {KnownStatsModuleTraceItem & Record} StatsModuleTraceItem */ +/** + * @typedef {Object} KnownStatsModuleTraceItem + * @property {string=} originIdentifier + * @property {string=} originName + * @property {string=} moduleIdentifier + * @property {string=} moduleName + * @property {StatsModuleTraceDependency[]=} dependencies + * @property {(string|number)=} originId + * @property {(string|number)=} moduleId + */ -const itemsJoinOneLine = items => items.filter(Boolean).join(" "); -const itemsJoinOneLineBrackets = items => - items.length > 0 ? `(${items.filter(Boolean).join(" ")})` : undefined; -const itemsJoinMoreSpacing = items => items.filter(Boolean).join("\n\n"); -const itemsJoinComma = items => items.filter(Boolean).join(", "); -const itemsJoinCommaBrackets = items => - items.length > 0 ? `(${items.filter(Boolean).join(", ")})` : undefined; -const itemsJoinCommaBracketsWithName = name => items => - items.length > 0 - ? `(${name}: ${items.filter(Boolean).join(", ")})` - : undefined; +/** @typedef {KnownStatsModuleTraceDependency & Record} StatsModuleTraceDependency */ +/** + * @typedef {Object} KnownStatsModuleTraceDependency + * @property {string=} loc + */ -/** @type {Record string>} */ -const SIMPLE_ITEMS_JOINER = { - "chunk.parents": itemsJoinOneLine, - "chunk.siblings": itemsJoinOneLine, - "chunk.children": itemsJoinOneLine, - "chunk.names": itemsJoinCommaBrackets, - "chunk.idHints": itemsJoinCommaBracketsWithName("id hint"), - "chunk.runtime": itemsJoinCommaBracketsWithName("runtime"), - "chunk.files": itemsJoinComma, - "chunk.childrenByOrder": itemsJoinOneLine, - "chunk.childrenByOrder[].children": itemsJoinOneLine, - "chunkGroup.assets": itemsJoinOneLine, - "chunkGroup.auxiliaryAssets": itemsJoinOneLineBrackets, - "chunkGroupChildGroup.children": itemsJoinComma, - "chunkGroupChild.assets": itemsJoinOneLine, - "chunkGroupChild.auxiliaryAssets": itemsJoinOneLineBrackets, - "asset.chunks": itemsJoinComma, - "asset.auxiliaryChunks": itemsJoinCommaBrackets, - "asset.chunkNames": itemsJoinCommaBracketsWithName("name"), - "asset.auxiliaryChunkNames": itemsJoinCommaBracketsWithName("auxiliary name"), - "asset.chunkIdHints": itemsJoinCommaBracketsWithName("id hint"), - "asset.auxiliaryChunkIdHints": - itemsJoinCommaBracketsWithName("auxiliary id hint"), - "module.chunks": itemsJoinOneLine, - "module.issuerPath": items => - items - .filter(Boolean) - .map(item => `${item} ->`) - .join(" "), - "compilation.errors": itemsJoinMoreSpacing, - "compilation.warnings": itemsJoinMoreSpacing, - "compilation.logging": itemsJoinMoreSpacing, - "compilation.children": items => indent(itemsJoinMoreSpacing(items), " "), - "moduleTraceItem.dependencies": itemsJoinOneLine, - "loggingEntry.children": items => - indent(items.filter(Boolean).join("\n"), " ", false) -}; +/** @typedef {KnownStatsError & Record} StatsError */ +/** + * @typedef {Object} KnownStatsError + * @property {string} message + * @property {string=} chunkName + * @property {boolean=} chunkEntry + * @property {boolean=} chunkInitial + * @property {string=} file + * @property {string=} moduleIdentifier + * @property {string=} moduleName + * @property {string=} loc + * @property {string|number=} chunkId + * @property {string|number=} moduleId + * @property {StatsModuleTraceItem[]=} moduleTrace + * @property {any=} details + * @property {string=} stack + */ -const joinOneLine = items => - items - .map(item => item.content) - .filter(Boolean) - .join(" "); +/** @typedef {Asset & { type: string, related: PreprocessedAsset[] }} PreprocessedAsset */ -const joinInBrackets = items => { - const res = []; - let mode = 0; +/** + * @template T + * @template O + * @typedef {Record void>} ExtractorsByOption + */ + +/** + * @typedef {Object} SimpleExtractors + * @property {ExtractorsByOption} compilation + * @property {ExtractorsByOption} asset + * @property {ExtractorsByOption} asset$visible + * @property {ExtractorsByOption<{ name: string, chunkGroup: ChunkGroup }, StatsChunkGroup>} chunkGroup + * @property {ExtractorsByOption} module + * @property {ExtractorsByOption} module$visible + * @property {ExtractorsByOption} moduleIssuer + * @property {ExtractorsByOption} profile + * @property {ExtractorsByOption} moduleReason + * @property {ExtractorsByOption} chunk + * @property {ExtractorsByOption} chunkOrigin + * @property {ExtractorsByOption} error + * @property {ExtractorsByOption} warning + * @property {ExtractorsByOption<{ origin: Module, module: Module }, StatsModuleTraceItem>} moduleTraceItem + * @property {ExtractorsByOption} moduleTraceDependency + */ + +/** + * @template T + * @template I + * @param {Iterable} items items to select from + * @param {function(T): Iterable} selector selector function to select values from item + * @returns {I[]} array of values + */ +const uniqueArray = (items, selector) => { + /** @type {Set} */ + const set = new Set(); for (const item of items) { - if (item.element === "separator!") { - switch (mode) { - case 0: - case 1: - mode += 2; - break; - case 4: - res.push(")"); - mode = 3; - break; - } - } - if (!item.content) continue; - switch (mode) { - case 0: - mode = 1; - break; - case 1: - res.push(" "); - break; - case 2: - res.push("("); - mode = 4; - break; - case 3: - res.push(" ("); - mode = 4; - break; - case 4: - res.push(", "); - break; + for (const i of selector(item)) { + set.add(i); } - res.push(item.content); } - if (mode === 4) res.push(")"); - return res.join(""); + return Array.from(set); }; -const indent = (str, prefix, noPrefixInFirstLine) => { - const rem = str.replace(/\n([^\n])/g, "\n" + prefix + "$1"); - if (noPrefixInFirstLine) return rem; - const ind = str[0] === "\n" ? "" : prefix; - return ind + rem; +/** + * @template T + * @template I + * @param {Iterable} items items to select from + * @param {function(T): Iterable} selector selector function to select values from item + * @param {Comparator} comparator comparator function + * @returns {I[]} array of values + */ +const uniqueOrderedArray = (items, selector, comparator) => { + return uniqueArray(items, selector).sort(comparator); }; -const joinExplicitNewLine = (items, indenter) => { - let firstInLine = true; - let first = true; - return items - .map(item => { - if (!item || !item.content) return; - let content = indent(item.content, first ? "" : indenter, !firstInLine); - if (firstInLine) { - content = content.replace(/^\n+/, ""); - } - if (!content) return; - first = false; - const noJoiner = firstInLine || content.startsWith("\n"); - firstInLine = content.endsWith("\n"); - return noJoiner ? content : " " + content; - }) - .filter(Boolean) - .join("") - .trim(); +/** @template T @template R @typedef {{ [P in keyof T]: R }} MappedValues */ + +/** + * @template T + * @template R + * @param {T} obj object to be mapped + * @param {function(T[keyof T], keyof T): R} fn mapping function + * @returns {MappedValues} mapped object + */ +const mapObject = (obj, fn) => { + const newObj = Object.create(null); + for (const key of Object.keys(obj)) { + newObj[key] = fn(obj[key], /** @type {keyof T} */ (key)); + } + return newObj; }; -const joinError = - error => - (items, { red, yellow }) => - `${error ? red("ERROR") : yellow("WARNING")} in ${joinExplicitNewLine( - items, - "" - )}`; +/** + * @param {Compilation} compilation the compilation + * @param {function(Compilation, string): any[]} getItems get items + * @returns {number} total number + */ +const countWithChildren = (compilation, getItems) => { + let count = getItems(compilation, "").length; + for (const child of compilation.children) { + count += countWithChildren(child, (c, type) => + getItems(c, `.children[].compilation${type}`) + ); + } + return count; +}; -/** @type {Record string>} */ -const SIMPLE_ELEMENT_JOINERS = { - compilation: items => { - const result = []; - let lastNeedMore = false; - for (const item of items) { - if (!item.content) continue; - const needMoreSpace = - item.element === "warnings" || - item.element === "filteredWarningDetailsCount" || - item.element === "errors" || - item.element === "filteredErrorDetailsCount" || - item.element === "logging"; - if (result.length !== 0) { - result.push(needMoreSpace || lastNeedMore ? "\n\n" : "\n"); +/** @type {ExtractorsByOption} */ +const EXTRACT_ERROR = { + _: (object, error, context, { requestShortener }) => { + // TODO webpack 6 disallow strings in the errors/warnings list + if (typeof error === "string") { + object.message = error; + } else { + if (error.chunk) { + object.chunkName = error.chunk.name; + object.chunkEntry = error.chunk.hasRuntime(); + object.chunkInitial = error.chunk.canBeInitial(); } - result.push(item.content); - lastNeedMore = needMoreSpace; + if (error.file) { + object.file = error.file; + } + if (error.module) { + object.moduleIdentifier = error.module.identifier(); + object.moduleName = error.module.readableIdentifier(requestShortener); + } + if (error.loc) { + object.loc = formatLocation(error.loc); + } + object.message = error.message; } - if (lastNeedMore) result.push("\n"); - return result.join(""); - }, - asset: items => - joinExplicitNewLine( - items.map(item => { - if ( - (item.element === "related" || item.element === "children") && - item.content - ) { - return { - ...item, - content: `\n${item.content}\n` - }; - } - return item; - }), - " " - ), - "asset.info": joinOneLine, - module: (items, { module }) => { - let hasName = false; - return joinExplicitNewLine( - items.map(item => { - switch (item.element) { - case "id": - if (module.id === module.name) { - if (hasName) return false; - if (item.content) hasName = true; - } - break; - case "name": - if (hasName) return false; - if (item.content) hasName = true; - break; - case "providedExports": - case "usedExports": - case "optimizationBailout": - case "reasons": - case "issuerPath": - case "profile": - case "children": - case "modules": - if (item.content) { - return { - ...item, - content: `\n${item.content}\n` - }; - } - break; - } - return item; - }), - " " - ); }, - chunk: items => { - let hasEntry = false; - return ( - "chunk " + - joinExplicitNewLine( - items.filter(item => { - switch (item.element) { - case "entry": - if (item.content) hasEntry = true; - break; - case "initial": - if (hasEntry) return false; - break; - } - return true; - }), - " " - ) - ); - }, - "chunk.childrenByOrder[]": items => `(${joinOneLine(items)})`, - chunkGroup: items => joinExplicitNewLine(items, " "), - chunkGroupAsset: joinOneLine, - chunkGroupChildGroup: joinOneLine, - chunkGroupChild: joinOneLine, - // moduleReason: (items, { moduleReason }) => { - // let hasName = false; - // return joinOneLine( - // items.filter(item => { - // switch (item.element) { - // case "moduleId": - // if (moduleReason.moduleId === moduleReason.module && item.content) - // hasName = true; - // break; - // case "module": - // if (hasName) return false; - // break; - // case "resolvedModule": - // return ( - // moduleReason.module !== moduleReason.resolvedModule && - // item.content - // ); - // } - // return true; - // }) - // ); - // }, - moduleReason: (items, { moduleReason }) => { - let hasName = false; - return joinExplicitNewLine( - items.map(item => { - switch (item.element) { - case "moduleId": - if (moduleReason.moduleId === moduleReason.module && item.content) - hasName = true; - break; - case "module": - if (hasName) return false; - break; - case "resolvedModule": - if (moduleReason.module === moduleReason.resolvedModule) - return false; - break; - case "children": - if (item.content) { - return { - ...item, - content: `\n${item.content}\n` - }; - } - break; - } - return item; - }), - " " - ); - }, - "module.profile": joinInBrackets, - moduleIssuer: joinOneLine, - chunkOrigin: items => "> " + joinOneLine(items), - "errors[].error": joinError(true), - "warnings[].error": joinError(false), - loggingGroup: items => joinExplicitNewLine(items, "").trimRight(), - moduleTraceItem: items => " @ " + joinOneLine(items), - moduleTraceDependency: joinOneLine -}; - -const AVAILABLE_COLORS = { - bold: "\u001b[1m", - yellow: "\u001b[1m\u001b[33m", - red: "\u001b[1m\u001b[31m", - green: "\u001b[1m\u001b[32m", - cyan: "\u001b[1m\u001b[36m", - magenta: "\u001b[1m\u001b[35m" -}; - -const AVAILABLE_FORMATS = { - formatChunkId: (id, { yellow }, direction) => { - switch (direction) { - case "parent": - return `<{${yellow(id)}}>`; - case "sibling": - return `={${yellow(id)}}=`; - case "child": - return `>{${yellow(id)}}<`; - default: - return `{${yellow(id)}}`; + ids: (object, error, { compilation: { chunkGraph } }) => { + if (typeof error !== "string") { + if (error.chunk) { + object.chunkId = error.chunk.id; + } + if (error.module) { + object.moduleId = chunkGraph.getModuleId(error.module); + } } }, - formatModuleId: id => `[${id}]`, - formatFilename: (filename, { green, yellow }, oversize) => - (oversize ? yellow : green)(filename), - formatFlag: flag => `[${flag}]`, - formatLayer: layer => `(in ${layer})`, - formatSize: __webpack_require__(15979).formatSize, - formatDateTime: (dateTime, { bold }) => { - const d = new Date(dateTime); - const x = twoDigit; - const date = `${d.getFullYear()}-${x(d.getMonth() + 1)}-${x(d.getDate())}`; - const time = `${x(d.getHours())}:${x(d.getMinutes())}:${x(d.getSeconds())}`; - return `${date} ${bold(time)}`; + moduleTrace: (object, error, context, options, factory) => { + if (typeof error !== "string" && error.module) { + const { + type, + compilation: { moduleGraph } + } = context; + /** @type {Set} */ + const visitedModules = new Set(); + const moduleTrace = []; + let current = error.module; + while (current) { + if (visitedModules.has(current)) break; // circular (technically impossible, but how knows) + visitedModules.add(current); + const origin = moduleGraph.getIssuer(current); + if (!origin) break; + moduleTrace.push({ origin, module: current }); + current = origin; + } + object.moduleTrace = factory.create( + `${type}.moduleTrace`, + moduleTrace, + context + ); + } }, - formatTime: ( - time, - { timeReference, bold, green, yellow, red }, - boldQuantity + errorDetails: ( + object, + error, + { type, compilation, cachedGetErrors, cachedGetWarnings }, + { errorDetails } ) => { - const unit = " ms"; - if (timeReference && time !== timeReference) { - const times = [ - timeReference / 2, - timeReference / 4, - timeReference / 8, - timeReference / 16 - ]; - if (time < times[3]) return `${time}${unit}`; - else if (time < times[2]) return bold(`${time}${unit}`); - else if (time < times[1]) return green(`${time}${unit}`); - else if (time < times[0]) return yellow(`${time}${unit}`); - else return red(`${time}${unit}`); - } else { - return `${boldQuantity ? bold(time) : time}${unit}`; + if ( + typeof error !== "string" && + (errorDetails === true || + (type.endsWith(".error") && cachedGetErrors(compilation).length < 3)) + ) { + object.details = error.details; } }, - formatError: (message, { green, yellow, red }) => { - if (message.includes("\u001b[")) return message; - const highlights = [ - { regExp: /(Did you mean .+)/g, format: green }, - { - regExp: /(Set 'mode' option to 'development' or 'production')/g, - format: green - }, - { regExp: /(\(module has no exports\))/g, format: red }, - { regExp: /\(possible exports: (.+)\)/g, format: green }, - { regExp: /\s*([^\s].* doesn't exist)/g, format: red }, - { regExp: /('\w+' option has not been set)/g, format: red }, - { - regExp: /(Emitted value instead of an instance of Error)/g, - format: yellow - }, - { regExp: /(Used? .+ instead)/gi, format: yellow }, - { regExp: /\b(deprecated|must|required)\b/g, format: yellow }, - { - regExp: /\b(BREAKING CHANGE)\b/gi, - format: red - }, - { - regExp: - /\b(error|failed|unexpected|invalid|not found|not supported|not available|not possible|not implemented|doesn't support|conflict|conflicting|not existing|duplicate)\b/gi, - format: red - } - ]; - for (const { regExp, format } of highlights) { - message = message.replace(regExp, (match, content) => { - return match.replace(content, format(content)); - }); + errorStack: (object, error) => { + if (typeof error !== "string") { + object.stack = error.stack; } - return message; } }; -const RESULT_MODIFIER = { - "module.modules": result => { - return indent(result, "| "); - } -}; +/** @type {SimpleExtractors} */ +const SIMPLE_EXTRACTORS = { + compilation: { + _: (object, compilation, context, options) => { + if (!context.makePathsRelative) { + context.makePathsRelative = makePathsRelative.bindContextCache( + compilation.compiler.context, + compilation.compiler.root + ); + } + if (!context.cachedGetErrors) { + const map = new WeakMap(); + context.cachedGetErrors = compilation => { + return ( + map.get(compilation) || + (errors => (map.set(compilation, errors), errors))( + compilation.getErrors() + ) + ); + }; + } + if (!context.cachedGetWarnings) { + const map = new WeakMap(); + context.cachedGetWarnings = compilation => { + return ( + map.get(compilation) || + (warnings => (map.set(compilation, warnings), warnings))( + compilation.getWarnings() + ) + ); + }; + } + if (compilation.name) { + object.name = compilation.name; + } + if (compilation.needAdditionalPass) { + object.needAdditionalPass = true; + } + + const { logging, loggingDebug, loggingTrace } = options; + if (logging || (loggingDebug && loggingDebug.length > 0)) { + const util = __webpack_require__(31669); + object.logging = {}; + let acceptedTypes; + let collapsedGroups = false; + switch (logging) { + default: + acceptedTypes = new Set(); + break; + case "error": + acceptedTypes = new Set([LogType.error]); + break; + case "warn": + acceptedTypes = new Set([LogType.error, LogType.warn]); + break; + case "info": + acceptedTypes = new Set([ + LogType.error, + LogType.warn, + LogType.info + ]); + break; + case "log": + acceptedTypes = new Set([ + LogType.error, + LogType.warn, + LogType.info, + LogType.log, + LogType.group, + LogType.groupEnd, + LogType.groupCollapsed, + LogType.clear + ]); + break; + case "verbose": + acceptedTypes = new Set([ + LogType.error, + LogType.warn, + LogType.info, + LogType.log, + LogType.group, + LogType.groupEnd, + LogType.groupCollapsed, + LogType.profile, + LogType.profileEnd, + LogType.time, + LogType.status, + LogType.clear + ]); + collapsedGroups = true; + break; + } + const cachedMakePathsRelative = makePathsRelative.bindContextCache( + options.context, + compilation.compiler.root + ); + let depthInCollapsedGroup = 0; + for (const [origin, logEntries] of compilation.logging) { + const debugMode = loggingDebug.some(fn => fn(origin)); + if (logging === false && !debugMode) continue; + /** @type {KnownStatsLoggingEntry[]} */ + const groupStack = []; + /** @type {KnownStatsLoggingEntry[]} */ + const rootList = []; + let currentList = rootList; + let processedLogEntries = 0; + for (const entry of logEntries) { + let type = entry.type; + if (!debugMode && !acceptedTypes.has(type)) continue; -const createOrder = (array, preferredOrder) => { - const originalArray = array.slice(); - const set = new Set(array); - const usedSet = new Set(); - array.length = 0; - for (const element of preferredOrder) { - if (element.endsWith("!") || set.has(element)) { - array.push(element); - usedSet.add(element); - } - } - for (const element of originalArray) { - if (!usedSet.has(element)) { - array.push(element); - } - } - return array; -}; + // Expand groups in verbose and debug modes + if ( + type === LogType.groupCollapsed && + (debugMode || collapsedGroups) + ) + type = LogType.group; -class DefaultStatsPrinterPlugin { - /** - * Apply the plugin - * @param {Compiler} compiler the compiler instance - * @returns {void} - */ - apply(compiler) { - compiler.hooks.compilation.tap("DefaultStatsPrinterPlugin", compilation => { - compilation.hooks.statsPrinter.tap( - "DefaultStatsPrinterPlugin", - (stats, options, context) => { - // Put colors into context - stats.hooks.print - .for("compilation") - .tap("DefaultStatsPrinterPlugin", (compilation, context) => { - for (const color of Object.keys(AVAILABLE_COLORS)) { - let start; - if (options.colors) { - if ( - typeof options.colors === "object" && - typeof options.colors[color] === "string" - ) { - start = options.colors[color]; - } else { - start = AVAILABLE_COLORS[color]; - } - } - if (start) { - context[color] = str => - `${start}${ - typeof str === "string" - ? str.replace( - /((\u001b\[39m|\u001b\[22m|\u001b\[0m)+)/g, - `$1${start}` - ) - : str - }\u001b[39m\u001b[22m`; - } else { - context[color] = str => str; - } + if (depthInCollapsedGroup === 0) { + processedLogEntries++; + } + + if (type === LogType.groupEnd) { + groupStack.pop(); + if (groupStack.length > 0) { + currentList = groupStack[groupStack.length - 1].children; + } else { + currentList = rootList; } - for (const format of Object.keys(AVAILABLE_FORMATS)) { - context[format] = (content, ...args) => - AVAILABLE_FORMATS[format](content, context, ...args); + if (depthInCollapsedGroup > 0) depthInCollapsedGroup--; + continue; + } + let message = undefined; + if (entry.type === LogType.time) { + message = `${entry.args[0]}: ${ + entry.args[1] * 1000 + entry.args[2] / 1000000 + } ms`; + } else if (entry.args && entry.args.length > 0) { + message = util.format(entry.args[0], ...entry.args.slice(1)); + } + /** @type {KnownStatsLoggingEntry} */ + const newEntry = { + ...entry, + type, + message, + trace: loggingTrace ? entry.trace : undefined, + children: + type === LogType.group || type === LogType.groupCollapsed + ? [] + : undefined + }; + currentList.push(newEntry); + if (newEntry.children) { + groupStack.push(newEntry); + currentList = newEntry.children; + if (depthInCollapsedGroup > 0) { + depthInCollapsedGroup++; + } else if (type === LogType.groupCollapsed) { + depthInCollapsedGroup = 1; } - context.timeReference = compilation.time; - }); - - for (const key of Object.keys(SIMPLE_PRINTERS)) { - stats.hooks.print - .for(key) - .tap("DefaultStatsPrinterPlugin", (obj, ctx) => - SIMPLE_PRINTERS[key](obj, ctx, stats) - ); + } } - - for (const key of Object.keys(PREFERRED_ORDERS)) { - const preferredOrder = PREFERRED_ORDERS[key]; - stats.hooks.sortElements - .for(key) - .tap("DefaultStatsPrinterPlugin", (elements, context) => { - createOrder(elements, preferredOrder); - }); + let name = cachedMakePathsRelative(origin).replace(/\|/g, " "); + if (name in object.logging) { + let i = 1; + while (`${name}#${i}` in object.logging) { + i++; + } + name = `${name}#${i}`; } - - for (const key of Object.keys(ITEM_NAMES)) { - const itemName = ITEM_NAMES[key]; - stats.hooks.getItemName - .for(key) - .tap( - "DefaultStatsPrinterPlugin", - typeof itemName === "string" ? () => itemName : itemName - ); + object.logging[name] = { + entries: rootList, + filteredEntries: logEntries.length - processedLogEntries, + debug: debugMode + }; + } + } + }, + hash: (object, compilation) => { + object.hash = compilation.hash; + }, + version: object => { + object.version = __webpack_require__(87168)/* .version */ .i8; + }, + env: (object, compilation, context, { _env }) => { + object.env = _env; + }, + timings: (object, compilation) => { + object.time = compilation.endTime - compilation.startTime; + }, + builtAt: (object, compilation) => { + object.builtAt = compilation.endTime; + }, + publicPath: (object, compilation) => { + object.publicPath = compilation.getPath( + compilation.outputOptions.publicPath + ); + }, + outputPath: (object, compilation) => { + object.outputPath = compilation.outputOptions.path; + }, + assets: (object, compilation, context, options, factory) => { + const { type } = context; + /** @type {Map} */ + const compilationFileToChunks = new Map(); + /** @type {Map} */ + const compilationAuxiliaryFileToChunks = new Map(); + for (const chunk of compilation.chunks) { + for (const file of chunk.files) { + let array = compilationFileToChunks.get(file); + if (array === undefined) { + array = []; + compilationFileToChunks.set(file, array); } - - for (const key of Object.keys(SIMPLE_ITEMS_JOINER)) { - const joiner = SIMPLE_ITEMS_JOINER[key]; - stats.hooks.printItems - .for(key) - .tap("DefaultStatsPrinterPlugin", joiner); + array.push(chunk); + } + for (const file of chunk.auxiliaryFiles) { + let array = compilationAuxiliaryFileToChunks.get(file); + if (array === undefined) { + array = []; + compilationAuxiliaryFileToChunks.set(file, array); } - - for (const key of Object.keys(SIMPLE_ELEMENT_JOINERS)) { - const joiner = SIMPLE_ELEMENT_JOINERS[key]; - stats.hooks.printElements - .for(key) - .tap("DefaultStatsPrinterPlugin", joiner); + array.push(chunk); + } + } + /** @type {Map} */ + const assetMap = new Map(); + /** @type {Set} */ + const assets = new Set(); + for (const asset of compilation.getAssets()) { + /** @type {PreprocessedAsset} */ + const item = { + ...asset, + type: "asset", + related: undefined + }; + assets.add(item); + assetMap.set(asset.name, item); + } + for (const item of assetMap.values()) { + const related = item.info.related; + if (!related) continue; + for (const type of Object.keys(related)) { + const relatedEntry = related[type]; + const deps = Array.isArray(relatedEntry) + ? relatedEntry + : [relatedEntry]; + for (const dep of deps) { + const depItem = assetMap.get(dep); + if (!depItem) continue; + assets.delete(depItem); + depItem.type = type; + item.related = item.related || []; + item.related.push(depItem); } + } + } - for (const key of Object.keys(RESULT_MODIFIER)) { - const modifier = RESULT_MODIFIER[key]; - stats.hooks.result - .for(key) - .tap("DefaultStatsPrinterPlugin", modifier); + object.assetsByChunkName = {}; + for (const [file, chunks] of compilationFileToChunks) { + for (const chunk of chunks) { + const name = chunk.name; + if (!name) continue; + if ( + !Object.prototype.hasOwnProperty.call( + object.assetsByChunkName, + name + ) + ) { + object.assetsByChunkName[name] = []; } + object.assetsByChunkName[name].push(file); } - ); - }); - } -} -module.exports = DefaultStatsPrinterPlugin; - - -/***/ }), - -/***/ 69646: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ - - - -const { HookMap, SyncBailHook, SyncWaterfallHook } = __webpack_require__(34718); -const { concatComparators, keepOriginalOrder } = __webpack_require__(26296); -const smartGrouping = __webpack_require__(84820); - -/** @typedef {import("../Chunk")} Chunk */ -/** @typedef {import("../Compilation")} Compilation */ -/** @typedef {import("../Module")} Module */ -/** @typedef {import("../WebpackError")} WebpackError */ -/** @typedef {import("../util/runtime").RuntimeSpec} RuntimeSpec */ - -/** @typedef {import("../util/smartGrouping").GroupConfig} GroupConfig */ - -/** - * @typedef {Object} KnownStatsFactoryContext - * @property {string} type - * @property {function(string): string=} makePathsRelative - * @property {Compilation=} compilation - * @property {Set=} rootModules - * @property {Map=} compilationFileToChunks - * @property {Map=} compilationAuxiliaryFileToChunks - * @property {RuntimeSpec=} runtime - * @property {function(Compilation): WebpackError[]=} cachedGetErrors - * @property {function(Compilation): WebpackError[]=} cachedGetWarnings - */ - -/** @typedef {KnownStatsFactoryContext & Record} StatsFactoryContext */ - -class StatsFactory { - constructor() { - this.hooks = Object.freeze({ - /** @type {HookMap>} */ - extract: new HookMap( - () => new SyncBailHook(["object", "data", "context"]) - ), - /** @type {HookMap>} */ - filter: new HookMap( - () => new SyncBailHook(["item", "context", "index", "unfilteredIndex"]) - ), - /** @type {HookMap>} */ - sort: new HookMap(() => new SyncBailHook(["comparators", "context"])), - /** @type {HookMap>} */ - filterSorted: new HookMap( - () => new SyncBailHook(["item", "context", "index", "unfilteredIndex"]) - ), - /** @type {HookMap>} */ - groupResults: new HookMap( - () => new SyncBailHook(["groupConfigs", "context"]) - ), - /** @type {HookMap>} */ - sortResults: new HookMap( - () => new SyncBailHook(["comparators", "context"]) - ), - /** @type {HookMap>} */ - filterResults: new HookMap( - () => new SyncBailHook(["item", "context", "index", "unfilteredIndex"]) - ), - /** @type {HookMap>} */ - merge: new HookMap(() => new SyncBailHook(["items", "context"])), - /** @type {HookMap>} */ - result: new HookMap(() => new SyncWaterfallHook(["result", "context"])), - /** @type {HookMap>} */ - getItemName: new HookMap(() => new SyncBailHook(["item", "context"])), - /** @type {HookMap>} */ - getItemFactory: new HookMap(() => new SyncBailHook(["item", "context"])) - }); - const hooks = this.hooks; - this._caches = - /** @type {Record[]>>} */ ({}); - for (const key of Object.keys(hooks)) { - this._caches[key] = new Map(); - } - this._inCreate = false; - } - - _getAllLevelHooks(hookMap, cache, type) { - const cacheEntry = cache.get(type); - if (cacheEntry !== undefined) { - return cacheEntry; - } - const hooks = []; - const typeParts = type.split("."); - for (let i = 0; i < typeParts.length; i++) { - const hook = hookMap.get(typeParts.slice(i).join(".")); - if (hook) { - hooks.push(hook); } - } - cache.set(type, hooks); - return hooks; - } - - _forEachLevel(hookMap, cache, type, fn) { - for (const hook of this._getAllLevelHooks(hookMap, cache, type)) { - const result = fn(hook); - if (result !== undefined) return result; - } - } - - _forEachLevelWaterfall(hookMap, cache, type, data, fn) { - for (const hook of this._getAllLevelHooks(hookMap, cache, type)) { - data = fn(hook, data); - } - return data; - } - _forEachLevelFilter(hookMap, cache, type, items, fn, forceClone) { - const hooks = this._getAllLevelHooks(hookMap, cache, type); - if (hooks.length === 0) return forceClone ? items.slice() : items; - let i = 0; - return items.filter((item, idx) => { - for (const hook of hooks) { - const r = fn(hook, item, idx, i); - if (r !== undefined) { - if (r) i++; - return r; + const groupedAssets = factory.create( + `${type}.assets`, + Array.from(assets), + { + ...context, + compilationFileToChunks, + compilationAuxiliaryFileToChunks + } + ); + const limited = spaceLimited(groupedAssets, options.assetsSpace); + object.assets = limited.children; + object.filteredAssets = limited.filteredChildren; + }, + chunks: (object, compilation, context, options, factory) => { + const { type } = context; + object.chunks = factory.create( + `${type}.chunks`, + Array.from(compilation.chunks), + context + ); + }, + modules: (object, compilation, context, options, factory) => { + const { type } = context; + const array = Array.from(compilation.modules); + const groupedModules = factory.create(`${type}.modules`, array, context); + const limited = spaceLimited(groupedModules, options.modulesSpace); + object.modules = limited.children; + object.filteredModules = limited.filteredChildren; + }, + entrypoints: ( + object, + compilation, + context, + { entrypoints, chunkGroups, chunkGroupAuxiliary, chunkGroupChildren }, + factory + ) => { + const { type } = context; + const array = Array.from(compilation.entrypoints, ([key, value]) => ({ + name: key, + chunkGroup: value + })); + if (entrypoints === "auto" && !chunkGroups) { + if (array.length > 5) return; + if ( + !chunkGroupChildren && + array.every(({ chunkGroup }) => { + if (chunkGroup.chunks.length !== 1) return false; + const chunk = chunkGroup.chunks[0]; + return ( + chunk.files.size === 1 && + (!chunkGroupAuxiliary || chunk.auxiliaryFiles.size === 0) + ); + }) + ) { + return; } } - i++; - return true; - }); - } - - /** - * @param {string} type type - * @param {any} data factory data - * @param {Omit} baseContext context used as base - * @returns {any} created object - */ - create(type, data, baseContext) { - if (this._inCreate) { - return this._create(type, data, baseContext); - } else { - try { - this._inCreate = true; - return this._create(type, data, baseContext); - } finally { - for (const key of Object.keys(this._caches)) this._caches[key].clear(); - this._inCreate = false; - } - } - } - - _create(type, data, baseContext) { - const context = { - ...baseContext, - type, - [type]: data - }; - if (Array.isArray(data)) { - // run filter on unsorted items - const items = this._forEachLevelFilter( - this.hooks.filter, - this._caches.filter, - type, - data, - (h, r, idx, i) => h.call(r, context, idx, i), - true + object.entrypoints = factory.create( + `${type}.entrypoints`, + array, + context ); - - // sort items - const comparators = []; - this._forEachLevel(this.hooks.sort, this._caches.sort, type, h => - h.call(comparators, context) + }, + chunkGroups: (object, compilation, context, options, factory) => { + const { type } = context; + const array = Array.from( + compilation.namedChunkGroups, + ([key, value]) => ({ + name: key, + chunkGroup: value + }) ); - if (comparators.length > 0) { - items.sort( - // @ts-expect-error number of arguments is correct - concatComparators(...comparators, keepOriginalOrder(items)) - ); - } - - // run filter on sorted items - const items2 = this._forEachLevelFilter( - this.hooks.filterSorted, - this._caches.filterSorted, - type, - items, - (h, r, idx, i) => h.call(r, context, idx, i), - false + object.namedChunkGroups = factory.create( + `${type}.namedChunkGroups`, + array, + context ); - - // for each item - let resultItems = items2.map((item, i) => { - const itemContext = { - ...context, - _index: i - }; - - // run getItemName - const itemName = this._forEachLevel( - this.hooks.getItemName, - this._caches.getItemName, - `${type}[]`, - h => h.call(item, itemContext) - ); - if (itemName) itemContext[itemName] = item; - const innerType = itemName ? `${type}[].${itemName}` : `${type}[]`; - - // run getItemFactory - const itemFactory = - this._forEachLevel( - this.hooks.getItemFactory, - this._caches.getItemFactory, - innerType, - h => h.call(item, itemContext) - ) || this; - - // run item factory - return itemFactory.create(innerType, item, itemContext); + }, + errors: (object, compilation, context, options, factory) => { + const { type, cachedGetErrors } = context; + object.errors = factory.create( + `${type}.errors`, + cachedGetErrors(compilation), + context + ); + }, + errorsCount: (object, compilation, { cachedGetErrors }) => { + object.errorsCount = countWithChildren(compilation, c => + cachedGetErrors(c) + ); + }, + warnings: (object, compilation, context, options, factory) => { + const { type, cachedGetWarnings } = context; + object.warnings = factory.create( + `${type}.warnings`, + cachedGetWarnings(compilation), + context + ); + }, + warningsCount: ( + object, + compilation, + context, + { warningsFilter }, + factory + ) => { + const { type, cachedGetWarnings } = context; + object.warningsCount = countWithChildren(compilation, (c, childType) => { + if (!warningsFilter && warningsFilter.length === 0) + return cachedGetWarnings(c); + return factory + .create(`${type}${childType}.warnings`, cachedGetWarnings(c), context) + .filter(warning => { + const warningString = Object.keys(warning) + .map(key => `${warning[key]}`) + .join("\n"); + return !warningsFilter.some(filter => + filter(warning, warningString) + ); + }); }); - - // sort result items - const comparators2 = []; - this._forEachLevel( - this.hooks.sortResults, - this._caches.sortResults, - type, - h => h.call(comparators2, context) + }, + errorDetails: ( + object, + compilation, + { cachedGetErrors, cachedGetWarnings }, + { errorDetails, errors, warnings } + ) => { + if (errorDetails === "auto") { + if (warnings) { + const warnings = cachedGetWarnings(compilation); + object.filteredWarningDetailsCount = warnings + .map(e => typeof e !== "string" && e.details) + .filter(Boolean).length; + } + if (errors) { + const errors = cachedGetErrors(compilation); + if (errors.length >= 3) { + object.filteredErrorDetailsCount = errors + .map(e => typeof e !== "string" && e.details) + .filter(Boolean).length; + } + } + } + }, + children: (object, compilation, context, options, factory) => { + const { type } = context; + object.children = factory.create( + `${type}.children`, + compilation.children, + context ); - if (comparators2.length > 0) { - resultItems.sort( - // @ts-expect-error number of arguments is correct - concatComparators(...comparators2, keepOriginalOrder(resultItems)) + } + }, + asset: { + _: (object, asset, context, options, factory) => { + const { compilation } = context; + object.type = asset.type; + object.name = asset.name; + object.size = asset.source.size(); + object.emitted = compilation.emittedAssets.has(asset.name); + object.comparedForEmit = compilation.comparedForEmitAssets.has( + asset.name + ); + const cached = !object.emitted && !object.comparedForEmit; + object.cached = cached; + object.info = asset.info; + if (!cached || options.cachedAssets) { + Object.assign( + object, + factory.create(`${context.type}$visible`, asset, context) ); } - - // group result items - const groupConfigs = []; - this._forEachLevel( - this.hooks.groupResults, - this._caches.groupResults, - type, - h => h.call(groupConfigs, context) + } + }, + asset$visible: { + _: ( + object, + asset, + { compilation, compilationFileToChunks, compilationAuxiliaryFileToChunks } + ) => { + const chunks = compilationFileToChunks.get(asset.name) || []; + const auxiliaryChunks = + compilationAuxiliaryFileToChunks.get(asset.name) || []; + object.chunkNames = uniqueOrderedArray( + chunks, + c => (c.name ? [c.name] : []), + compareIds ); - if (groupConfigs.length > 0) { - resultItems = smartGrouping(resultItems, groupConfigs); - } - - // run filter on sorted result items - const finalResultItems = this._forEachLevelFilter( - this.hooks.filterResults, - this._caches.filterResults, - type, - resultItems, - (h, r, idx, i) => h.call(r, context, idx, i), - false + object.chunkIdHints = uniqueOrderedArray( + chunks, + c => Array.from(c.idNameHints), + compareIds ); - - // run merge on mapped items - let result = this._forEachLevel( - this.hooks.merge, - this._caches.merge, - type, - h => h.call(finalResultItems, context) + object.auxiliaryChunkNames = uniqueOrderedArray( + auxiliaryChunks, + c => (c.name ? [c.name] : []), + compareIds ); - if (result === undefined) result = finalResultItems; - - // run result on merged items - return this._forEachLevelWaterfall( - this.hooks.result, - this._caches.result, - type, - result, - (h, r) => h.call(r, context) + object.auxiliaryChunkIdHints = uniqueOrderedArray( + auxiliaryChunks, + c => Array.from(c.idNameHints), + compareIds ); - } else { - const object = {}; - - // run extract on value - this._forEachLevel(this.hooks.extract, this._caches.extract, type, h => - h.call(object, data, context) + object.filteredRelated = asset.related ? asset.related.length : undefined; + }, + relatedAssets: (object, asset, context, options, factory) => { + const { type } = context; + object.related = factory.create( + `${type.slice(0, -8)}.related`, + asset.related, + context ); - - // run result on extracted object - return this._forEachLevelWaterfall( - this.hooks.result, - this._caches.result, - type, - object, - (h, r) => h.call(r, context) + object.filteredRelated = asset.related + ? asset.related.length - object.related.length + : undefined; + }, + ids: ( + object, + asset, + { compilationFileToChunks, compilationAuxiliaryFileToChunks } + ) => { + const chunks = compilationFileToChunks.get(asset.name) || []; + const auxiliaryChunks = + compilationAuxiliaryFileToChunks.get(asset.name) || []; + object.chunks = uniqueOrderedArray(chunks, c => c.ids, compareIds); + object.auxiliaryChunks = uniqueOrderedArray( + auxiliaryChunks, + c => c.ids, + compareIds ); + }, + performance: (object, asset) => { + object.isOverSizeLimit = SizeLimitsPlugin.isOverSizeLimit(asset.source); } - } -} -module.exports = StatsFactory; - - -/***/ }), - -/***/ 61025: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ - - - -const { HookMap, SyncWaterfallHook, SyncBailHook } = __webpack_require__(34718); - -/** @template T @typedef {import("tapable").AsArray} AsArray */ -/** @typedef {import("tapable").Hook} Hook */ -/** @typedef {import("./DefaultStatsFactoryPlugin").StatsAsset} StatsAsset */ -/** @typedef {import("./DefaultStatsFactoryPlugin").StatsChunk} StatsChunk */ -/** @typedef {import("./DefaultStatsFactoryPlugin").StatsChunkGroup} StatsChunkGroup */ -/** @typedef {import("./DefaultStatsFactoryPlugin").StatsCompilation} StatsCompilation */ -/** @typedef {import("./DefaultStatsFactoryPlugin").StatsModule} StatsModule */ -/** @typedef {import("./DefaultStatsFactoryPlugin").StatsModuleReason} StatsModuleReason */ - -/** - * @typedef {Object} PrintedElement - * @property {string} element - * @property {string} content - */ - -/** - * @typedef {Object} KnownStatsPrinterContext - * @property {string=} type - * @property {StatsCompilation=} compilation - * @property {StatsChunkGroup=} chunkGroup - * @property {StatsAsset=} asset - * @property {StatsModule=} module - * @property {StatsChunk=} chunk - * @property {StatsModuleReason=} moduleReason - * @property {(str: string) => string=} bold - * @property {(str: string) => string=} yellow - * @property {(str: string) => string=} red - * @property {(str: string) => string=} green - * @property {(str: string) => string=} magenta - * @property {(str: string) => string=} cyan - * @property {(file: string, oversize?: boolean) => string=} formatFilename - * @property {(id: string) => string=} formatModuleId - * @property {(id: string, direction?: "parent"|"child"|"sibling") => string=} formatChunkId - * @property {(size: number) => string=} formatSize - * @property {(dateTime: number) => string=} formatDateTime - * @property {(flag: string) => string=} formatFlag - * @property {(time: number, boldQuantity?: boolean) => string=} formatTime - * @property {string=} chunkGroupKind - */ - -/** @typedef {KnownStatsPrinterContext & Record} StatsPrinterContext */ - -class StatsPrinter { - constructor() { - this.hooks = Object.freeze({ - /** @type {HookMap>} */ - sortElements: new HookMap( - () => new SyncBailHook(["elements", "context"]) - ), - /** @type {HookMap>} */ - printElements: new HookMap( - () => new SyncBailHook(["printedElements", "context"]) - ), - /** @type {HookMap>} */ - sortItems: new HookMap(() => new SyncBailHook(["items", "context"])), - /** @type {HookMap>} */ - getItemName: new HookMap(() => new SyncBailHook(["item", "context"])), - /** @type {HookMap>} */ - printItems: new HookMap( - () => new SyncBailHook(["printedItems", "context"]) - ), - /** @type {HookMap>} */ - print: new HookMap(() => new SyncBailHook(["object", "context"])), - /** @type {HookMap>} */ - result: new HookMap(() => new SyncWaterfallHook(["result", "context"])) - }); - /** @type {Map, Map>} */ - this._levelHookCache = new Map(); - this._inPrint = false; - } - - /** - * get all level hooks - * @private - * @template {Hook} T - * @param {HookMap} hookMap HookMap - * @param {string} type type - * @returns {T[]} hooks - */ - _getAllLevelHooks(hookMap, type) { - let cache = /** @type {Map} */ ( - this._levelHookCache.get(hookMap) - ); - if (cache === undefined) { - cache = new Map(); - this._levelHookCache.set(hookMap, cache); - } - const cacheEntry = cache.get(type); - if (cacheEntry !== undefined) { - return cacheEntry; - } - /** @type {T[]} */ - const hooks = []; - const typeParts = type.split("."); - for (let i = 0; i < typeParts.length; i++) { - const hook = hookMap.get(typeParts.slice(i).join(".")); - if (hook) { - hooks.push(hook); - } - } - cache.set(type, hooks); - return hooks; - } - - /** - * Run `fn` for each level - * @private - * @template T - * @template R - * @param {HookMap>} hookMap HookMap - * @param {string} type type - * @param {(hook: SyncBailHook) => R} fn function - * @returns {R} result of `fn` - */ - _forEachLevel(hookMap, type, fn) { - for (const hook of this._getAllLevelHooks(hookMap, type)) { - const result = fn(hook); - if (result !== undefined) return result; - } - } + }, + chunkGroup: { + _: ( + object, + { name, chunkGroup }, + { compilation, compilation: { moduleGraph, chunkGraph } }, + { ids, chunkGroupAuxiliary, chunkGroupChildren, chunkGroupMaxAssets } + ) => { + const children = + chunkGroupChildren && + chunkGroup.getChildrenByOrders(moduleGraph, chunkGraph); + /** + * @param {string} name Name + * @returns {{ name: string, size: number }} Asset object + */ + const toAsset = name => { + const asset = compilation.getAsset(name); + return { + name, + size: asset ? asset.info.size : -1 + }; + }; + /** @type {(total: number, asset: { size: number }) => number} */ + const sizeReducer = (total, { size }) => total + size; + const assets = uniqueArray(chunkGroup.chunks, c => c.files).map(toAsset); + const auxiliaryAssets = uniqueOrderedArray( + chunkGroup.chunks, + c => c.auxiliaryFiles, + compareIds + ).map(toAsset); + const assetsSize = assets.reduce(sizeReducer, 0); + const auxiliaryAssetsSize = auxiliaryAssets.reduce(sizeReducer, 0); + /** @type {KnownStatsChunkGroup} */ + const statsChunkGroup = { + name, + chunks: ids ? chunkGroup.chunks.map(c => c.id) : undefined, + assets: assets.length <= chunkGroupMaxAssets ? assets : undefined, + filteredAssets: + assets.length <= chunkGroupMaxAssets ? 0 : assets.length, + assetsSize, + auxiliaryAssets: + chunkGroupAuxiliary && auxiliaryAssets.length <= chunkGroupMaxAssets + ? auxiliaryAssets + : undefined, + filteredAuxiliaryAssets: + chunkGroupAuxiliary && auxiliaryAssets.length <= chunkGroupMaxAssets + ? 0 + : auxiliaryAssets.length, + auxiliaryAssetsSize, + children: children + ? mapObject(children, groups => + groups.map(group => { + const assets = uniqueArray(group.chunks, c => c.files).map( + toAsset + ); + const auxiliaryAssets = uniqueOrderedArray( + group.chunks, + c => c.auxiliaryFiles, + compareIds + ).map(toAsset); - /** - * Run `fn` for each level - * @private - * @template T - * @param {HookMap>} hookMap HookMap - * @param {string} type type - * @param {AsArray[0]} data data - * @param {(hook: SyncWaterfallHook, data: AsArray[0]) => AsArray[0]} fn function - * @returns {AsArray[0]} result of `fn` - */ - _forEachLevelWaterfall(hookMap, type, data, fn) { - for (const hook of this._getAllLevelHooks(hookMap, type)) { - data = fn(hook, data); + /** @type {KnownStatsChunkGroup} */ + const childStatsChunkGroup = { + name: group.name, + chunks: ids ? group.chunks.map(c => c.id) : undefined, + assets: + assets.length <= chunkGroupMaxAssets ? assets : undefined, + filteredAssets: + assets.length <= chunkGroupMaxAssets ? 0 : assets.length, + auxiliaryAssets: + chunkGroupAuxiliary && + auxiliaryAssets.length <= chunkGroupMaxAssets + ? auxiliaryAssets + : undefined, + filteredAuxiliaryAssets: + chunkGroupAuxiliary && + auxiliaryAssets.length <= chunkGroupMaxAssets + ? 0 + : auxiliaryAssets.length + }; + + return childStatsChunkGroup; + }) + ) + : undefined, + childAssets: children + ? mapObject(children, groups => { + /** @type {Set} */ + const set = new Set(); + for (const group of groups) { + for (const chunk of group.chunks) { + for (const asset of chunk.files) { + set.add(asset); + } + } + } + return Array.from(set); + }) + : undefined + }; + Object.assign(object, statsChunkGroup); + }, + performance: (object, { chunkGroup }) => { + object.isOverSizeLimit = SizeLimitsPlugin.isOverSizeLimit(chunkGroup); } - return data; - } + }, + module: { + _: (object, module, context, options, factory) => { + const { compilation, type } = context; + const built = compilation.builtModules.has(module); + const codeGenerated = compilation.codeGeneratedModules.has(module); + const buildTimeExecuted = + compilation.buildTimeExecutedModules.has(module); + /** @type {{[x: string]: number}} */ + const sizes = {}; + for (const sourceType of module.getSourceTypes()) { + sizes[sourceType] = module.size(sourceType); + } + /** @type {KnownStatsModule} */ + const statsModule = { + type: "module", + moduleType: module.type, + layer: module.layer, + size: module.size(), + sizes, + built, + codeGenerated, + buildTimeExecuted, + cached: !built && !codeGenerated + }; + Object.assign(object, statsModule); - /** - * @param {string} type The type - * @param {Object} object Object to print - * @param {Object=} baseContext The base context - * @returns {string} printed result - */ - print(type, object, baseContext) { - if (this._inPrint) { - return this._print(type, object, baseContext); - } else { - try { - this._inPrint = true; - return this._print(type, object, baseContext); - } finally { - this._levelHookCache.clear(); - this._inPrint = false; + if (built || codeGenerated || options.cachedModules) { + Object.assign( + object, + factory.create(`${type}$visible`, module, context) + ); } } - } - - /** - * @private - * @param {string} type type - * @param {Object} object object - * @param {Object=} baseContext context - * @returns {string} printed result - */ - _print(type, object, baseContext) { - const context = { - ...baseContext, - type, - [type]: object - }; - - let printResult = this._forEachLevel(this.hooks.print, type, hook => - hook.call(object, context) - ); - if (printResult === undefined) { - if (Array.isArray(object)) { - const sortedItems = object.slice(); - this._forEachLevel(this.hooks.sortItems, type, h => - h.call(sortedItems, context) + }, + module$visible: { + _: (object, module, context, { requestShortener }, factory) => { + const { compilation, type, rootModules } = context; + const { moduleGraph } = compilation; + /** @type {Module[]} */ + const path = []; + const issuer = moduleGraph.getIssuer(module); + let current = issuer; + while (current) { + path.push(current); + current = moduleGraph.getIssuer(current); + } + path.reverse(); + const profile = moduleGraph.getProfile(module); + const errors = module.getErrors(); + const errorsCount = errors !== undefined ? countIterable(errors) : 0; + const warnings = module.getWarnings(); + const warningsCount = + warnings !== undefined ? countIterable(warnings) : 0; + /** @type {{[x: string]: number}} */ + const sizes = {}; + for (const sourceType of module.getSourceTypes()) { + sizes[sourceType] = module.size(sourceType); + } + /** @type {KnownStatsModule} */ + const statsModule = { + identifier: module.identifier(), + name: module.readableIdentifier(requestShortener), + nameForCondition: module.nameForCondition(), + index: moduleGraph.getPreOrderIndex(module), + preOrderIndex: moduleGraph.getPreOrderIndex(module), + index2: moduleGraph.getPostOrderIndex(module), + postOrderIndex: moduleGraph.getPostOrderIndex(module), + cacheable: module.buildInfo.cacheable, + optional: module.isOptional(moduleGraph), + orphan: + !type.endsWith("module.modules[].module$visible") && + compilation.chunkGraph.getNumberOfModuleChunks(module) === 0, + dependent: rootModules ? !rootModules.has(module) : undefined, + issuer: issuer && issuer.identifier(), + issuerName: issuer && issuer.readableIdentifier(requestShortener), + issuerPath: + issuer && + factory.create(`${type.slice(0, -8)}.issuerPath`, path, context), + failed: errorsCount > 0, + errors: errorsCount, + warnings: warningsCount + }; + Object.assign(object, statsModule); + if (profile) { + object.profile = factory.create( + `${type.slice(0, -8)}.profile`, + profile, + context ); - const printedItems = sortedItems.map((item, i) => { - const itemContext = { - ...context, - _index: i - }; - const itemName = this._forEachLevel( - this.hooks.getItemName, - `${type}[]`, - h => h.call(item, itemContext) - ); - if (itemName) itemContext[itemName] = item; - return this.print( - itemName ? `${type}[].${itemName}` : `${type}[]`, - item, - itemContext - ); + } + }, + ids: (object, module, { compilation: { chunkGraph, moduleGraph } }) => { + object.id = chunkGraph.getModuleId(module); + const issuer = moduleGraph.getIssuer(module); + object.issuerId = issuer && chunkGraph.getModuleId(issuer); + object.chunks = Array.from( + chunkGraph.getOrderedModuleChunksIterable(module, compareChunksById), + chunk => chunk.id + ); + }, + moduleAssets: (object, module) => { + object.assets = module.buildInfo.assets + ? Object.keys(module.buildInfo.assets) + : []; + }, + reasons: (object, module, context, options, factory) => { + const { + type, + compilation: { moduleGraph } + } = context; + const groupsReasons = factory.create( + `${type.slice(0, -8)}.reasons`, + Array.from(moduleGraph.getIncomingConnections(module)), + context + ); + const limited = spaceLimited(groupsReasons, options.reasonsSpace); + object.reasons = limited.children; + object.filteredReasons = limited.filteredChildren; + }, + usedExports: ( + object, + module, + { runtime, compilation: { moduleGraph } } + ) => { + const usedExports = moduleGraph.getUsedExports(module, runtime); + if (usedExports === null) { + object.usedExports = null; + } else if (typeof usedExports === "boolean") { + object.usedExports = usedExports; + } else { + object.usedExports = Array.from(usedExports); + } + }, + providedExports: (object, module, { compilation: { moduleGraph } }) => { + const providedExports = moduleGraph.getProvidedExports(module); + object.providedExports = Array.isArray(providedExports) + ? providedExports + : null; + }, + optimizationBailout: ( + object, + module, + { compilation: { moduleGraph } }, + { requestShortener } + ) => { + object.optimizationBailout = moduleGraph + .getOptimizationBailout(module) + .map(item => { + if (typeof item === "function") return item(requestShortener); + return item; }); - printResult = this._forEachLevel(this.hooks.printItems, type, h => - h.call(printedItems, context) - ); - if (printResult === undefined) { - const result = printedItems.filter(Boolean); - if (result.length > 0) printResult = result.join("\n"); - } - } else if (object !== null && typeof object === "object") { - const elements = Object.keys(object).filter( - key => object[key] !== undefined - ); - this._forEachLevel(this.hooks.sortElements, type, h => - h.call(elements, context) + }, + depth: (object, module, { compilation: { moduleGraph } }) => { + object.depth = moduleGraph.getDepth(module); + }, + nestedModules: (object, module, context, options, factory) => { + const { type } = context; + const innerModules = /** @type {Module & { modules?: Module[] }} */ ( + module + ).modules; + if (Array.isArray(innerModules)) { + const groupedModules = factory.create( + `${type.slice(0, -8)}.modules`, + innerModules, + context ); - const printedElements = elements.map(element => { - const content = this.print(`${type}.${element}`, object[element], { - ...context, - _parent: object, - _element: element, - [element]: object[element] - }); - return { element, content }; - }); - printResult = this._forEachLevel(this.hooks.printElements, type, h => - h.call(printedElements, context) + const limited = spaceLimited( + groupedModules, + options.nestedModulesSpace ); - if (printResult === undefined) { - const result = printedElements.map(e => e.content).filter(Boolean); - if (result.length > 0) printResult = result.join("\n"); - } + object.modules = limited.children; + object.filteredModules = limited.filteredChildren; + } + }, + source: (object, module) => { + const originalSource = module.originalSource(); + if (originalSource) { + object.source = originalSource.source(); } } - - return this._forEachLevelWaterfall( - this.hooks.result, - type, - printResult, - (h, r) => h.call(r, context) - ); - } -} -module.exports = StatsPrinter; - - -/***/ }), - -/***/ 21537: -/***/ (function(__unused_webpack_module, exports) { - -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ - - - -exports.equals = (a, b) => { - if (a.length !== b.length) return false; - for (let i = 0; i < a.length; i++) { - if (a[i] !== b[i]) return false; - } - return true; -}; - -/** - * - * @param {Array} arr Array of values to be partitioned - * @param {(value: any) => boolean} fn Partition function which partitions based on truthiness of result. - * @returns {[Array, Array]} returns the values of `arr` partitioned into two new arrays based on fn predicate. - */ -exports.groupBy = (arr = [], fn) => { - return arr.reduce( - (groups, value) => { - groups[fn(value) ? 0 : 1].push(value); - return groups; + }, + profile: { + _: (object, profile) => { + /** @type {KnownStatsProfile} */ + const statsProfile = { + total: + profile.factory + + profile.restoring + + profile.integration + + profile.building + + profile.storing, + resolving: profile.factory, + restoring: profile.restoring, + building: profile.building, + integration: profile.integration, + storing: profile.storing, + additionalResolving: profile.additionalFactories, + additionalIntegration: profile.additionalIntegration, + // TODO remove this in webpack 6 + factory: profile.factory, + // TODO remove this in webpack 6 + dependencies: profile.additionalFactories + }; + Object.assign(object, statsProfile); + } + }, + moduleIssuer: { + _: (object, module, context, { requestShortener }, factory) => { + const { compilation, type } = context; + const { moduleGraph } = compilation; + const profile = moduleGraph.getProfile(module); + /** @type {KnownStatsModuleIssuer} */ + const statsModuleIssuer = { + identifier: module.identifier(), + name: module.readableIdentifier(requestShortener) + }; + Object.assign(object, statsModuleIssuer); + if (profile) { + object.profile = factory.create(`${type}.profile`, profile, context); + } }, - [[], []] - ); -}; - - -/***/ }), - -/***/ 29704: -/***/ (function(module) { - -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ - - - -/** - * @template T - */ -class ArrayQueue { - /** - * @param {Iterable=} items The initial elements. - */ - constructor(items) { - /** @private @type {T[]} */ - this._list = items ? Array.from(items) : []; - /** @private @type {T[]} */ - this._listReversed = []; - } - - /** - * Returns the number of elements in this queue. - * @returns {number} The number of elements in this queue. - */ - get length() { - return this._list.length + this._listReversed.length; - } - - /** - * Empties the queue. - */ - clear() { - this._list.length = 0; - this._listReversed.length = 0; - } - - /** - * Appends the specified element to this queue. - * @param {T} item The element to add. - * @returns {void} - */ - enqueue(item) { - this._list.push(item); - } - - /** - * Retrieves and removes the head of this queue. - * @returns {T | undefined} The head of the queue of `undefined` if this queue is empty. - */ - dequeue() { - if (this._listReversed.length === 0) { - if (this._list.length === 0) return undefined; - if (this._list.length === 1) return this._list.pop(); - if (this._list.length < 16) return this._list.shift(); - const temp = this._listReversed; - this._listReversed = this._list; - this._listReversed.reverse(); - this._list = temp; + ids: (object, module, { compilation: { chunkGraph } }) => { + object.id = chunkGraph.getModuleId(module); + } + }, + moduleReason: { + _: (object, reason, { runtime }, { requestShortener }) => { + const dep = reason.dependency; + const moduleDep = + dep && dep instanceof ModuleDependency ? dep : undefined; + /** @type {KnownStatsModuleReason} */ + const statsModuleReason = { + moduleIdentifier: reason.originModule + ? reason.originModule.identifier() + : null, + module: reason.originModule + ? reason.originModule.readableIdentifier(requestShortener) + : null, + moduleName: reason.originModule + ? reason.originModule.readableIdentifier(requestShortener) + : null, + resolvedModuleIdentifier: reason.resolvedOriginModule + ? reason.resolvedOriginModule.identifier() + : null, + resolvedModule: reason.resolvedOriginModule + ? reason.resolvedOriginModule.readableIdentifier(requestShortener) + : null, + type: reason.dependency ? reason.dependency.type : null, + active: reason.isActive(runtime), + explanation: reason.explanation, + userRequest: (moduleDep && moduleDep.userRequest) || null + }; + Object.assign(object, statsModuleReason); + if (reason.dependency) { + const locInfo = formatLocation(reason.dependency.loc); + if (locInfo) { + object.loc = locInfo; + } + } + }, + ids: (object, reason, { compilation: { chunkGraph } }) => { + object.moduleId = reason.originModule + ? chunkGraph.getModuleId(reason.originModule) + : null; + object.resolvedModuleId = reason.resolvedOriginModule + ? chunkGraph.getModuleId(reason.resolvedOriginModule) + : null; } - return this._listReversed.pop(); - } + }, + chunk: { + _: (object, chunk, { makePathsRelative, compilation: { chunkGraph } }) => { + const childIdByOrder = chunk.getChildIdsByOrders(chunkGraph); - /** - * Finds and removes an item - * @param {T} item the item - * @returns {void} - */ - delete(item) { - const i = this._list.indexOf(item); - if (i >= 0) { - this._list.splice(i, 1); - } else { - const i = this._listReversed.indexOf(item); - if (i >= 0) this._listReversed.splice(i, 1); - } - } + /** @type {KnownStatsChunk} */ + const statsChunk = { + rendered: chunk.rendered, + initial: chunk.canBeInitial(), + entry: chunk.hasRuntime(), + recorded: AggressiveSplittingPlugin.wasChunkRecorded(chunk), + reason: chunk.chunkReason, + size: chunkGraph.getChunkModulesSize(chunk), + sizes: chunkGraph.getChunkModulesSizes(chunk), + names: chunk.name ? [chunk.name] : [], + idHints: Array.from(chunk.idNameHints), + runtime: + chunk.runtime === undefined + ? undefined + : typeof chunk.runtime === "string" + ? [makePathsRelative(chunk.runtime)] + : Array.from(chunk.runtime.sort(), makePathsRelative), + files: Array.from(chunk.files), + auxiliaryFiles: Array.from(chunk.auxiliaryFiles).sort(compareIds), + hash: chunk.renderedHash, + childrenByOrder: childIdByOrder + }; + Object.assign(object, statsChunk); + }, + ids: (object, chunk) => { + object.id = chunk.id; + }, + chunkRelations: (object, chunk, { compilation: { chunkGraph } }) => { + /** @type {Set} */ + const parents = new Set(); + /** @type {Set} */ + const children = new Set(); + /** @type {Set} */ + const siblings = new Set(); - [Symbol.iterator]() { - let i = -1; - let reversed = false; - return { - next: () => { - if (!reversed) { - i++; - if (i < this._list.length) { - return { - done: false, - value: this._list[i] - }; + for (const chunkGroup of chunk.groupsIterable) { + for (const parentGroup of chunkGroup.parentsIterable) { + for (const chunk of parentGroup.chunks) { + parents.add(chunk.id); } - reversed = true; - i = this._listReversed.length; } - i--; - if (i < 0) { - return { - done: true, - value: undefined - }; + for (const childGroup of chunkGroup.childrenIterable) { + for (const chunk of childGroup.chunks) { + children.add(chunk.id); + } + } + for (const sibling of chunkGroup.chunks) { + if (sibling !== chunk) siblings.add(sibling.id); } - return { - done: false, - value: this._listReversed[i] - }; } - }; - } -} - -module.exports = ArrayQueue; - - -/***/ }), - -/***/ 55531: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ - - - -const { SyncHook, AsyncSeriesHook } = __webpack_require__(34718); -const { makeWebpackError } = __webpack_require__(89935); -const WebpackError = __webpack_require__(68422); -const ArrayQueue = __webpack_require__(29704); - -const QUEUED_STATE = 0; -const PROCESSING_STATE = 1; -const DONE_STATE = 2; - -let inHandleResult = 0; - -/** - * @template T - * @callback Callback - * @param {WebpackError=} err - * @param {T=} result - */ - -/** - * @template T - * @template K - * @template R - */ -class AsyncQueueEntry { - /** - * @param {T} item the item - * @param {Callback} callback the callback - */ - constructor(item, callback) { - this.item = item; - /** @type {typeof QUEUED_STATE | typeof PROCESSING_STATE | typeof DONE_STATE} */ - this.state = QUEUED_STATE; - this.callback = callback; - /** @type {Callback[] | undefined} */ - this.callbacks = undefined; - this.result = undefined; - /** @type {WebpackError | undefined} */ - this.error = undefined; + object.siblings = Array.from(siblings).sort(compareIds); + object.parents = Array.from(parents).sort(compareIds); + object.children = Array.from(children).sort(compareIds); + }, + chunkModules: (object, chunk, context, options, factory) => { + const { + type, + compilation: { chunkGraph } + } = context; + const array = chunkGraph.getChunkModules(chunk); + const groupedModules = factory.create(`${type}.modules`, array, { + ...context, + runtime: chunk.runtime, + rootModules: new Set(chunkGraph.getChunkRootModules(chunk)) + }); + const limited = spaceLimited(groupedModules, options.chunkModulesSpace); + object.modules = limited.children; + object.filteredModules = limited.filteredChildren; + }, + chunkOrigins: (object, chunk, context, options, factory) => { + const { + type, + compilation: { chunkGraph } + } = context; + /** @type {Set} */ + const originsKeySet = new Set(); + const origins = []; + for (const g of chunk.groupsIterable) { + origins.push(...g.origins); + } + const array = origins.filter(origin => { + const key = [ + origin.module ? chunkGraph.getModuleId(origin.module) : undefined, + formatLocation(origin.loc), + origin.request + ].join(); + if (originsKeySet.has(key)) return false; + originsKeySet.add(key); + return true; + }); + object.origins = factory.create(`${type}.origins`, array, context); + } + }, + chunkOrigin: { + _: (object, origin, context, { requestShortener }) => { + /** @type {KnownStatsChunkOrigin} */ + const statsChunkOrigin = { + module: origin.module ? origin.module.identifier() : "", + moduleIdentifier: origin.module ? origin.module.identifier() : "", + moduleName: origin.module + ? origin.module.readableIdentifier(requestShortener) + : "", + loc: formatLocation(origin.loc), + request: origin.request + }; + Object.assign(object, statsChunkOrigin); + }, + ids: (object, origin, { compilation: { chunkGraph } }) => { + object.moduleId = origin.module + ? chunkGraph.getModuleId(origin.module) + : undefined; + } + }, + error: EXTRACT_ERROR, + warning: EXTRACT_ERROR, + moduleTraceItem: { + _: (object, { origin, module }, context, { requestShortener }, factory) => { + const { + type, + compilation: { moduleGraph } + } = context; + object.originIdentifier = origin.identifier(); + object.originName = origin.readableIdentifier(requestShortener); + object.moduleIdentifier = module.identifier(); + object.moduleName = module.readableIdentifier(requestShortener); + const dependencies = Array.from( + moduleGraph.getIncomingConnections(module) + ) + .filter(c => c.resolvedOriginModule === origin && c.dependency) + .map(c => c.dependency); + object.dependencies = factory.create( + `${type}.dependencies`, + Array.from(new Set(dependencies)), + context + ); + }, + ids: (object, { origin, module }, { compilation: { chunkGraph } }) => { + object.originId = chunkGraph.getModuleId(origin); + object.moduleId = chunkGraph.getModuleId(module); + } + }, + moduleTraceDependency: { + _: (object, dependency) => { + object.loc = formatLocation(dependency.loc); + } } -} +}; -/** - * @template T - * @template K - * @template R - */ -class AsyncQueue { - /** - * @param {Object} options options object - * @param {string=} options.name name of the queue - * @param {number=} options.parallelism how many items should be processed at once - * @param {AsyncQueue=} options.parent parent queue, which will have priority over this queue and with shared parallelism - * @param {function(T): K=} options.getKey extract key from item - * @param {function(T, Callback): void} options.processor async function to process items - */ - constructor({ name, parallelism, parent, processor, getKey }) { - this._name = name; - this._parallelism = parallelism || 1; - this._processor = processor; - this._getKey = - getKey || /** @type {(T) => K} */ (item => /** @type {any} */ (item)); - /** @type {Map>} */ - this._entries = new Map(); - /** @type {ArrayQueue>} */ - this._queued = new ArrayQueue(); - /** @type {AsyncQueue[]} */ - this._children = undefined; - this._activeTasks = 0; - this._willEnsureProcessing = false; - this._needProcessing = false; - this._stopped = false; - this._root = parent ? parent._root : this; - if (parent) { - if (this._root._children === undefined) { - this._root._children = [this]; - } else { - this._root._children.push(this); +/** @type {Record boolean | undefined>>} */ +const FILTER = { + "module.reasons": { + "!orphanModules": (reason, { compilation: { chunkGraph } }) => { + if ( + reason.originModule && + chunkGraph.getNumberOfModuleChunks(reason.originModule) === 0 + ) { + return false; } } - - this.hooks = { - /** @type {AsyncSeriesHook<[T]>} */ - beforeAdd: new AsyncSeriesHook(["item"]), - /** @type {SyncHook<[T]>} */ - added: new SyncHook(["item"]), - /** @type {AsyncSeriesHook<[T]>} */ - beforeStart: new AsyncSeriesHook(["item"]), - /** @type {SyncHook<[T]>} */ - started: new SyncHook(["item"]), - /** @type {SyncHook<[T, Error, R]>} */ - result: new SyncHook(["item", "error", "result"]) - }; - - this._ensureProcessing = this._ensureProcessing.bind(this); } +}; - /** - * @param {T} item an item - * @param {Callback} callback callback function - * @returns {void} - */ - add(item, callback) { - if (this._stopped) return callback(new WebpackError("Queue was stopped")); - this.hooks.beforeAdd.callAsync(item, err => { - if (err) { - callback( - makeWebpackError(err, `AsyncQueue(${this._name}).hooks.beforeAdd`) - ); - return; - } - const key = this._getKey(item); - const entry = this._entries.get(key); - if (entry !== undefined) { - if (entry.state === DONE_STATE) { - if (inHandleResult++ > 3) { - process.nextTick(() => callback(entry.error, entry.result)); - } else { - callback(entry.error, entry.result); - } - inHandleResult--; - } else if (entry.callbacks === undefined) { - entry.callbacks = [callback]; - } else { - entry.callbacks.push(callback); - } - return; - } - const newEntry = new AsyncQueueEntry(item, callback); - if (this._stopped) { - this.hooks.added.call(item); - this._root._activeTasks++; - process.nextTick(() => - this._handleResult(newEntry, new WebpackError("Queue was stopped")) - ); - } else { - this._entries.set(key, newEntry); - this._queued.enqueue(newEntry); - const root = this._root; - root._needProcessing = true; - if (root._willEnsureProcessing === false) { - root._willEnsureProcessing = true; - setImmediate(root._ensureProcessing); - } - this.hooks.added.call(item); - } - }); +/** @type {Record boolean | undefined>>} */ +const FILTER_RESULTS = { + "compilation.warnings": { + warningsFilter: util.deprecate( + (warning, context, { warningsFilter }) => { + const warningString = Object.keys(warning) + .map(key => `${warning[key]}`) + .join("\n"); + return !warningsFilter.some(filter => filter(warning, warningString)); + }, + "config.stats.warningsFilter is deprecated in favor of config.ignoreWarnings", + "DEP_WEBPACK_STATS_WARNINGS_FILTER" + ) } +}; - /** - * @param {T} item an item - * @returns {void} - */ - invalidate(item) { - const key = this._getKey(item); - const entry = this._entries.get(key); - this._entries.delete(key); - if (entry.state === QUEUED_STATE) { - this._queued.delete(entry); - } +/** @type {Record void>} */ +const MODULES_SORTER = { + _: (comparators, { compilation: { moduleGraph } }) => { + comparators.push( + compareSelect( + /** + * @param {Module} m module + * @returns {number} depth + */ + m => moduleGraph.getDepth(m), + compareNumbers + ), + compareSelect( + /** + * @param {Module} m module + * @returns {number} index + */ + m => moduleGraph.getPreOrderIndex(m), + compareNumbers + ), + compareSelect( + /** + * @param {Module} m module + * @returns {string} identifier + */ + m => m.identifier(), + compareIds + ) + ); } +}; - /** - * Waits for an already started item - * @param {T} item an item - * @param {Callback} callback callback function - * @returns {void} - */ - waitFor(item, callback) { - const key = this._getKey(item); - const entry = this._entries.get(key); - if (entry === undefined) { - return callback( - new WebpackError( - "waitFor can only be called for an already started item" +/** @type {Record void>>} */ +const SORTERS = { + "compilation.chunks": { + _: comparators => { + comparators.push(compareSelect(c => c.id, compareIds)); + } + }, + "compilation.modules": MODULES_SORTER, + "chunk.rootModules": MODULES_SORTER, + "chunk.modules": MODULES_SORTER, + "module.modules": MODULES_SORTER, + "module.reasons": { + _: (comparators, { compilation: { chunkGraph } }) => { + comparators.push( + compareSelect(x => x.originModule, compareModulesByIdentifier) + ); + comparators.push( + compareSelect(x => x.resolvedOriginModule, compareModulesByIdentifier) + ); + comparators.push( + compareSelect( + x => x.dependency, + concatComparators( + compareSelect( + /** + * @param {Dependency} x dependency + * @returns {DependencyLocation} location + */ + x => x.loc, + compareLocations + ), + compareSelect(x => x.type, compareIds) + ) ) ); } - if (entry.state === DONE_STATE) { - process.nextTick(() => callback(entry.error, entry.result)); - } else if (entry.callbacks === undefined) { - entry.callbacks = [callback]; + }, + "chunk.origins": { + _: (comparators, { compilation: { chunkGraph } }) => { + comparators.push( + compareSelect( + origin => + origin.module ? chunkGraph.getModuleId(origin.module) : undefined, + compareIds + ), + compareSelect(origin => formatLocation(origin.loc), compareIds), + compareSelect(origin => origin.request, compareIds) + ); + } + } +}; + +const getItemSize = item => { + // Each item takes 1 line + // + the size of the children + // + 1 extra line when it has children and filteredChildren + return !item.children + ? 1 + : item.filteredChildren + ? 2 + getTotalSize(item.children) + : 1 + getTotalSize(item.children); +}; + +const getTotalSize = children => { + let size = 0; + for (const child of children) { + size += getItemSize(child); + } + return size; +}; + +const getTotalItems = children => { + let count = 0; + for (const child of children) { + if (!child.children && !child.filteredChildren) { + count++; } else { - entry.callbacks.push(callback); + if (child.children) count += getTotalItems(child.children); + if (child.filteredChildren) count += child.filteredChildren; } } + return count; +}; - /** - * @returns {void} - */ - stop() { - this._stopped = true; - const queue = this._queued; - this._queued = new ArrayQueue(); - const root = this._root; - for (const entry of queue) { - this._entries.delete(this._getKey(entry.item)); - root._activeTasks++; - this._handleResult(entry, new WebpackError("Queue was stopped")); +const collapse = children => { + // After collapse each child must take exactly one line + const newChildren = []; + for (const child of children) { + if (child.children) { + let filteredChildren = child.filteredChildren || 0; + filteredChildren += getTotalItems(child.children); + newChildren.push({ + ...child, + children: undefined, + filteredChildren + }); + } else { + newChildren.push(child); } } + return newChildren; +}; - /** - * @returns {void} - */ - increaseParallelism() { - const root = this._root; - root._parallelism++; - /* istanbul ignore next */ - if (root._willEnsureProcessing === false && root._needProcessing) { - root._willEnsureProcessing = true; - setImmediate(root._ensureProcessing); +const spaceLimited = (itemsAndGroups, max) => { + /** @type {any[] | undefined} */ + let children = undefined; + /** @type {number | undefined} */ + let filteredChildren = undefined; + // This are the groups, which take 1+ lines each + const groups = itemsAndGroups.filter(c => c.children || c.filteredChildren); + // The sizes of the groups are stored in groupSizes + const groupSizes = groups.map(g => getItemSize(g)); + // This are the items, which take 1 line each + const items = itemsAndGroups.filter(c => !c.children && !c.filteredChildren); + // The total of group sizes + let groupsSize = groupSizes.reduce((a, b) => a + b, 0); + if (groupsSize + items.length <= max) { + // The total size in the current state fits into the max + // keep all + children = groups.concat(items); + } else if ( + groups.length > 0 && + groups.length + Math.min(1, items.length) < max + ) { + // If each group would take 1 line the total would be below the maximum + // collapse some groups, keep items + while (groupsSize + items.length + (filteredChildren ? 1 : 0) > max) { + // calculate how much we are over the size limit + // this allows to approach the limit faster + // it's always > 1 + const oversize = + items.length + groupsSize + (filteredChildren ? 1 : 0) - max; + // Find the maximum group and process only this one + const maxGroupSize = Math.max(...groupSizes); + if (maxGroupSize < items.length) { + filteredChildren = items.length; + items.length = 0; + continue; + } + for (let i = 0; i < groups.length; i++) { + if (groupSizes[i] === maxGroupSize) { + const group = groups[i]; + // run this algorithm recursively and limit the size of the children to + // current size - oversize / number of groups + // So it should always end up being smaller + const headerSize = !group.children + ? 0 + : group.filteredChildren + ? 2 + : 1; + const limited = spaceLimited( + group.children, + groupSizes[i] - headerSize - oversize / groups.length + ); + groups[i] = { + ...group, + children: limited.children, + filteredChildren: + (group.filteredChildren || 0) + limited.filteredChildren + }; + const newSize = getItemSize(groups[i]); + groupsSize -= groupSizes[i] - newSize; + groupSizes[i] = newSize; + break; + } + } } + children = groups.concat(items); + } else if ( + groups.length > 0 && + groups.length + Math.min(1, items.length) <= max + ) { + // If we have only enough space to show one line per group and one line for the filtered items + // collapse all groups and items + children = groups.length ? collapse(groups) : undefined; + filteredChildren = items.length; + } else { + // If we have no space + // collapse complete group + filteredChildren = getTotalItems(itemsAndGroups); } + return { + children, + filteredChildren + }; +}; - /** - * @returns {void} - */ - decreaseParallelism() { - const root = this._root; - root._parallelism--; - } - - /** - * @param {T} item an item - * @returns {boolean} true, if the item is currently being processed - */ - isProcessing(item) { - const key = this._getKey(item); - const entry = this._entries.get(key); - return entry !== undefined && entry.state === PROCESSING_STATE; +const assetGroup = (children, assets) => { + let size = 0; + for (const asset of children) { + size += asset.size; } + return { + size + }; +}; - /** - * @param {T} item an item - * @returns {boolean} true, if the item is currently queued - */ - isQueued(item) { - const key = this._getKey(item); - const entry = this._entries.get(key); - return entry !== undefined && entry.state === QUEUED_STATE; +const moduleGroup = (children, modules) => { + let size = 0; + const sizes = {}; + for (const module of children) { + size += module.size; + for (const key of Object.keys(module.sizes)) { + sizes[key] = (sizes[key] || 0) + module.sizes[key]; + } } + return { + size, + sizes + }; +}; - /** - * @param {T} item an item - * @returns {boolean} true, if the item is currently queued - */ - isDone(item) { - const key = this._getKey(item); - const entry = this._entries.get(key); - return entry !== undefined && entry.state === DONE_STATE; +const reasonGroup = (children, reasons) => { + let active = false; + for (const reason of children) { + active = active || reason.active; } + return { + active + }; +}; - /** - * @returns {void} - */ - _ensureProcessing() { - while (this._activeTasks < this._parallelism) { - const entry = this._queued.dequeue(); - if (entry === undefined) break; - this._activeTasks++; - entry.state = PROCESSING_STATE; - this._startProcessing(entry); +/** @type {Record void>} */ +const ASSETS_GROUPERS = { + _: (groupConfigs, context, options) => { + const groupByFlag = (name, exclude) => { + groupConfigs.push({ + getKeys: asset => { + return asset[name] ? ["1"] : undefined; + }, + getOptions: () => { + return { + groupChildren: !exclude, + force: exclude + }; + }, + createGroup: (key, children, assets) => { + return exclude + ? { + type: "assets by status", + [name]: !!key, + filteredChildren: assets.length, + ...assetGroup(children, assets) + } + : { + type: "assets by status", + [name]: !!key, + children, + ...assetGroup(children, assets) + }; + } + }); + }; + const { + groupAssetsByEmitStatus, + groupAssetsByPath, + groupAssetsByExtension + } = options; + if (groupAssetsByEmitStatus) { + groupByFlag("emitted"); + groupByFlag("comparedForEmit"); + groupByFlag("isOverSizeLimit"); } - this._willEnsureProcessing = false; - if (this._queued.length > 0) return; - if (this._children !== undefined) { - for (const child of this._children) { - while (this._activeTasks < this._parallelism) { - const entry = child._queued.dequeue(); - if (entry === undefined) break; - this._activeTasks++; - entry.state = PROCESSING_STATE; - child._startProcessing(entry); + if (groupAssetsByEmitStatus || !options.cachedAssets) { + groupByFlag("cached", !options.cachedAssets); + } + if (groupAssetsByPath || groupAssetsByExtension) { + groupConfigs.push({ + getKeys: asset => { + const extensionMatch = + groupAssetsByExtension && /(\.[^.]+)(?:\?.*|$)/.exec(asset.name); + const extension = extensionMatch ? extensionMatch[1] : ""; + const pathMatch = + groupAssetsByPath && /(.+)[/\\][^/\\]+(?:\?.*|$)/.exec(asset.name); + const path = pathMatch ? pathMatch[1].split(/[/\\]/) : []; + const keys = []; + if (groupAssetsByPath) { + keys.push("."); + if (extension) + keys.push( + path.length + ? `${path.join("/")}/*${extension}` + : `*${extension}` + ); + while (path.length > 0) { + keys.push(path.join("/") + "/"); + path.pop(); + } + } else { + if (extension) keys.push(`*${extension}`); + } + return keys; + }, + createGroup: (key, children, assets) => { + return { + type: groupAssetsByPath ? "assets by path" : "assets by extension", + name: key, + children, + ...assetGroup(children, assets) + }; } - if (child._queued.length > 0) return; - } + }); } - if (!this._willEnsureProcessing) this._needProcessing = false; - } - - /** - * @param {AsyncQueueEntry} entry the entry - * @returns {void} - */ - _startProcessing(entry) { - this.hooks.beforeStart.callAsync(entry.item, err => { - if (err) { - this._handleResult( - entry, - makeWebpackError(err, `AsyncQueue(${this._name}).hooks.beforeStart`) - ); - return; - } - let inCallback = false; - try { - this._processor(entry.item, (e, r) => { - inCallback = true; - this._handleResult(entry, e, r); - }); - } catch (err) { - if (inCallback) throw err; - this._handleResult(entry, err, null); - } - this.hooks.started.call(entry.item); + }, + groupAssetsByInfo: (groupConfigs, context, options) => { + const groupByAssetInfoFlag = name => { + groupConfigs.push({ + getKeys: asset => { + return asset.info && asset.info[name] ? ["1"] : undefined; + }, + createGroup: (key, children, assets) => { + return { + type: "assets by info", + info: { + [name]: !!key + }, + children, + ...assetGroup(children, assets) + }; + } + }); + }; + groupByAssetInfoFlag("immutable"); + groupByAssetInfoFlag("development"); + groupByAssetInfoFlag("hotModuleReplacement"); + }, + groupAssetsByChunk: (groupConfigs, context, options) => { + const groupByNames = name => { + groupConfigs.push({ + getKeys: asset => { + return asset[name]; + }, + createGroup: (key, children, assets) => { + return { + type: "assets by chunk", + [name]: [key], + children, + ...assetGroup(children, assets) + }; + } + }); + }; + groupByNames("chunkNames"); + groupByNames("auxiliaryChunkNames"); + groupByNames("chunkIdHints"); + groupByNames("auxiliaryChunkIdHints"); + }, + excludeAssets: (groupConfigs, context, { excludeAssets }) => { + groupConfigs.push({ + getKeys: asset => { + const ident = asset.name; + const excluded = excludeAssets.some(fn => fn(ident, asset)); + if (excluded) return ["excluded"]; + }, + getOptions: () => ({ + groupChildren: false, + force: true + }), + createGroup: (key, children, assets) => ({ + type: "hidden assets", + filteredChildren: assets.length, + ...assetGroup(children, assets) + }) }); } +}; - /** - * @param {AsyncQueueEntry} entry the entry - * @param {WebpackError=} err error, if any - * @param {R=} result result, if any - * @returns {void} - */ - _handleResult(entry, err, result) { - this.hooks.result.callAsync(entry.item, err, result, hookError => { - const error = hookError - ? makeWebpackError(hookError, `AsyncQueue(${this._name}).hooks.result`) - : err; - - const callback = entry.callback; - const callbacks = entry.callbacks; - entry.state = DONE_STATE; - entry.callback = undefined; - entry.callbacks = undefined; - entry.result = result; - entry.error = error; - - const root = this._root; - root._activeTasks--; - if (root._willEnsureProcessing === false && root._needProcessing) { - root._willEnsureProcessing = true; - setImmediate(root._ensureProcessing); - } - - if (inHandleResult++ > 3) { - process.nextTick(() => { - callback(error, result); - if (callbacks !== undefined) { - for (const callback of callbacks) { - callback(error, result); +/** @type {function("module" | "chunk" | "root-of-chunk" | "nested"): Record void>} */ +const MODULES_GROUPERS = type => ({ + _: (groupConfigs, context, options) => { + const groupByFlag = (name, type, exclude) => { + groupConfigs.push({ + getKeys: module => { + return module[name] ? ["1"] : undefined; + }, + getOptions: () => { + return { + groupChildren: !exclude, + force: exclude + }; + }, + createGroup: (key, children, modules) => { + return { + type, + [name]: !!key, + ...(exclude ? { filteredChildren: modules.length } : { children }), + ...moduleGroup(children, modules) + }; + } + }); + }; + const { + groupModulesByCacheStatus, + groupModulesByLayer, + groupModulesByAttributes, + groupModulesByType, + groupModulesByPath, + groupModulesByExtension + } = options; + if (groupModulesByAttributes) { + groupByFlag("errors", "modules with errors"); + groupByFlag("warnings", "modules with warnings"); + groupByFlag("assets", "modules with assets"); + groupByFlag("optional", "optional modules"); + } + if (groupModulesByCacheStatus) { + groupByFlag("cacheable", "cacheable modules"); + groupByFlag("built", "built modules"); + groupByFlag("codeGenerated", "code generated modules"); + } + if (groupModulesByCacheStatus || !options.cachedModules) { + groupByFlag("cached", "cached modules", !options.cachedModules); + } + if (groupModulesByAttributes || !options.orphanModules) { + groupByFlag("orphan", "orphan modules", !options.orphanModules); + } + if (groupModulesByAttributes || !options.dependentModules) { + groupByFlag("dependent", "dependent modules", !options.dependentModules); + } + if (groupModulesByType || !options.runtimeModules) { + groupConfigs.push({ + getKeys: module => { + if (!module.moduleType) return; + if (groupModulesByType) { + return [module.moduleType.split("/", 1)[0]]; + } else if (module.moduleType === "runtime") { + return ["runtime"]; + } + }, + getOptions: key => { + const exclude = key === "runtime" && !options.runtimeModules; + return { + groupChildren: !exclude, + force: exclude + }; + }, + createGroup: (key, children, modules) => { + const exclude = key === "runtime" && !options.runtimeModules; + return { + type: `${key} modules`, + moduleType: key, + ...(exclude ? { filteredChildren: modules.length } : { children }), + ...moduleGroup(children, modules) + }; + } + }); + } + if (groupModulesByLayer) { + groupConfigs.push({ + getKeys: module => { + return [module.layer]; + }, + createGroup: (key, children, modules) => { + return { + type: "modules by layer", + layer: key, + children, + ...moduleGroup(children, modules) + }; + } + }); + } + if (groupModulesByPath || groupModulesByExtension) { + groupConfigs.push({ + getKeys: module => { + if (!module.name) return; + const resource = parseResource(module.name.split("!").pop()).path; + const extensionMatch = + groupModulesByExtension && /(\.[^.]+)(?:\?.*|$)/.exec(resource); + const extension = extensionMatch ? extensionMatch[1] : ""; + const pathMatch = + groupModulesByPath && /(.+)[/\\][^/\\]+(?:\?.*|$)/.exec(resource); + const path = pathMatch ? pathMatch[1].split(/[/\\]/) : []; + const keys = []; + if (groupModulesByPath) { + if (extension) + keys.push( + path.length + ? `${path.join("/")}/*${extension}` + : `*${extension}` + ); + while (path.length > 0) { + keys.push(path.join("/") + "/"); + path.pop(); } + } else { + if (extension) keys.push(`*${extension}`); } - }); - } else { - callback(error, result); - if (callbacks !== undefined) { - for (const callback of callbacks) { - callback(error, result); - } + return keys; + }, + createGroup: (key, children, modules) => { + return { + type: groupModulesByPath + ? "modules by path" + : "modules by extension", + name: key, + children, + ...moduleGroup(children, modules) + }; } - } - inHandleResult--; + }); + } + }, + excludeModules: (groupConfigs, context, { excludeModules }) => { + groupConfigs.push({ + getKeys: module => { + const name = module.name; + if (name) { + const excluded = excludeModules.some(fn => fn(name, module, type)); + if (excluded) return ["1"]; + } + }, + getOptions: () => ({ + groupChildren: false, + force: true + }), + createGroup: (key, children, modules) => ({ + type: "hidden modules", + filteredChildren: children.length, + ...moduleGroup(children, modules) + }) }); } +}); - clear() { - this._entries.clear(); - this._queued.clear(); - this._activeTasks = 0; - this._willEnsureProcessing = false; - this._needProcessing = false; - this._stopped = false; +/** @type {Record void>>} */ +const RESULT_GROUPERS = { + "compilation.assets": ASSETS_GROUPERS, + "asset.related": ASSETS_GROUPERS, + "compilation.modules": MODULES_GROUPERS("module"), + "chunk.modules": MODULES_GROUPERS("chunk"), + "chunk.rootModules": MODULES_GROUPERS("root-of-chunk"), + "module.modules": MODULES_GROUPERS("nested"), + "module.reasons": { + groupReasonsByOrigin: groupConfigs => { + groupConfigs.push({ + getKeys: reason => { + return [reason.module]; + }, + createGroup: (key, children, reasons) => { + return { + type: "from origin", + module: key, + children, + ...reasonGroup(children, reasons) + }; + } + }); + } } -} - -module.exports = AsyncQueue; - - -/***/ }), - -/***/ 21301: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ - - +}; -class Hash { - /* istanbul ignore next */ - /** - * Update hash {@link https://nodejs.org/api/crypto.html#crypto_hash_update_data_inputencoding} - * @abstract - * @param {string|Buffer} data data - * @param {string=} inputEncoding data encoding - * @returns {this} updated hash - */ - update(data, inputEncoding) { - const AbstractMethodError = __webpack_require__(570); - throw new AbstractMethodError(); +// remove a prefixed "!" that can be specified to reverse sort order +const normalizeFieldKey = field => { + if (field[0] === "!") { + return field.substr(1); } + return field; +}; - /* istanbul ignore next */ - /** - * Calculates the digest {@link https://nodejs.org/api/crypto.html#crypto_hash_digest_encoding} - * @abstract - * @param {string=} encoding encoding of the return value - * @returns {string|Buffer} digest - */ - digest(encoding) { - const AbstractMethodError = __webpack_require__(570); - throw new AbstractMethodError(); +// if a field is prefixed by a "!" reverse sort order +const sortOrderRegular = field => { + if (field[0] === "!") { + return false; } -} + return true; +}; -module.exports = Hash; +/** + * @param {string} field field name + * @returns {function(Object, Object): number} comparators + */ +const sortByField = field => { + if (!field) { + /** + * @param {any} a first + * @param {any} b second + * @returns {-1|0|1} zero + */ + const noSort = (a, b) => 0; + return noSort; + } + const fieldKey = normalizeFieldKey(field); -/***/ }), + let sortFn = compareSelect(m => m[fieldKey], compareIds); -/***/ 31065: -/***/ (function(__unused_webpack_module, exports) { + // if a field is prefixed with a "!" the sort is reversed! + const sortIsRegular = sortOrderRegular(field); -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ + if (!sortIsRegular) { + const oldSortFn = sortFn; + sortFn = (a, b) => oldSortFn(b, a); + } + return sortFn; +}; +const ASSET_SORTERS = { + /** @type {(comparators: Function[], context: StatsFactoryContext, options: NormalizedStatsOptions) => void} */ + assetsSort: (comparators, context, { assetsSort }) => { + comparators.push(sortByField(assetsSort)); + }, + _: comparators => { + comparators.push(compareSelect(a => a.name, compareIds)); + } +}; -/** - * @template T - * @param {Iterable} set a set - * @returns {T | undefined} last item - */ -const last = set => { - let last; - for (const item of set) last = item; - return last; +/** @type {Record void>>} */ +const RESULT_SORTERS = { + "compilation.chunks": { + chunksSort: (comparators, context, { chunksSort }) => { + comparators.push(sortByField(chunksSort)); + } + }, + "compilation.modules": { + modulesSort: (comparators, context, { modulesSort }) => { + comparators.push(sortByField(modulesSort)); + } + }, + "chunk.modules": { + chunkModulesSort: (comparators, context, { chunkModulesSort }) => { + comparators.push(sortByField(chunkModulesSort)); + } + }, + "module.modules": { + nestedModulesSort: (comparators, context, { nestedModulesSort }) => { + comparators.push(sortByField(nestedModulesSort)); + } + }, + "compilation.assets": ASSET_SORTERS, + "asset.related": ASSET_SORTERS }; /** - * @template T - * @param {Iterable} iterable iterable - * @param {function(T): boolean} filter predicate - * @returns {boolean} true, if some items match the filter predicate + * @param {Record>} config the config see above + * @param {NormalizedStatsOptions} options stats options + * @param {function(string, Function): void} fn handler function called for every active line in config + * @returns {void} */ -const someInIterable = (iterable, filter) => { - for (const item of iterable) { - if (filter(item)) return true; +const iterateConfig = (config, options, fn) => { + for (const hookFor of Object.keys(config)) { + const subConfig = config[hookFor]; + for (const option of Object.keys(subConfig)) { + if (option !== "_") { + if (option.startsWith("!")) { + if (options[option.slice(1)]) continue; + } else { + const value = options[option]; + if ( + value === false || + value === undefined || + (Array.isArray(value) && value.length === 0) + ) + continue; + } + } + fn(hookFor, subConfig[option]); + } } - return false; }; -/** - * @template T - * @param {Iterable} iterable an iterable - * @returns {number} count of items - */ -const countIterable = iterable => { - let i = 0; - // eslint-disable-next-line no-unused-vars - for (const _ of iterable) i++; - return i; +/** @type {Record} */ +const ITEM_NAMES = { + "compilation.children[]": "compilation", + "compilation.modules[]": "module", + "compilation.entrypoints[]": "chunkGroup", + "compilation.namedChunkGroups[]": "chunkGroup", + "compilation.errors[]": "error", + "compilation.warnings[]": "warning", + "chunk.modules[]": "module", + "chunk.rootModules[]": "module", + "chunk.origins[]": "chunkOrigin", + "compilation.chunks[]": "chunk", + "compilation.assets[]": "asset", + "asset.related[]": "asset", + "module.issuerPath[]": "moduleIssuer", + "module.reasons[]": "moduleReason", + "module.modules[]": "module", + "module.children[]": "module", + "moduleTrace[]": "moduleTraceItem", + "moduleTraceItem.dependencies[]": "moduleTraceDependency" }; -exports.last = last; -exports.someInIterable = someInIterable; -exports.countIterable = countIterable; - - -/***/ }), - -/***/ 79300: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ - - - -const { first } = __webpack_require__(34715); -const SortableSet = __webpack_require__(67563); - /** - * Multi layer bucket sorted set: - * Supports adding non-existing items (DO NOT ADD ITEM TWICE), - * Supports removing exiting items (DO NOT REMOVE ITEM NOT IN SET), - * Supports popping the first items according to defined order, - * Supports iterating all items without order, - * Supports updating an item in an efficient way, - * Supports size property, which is the number of items, - * Items are lazy partially sorted when needed - * @template T - * @template K + * @param {Object[]} items items to be merged + * @returns {Object} an object */ -class LazyBucketSortedSet { - /** - * @param {function(T): K} getKey function to get key from item - * @param {function(K, K): number} comparator comparator to sort keys - * @param {...((function(T): any) | (function(any, any): number))} args more pairs of getKey and comparator plus optional final comparator for the last layer - */ - constructor(getKey, comparator, ...args) { - this._getKey = getKey; - this._innerArgs = args; - this._leaf = args.length <= 1; - this._keys = new SortableSet(undefined, comparator); - /** @type {Map | SortableSet>} */ - this._map = new Map(); - this._unsortedItems = new Set(); - this.size = 0; - } - - /** - * @param {T} item an item - * @returns {void} - */ - add(item) { - this.size++; - this._unsortedItems.add(item); - } - - /** - * @param {K} key key of item - * @param {T} item the item - * @returns {void} - */ - _addInternal(key, item) { - let entry = this._map.get(key); - if (entry === undefined) { - entry = this._leaf - ? new SortableSet(undefined, this._innerArgs[0]) - : new /** @type {any} */ (LazyBucketSortedSet)(...this._innerArgs); - this._keys.add(key); - this._map.set(key, entry); - } - entry.add(item); +const mergeToObject = items => { + const obj = Object.create(null); + for (const item of items) { + obj[item.name] = item; } + return obj; +}; - /** - * @param {T} item an item - * @returns {void} - */ - delete(item) { - this.size--; - if (this._unsortedItems.has(item)) { - this._unsortedItems.delete(item); - return; - } - const key = this._getKey(item); - const entry = this._map.get(key); - entry.delete(item); - if (entry.size === 0) { - this._deleteKey(key); - } - } +/** @type {Record any>} */ +const MERGER = { + "compilation.entrypoints": mergeToObject, + "compilation.namedChunkGroups": mergeToObject +}; +class DefaultStatsFactoryPlugin { /** - * @param {K} key key to be removed + * Apply the plugin + * @param {Compiler} compiler the compiler instance * @returns {void} */ - _deleteKey(key) { - this._keys.delete(key); - this._map.delete(key); - } - - /** - * @returns {T | undefined} an item - */ - popFirst() { - if (this.size === 0) return undefined; - this.size--; - if (this._unsortedItems.size > 0) { - for (const item of this._unsortedItems) { - const key = this._getKey(item); - this._addInternal(key, item); - } - this._unsortedItems.clear(); - } - this._keys.sort(); - const key = first(this._keys); - const entry = this._map.get(key); - if (this._leaf) { - const leafEntry = /** @type {SortableSet} */ (entry); - leafEntry.sort(); - const item = first(leafEntry); - leafEntry.delete(item); - if (leafEntry.size === 0) { - this._deleteKey(key); - } - return item; - } else { - const nodeEntry = /** @type {LazyBucketSortedSet} */ (entry); - const item = nodeEntry.popFirst(); - if (nodeEntry.size === 0) { - this._deleteKey(key); - } - return item; - } - } - - /** - * @param {T} item to be updated item - * @returns {function(true=): void} finish update - */ - startUpdate(item) { - if (this._unsortedItems.has(item)) { - return remove => { - if (remove) { - this._unsortedItems.delete(item); - this.size--; - return; - } - }; - } - const key = this._getKey(item); - if (this._leaf) { - const oldEntry = /** @type {SortableSet} */ (this._map.get(key)); - return remove => { - if (remove) { - this.size--; - oldEntry.delete(item); - if (oldEntry.size === 0) { - this._deleteKey(key); - } - return; - } - const newKey = this._getKey(item); - if (key === newKey) { - // This flags the sortable set as unordered - oldEntry.add(item); - } else { - oldEntry.delete(item); - if (oldEntry.size === 0) { - this._deleteKey(key); - } - this._addInternal(newKey, item); - } - }; - } else { - const oldEntry = /** @type {LazyBucketSortedSet} */ ( - this._map.get(key) - ); - const finishUpdate = oldEntry.startUpdate(item); - return remove => { - if (remove) { - this.size--; - finishUpdate(true); - if (oldEntry.size === 0) { - this._deleteKey(key); + apply(compiler) { + compiler.hooks.compilation.tap("DefaultStatsFactoryPlugin", compilation => { + compilation.hooks.statsFactory.tap( + "DefaultStatsFactoryPlugin", + (stats, options, context) => { + iterateConfig(SIMPLE_EXTRACTORS, options, (hookFor, fn) => { + stats.hooks.extract + .for(hookFor) + .tap("DefaultStatsFactoryPlugin", (obj, data, ctx) => + fn(obj, data, ctx, options, stats) + ); + }); + iterateConfig(FILTER, options, (hookFor, fn) => { + stats.hooks.filter + .for(hookFor) + .tap("DefaultStatsFactoryPlugin", (item, ctx, idx, i) => + fn(item, ctx, options, idx, i) + ); + }); + iterateConfig(FILTER_RESULTS, options, (hookFor, fn) => { + stats.hooks.filterResults + .for(hookFor) + .tap("DefaultStatsFactoryPlugin", (item, ctx, idx, i) => + fn(item, ctx, options, idx, i) + ); + }); + iterateConfig(SORTERS, options, (hookFor, fn) => { + stats.hooks.sort + .for(hookFor) + .tap("DefaultStatsFactoryPlugin", (comparators, ctx) => + fn(comparators, ctx, options) + ); + }); + iterateConfig(RESULT_SORTERS, options, (hookFor, fn) => { + stats.hooks.sortResults + .for(hookFor) + .tap("DefaultStatsFactoryPlugin", (comparators, ctx) => + fn(comparators, ctx, options) + ); + }); + iterateConfig(RESULT_GROUPERS, options, (hookFor, fn) => { + stats.hooks.groupResults + .for(hookFor) + .tap("DefaultStatsFactoryPlugin", (groupConfigs, ctx) => + fn(groupConfigs, ctx, options) + ); + }); + for (const key of Object.keys(ITEM_NAMES)) { + const itemName = ITEM_NAMES[key]; + stats.hooks.getItemName + .for(key) + .tap("DefaultStatsFactoryPlugin", () => itemName); } - return; - } - const newKey = this._getKey(item); - if (key === newKey) { - finishUpdate(); - } else { - finishUpdate(true); - if (oldEntry.size === 0) { - this._deleteKey(key); + for (const key of Object.keys(MERGER)) { + const merger = MERGER[key]; + stats.hooks.merge.for(key).tap("DefaultStatsFactoryPlugin", merger); + } + if (options.children) { + if (Array.isArray(options.children)) { + stats.hooks.getItemFactory + .for("compilation.children[].compilation") + .tap("DefaultStatsFactoryPlugin", (comp, { _index: idx }) => { + if (idx < options.children.length) { + return compilation.createStatsFactory( + compilation.createStatsOptions( + options.children[idx], + context + ) + ); + } + }); + } else if (options.children !== true) { + const childFactory = compilation.createStatsFactory( + compilation.createStatsOptions(options.children, context) + ); + stats.hooks.getItemFactory + .for("compilation.children[].compilation") + .tap("DefaultStatsFactoryPlugin", () => { + return childFactory; + }); + } } - this._addInternal(newKey, item); - } - }; - } - } - - /** - * @param {Iterator[]} iterators list of iterators to append to - * @returns {void} - */ - _appendIterators(iterators) { - if (this._unsortedItems.size > 0) - iterators.push(this._unsortedItems[Symbol.iterator]()); - for (const key of this._keys) { - const entry = this._map.get(key); - if (this._leaf) { - const leafEntry = /** @type {SortableSet} */ (entry); - const iterator = leafEntry[Symbol.iterator](); - iterators.push(iterator); - } else { - const nodeEntry = /** @type {LazyBucketSortedSet} */ (entry); - nodeEntry._appendIterators(iterators); - } - } - } - - /** - * @returns {Iterator} the iterator - */ - [Symbol.iterator]() { - const iterators = []; - this._appendIterators(iterators); - iterators.reverse(); - let currentIterator = iterators.pop(); - return { - next: () => { - const res = currentIterator.next(); - if (res.done) { - if (iterators.length === 0) return res; - currentIterator = iterators.pop(); - return currentIterator.next(); } - return res; - } - }; + ); + }); } } - -module.exports = LazyBucketSortedSet; +module.exports = DefaultStatsFactoryPlugin; /***/ }), -/***/ 59534: +/***/ 2130: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; @@ -123204,213 +121959,331 @@ module.exports = LazyBucketSortedSet; -const makeSerializable = __webpack_require__(26522); +const RequestShortener = __webpack_require__(43157); -/** - * @template T - * @param {Set} targetSet set where items should be added - * @param {Set>} toMerge iterables to be merged - * @returns {void} - */ -const merge = (targetSet, toMerge) => { - for (const set of toMerge) { - for (const item of set) { - targetSet.add(item); - } - } -}; +/** @typedef {import("../../declarations/WebpackOptions").StatsOptions} StatsOptions */ +/** @typedef {import("../Compilation")} Compilation */ +/** @typedef {import("../Compilation").CreateStatsOptionsContext} CreateStatsOptionsContext */ +/** @typedef {import("../Compiler")} Compiler */ -/** - * @template T - * @param {Set>} targetSet set where iterables should be added - * @param {Array>} toDeepMerge lazy sets to be flattened - * @returns {void} - */ -const flatten = (targetSet, toDeepMerge) => { - for (const set of toDeepMerge) { - if (set._set.size > 0) targetSet.add(set._set); - if (set._needMerge) { - for (const mergedSet of set._toMerge) { - targetSet.add(mergedSet); - } - flatten(targetSet, set._toDeepMerge); +const applyDefaults = (options, defaults) => { + for (const key of Object.keys(defaults)) { + if (typeof options[key] === "undefined") { + options[key] = defaults[key]; } } }; -/** - * Like Set but with an addAll method to eventually add items from another iterable. - * Access methods make sure that all delayed operations are executed. - * Iteration methods deopts to normal Set performance until clear is called again (because of the chance of modifications during iteration). - * @template T - */ -class LazySet { - /** - * @param {Iterable=} iterable init iterable - */ - constructor(iterable) { - /** @type {Set} */ - this._set = new Set(iterable); - /** @type {Set>} */ - this._toMerge = new Set(); - /** @type {Array>} */ - this._toDeepMerge = []; - this._needMerge = false; - this._deopt = false; +const NAMED_PRESETS = { + verbose: { + hash: true, + builtAt: true, + relatedAssets: true, + entrypoints: true, + chunkGroups: true, + ids: true, + modules: false, + chunks: true, + chunkRelations: true, + chunkModules: true, + dependentModules: true, + chunkOrigins: true, + depth: true, + env: true, + reasons: true, + usedExports: true, + providedExports: true, + optimizationBailout: true, + errorDetails: true, + errorStack: true, + publicPath: true, + logging: "verbose", + orphanModules: true, + runtimeModules: true, + exclude: false, + modulesSpace: Infinity, + chunkModulesSpace: Infinity, + assetsSpace: Infinity, + reasonsSpace: Infinity, + children: true + }, + detailed: { + hash: true, + builtAt: true, + relatedAssets: true, + entrypoints: true, + chunkGroups: true, + ids: true, + chunks: true, + chunkRelations: true, + chunkModules: false, + chunkOrigins: true, + depth: true, + usedExports: true, + providedExports: true, + optimizationBailout: true, + errorDetails: true, + publicPath: true, + logging: true, + runtimeModules: true, + exclude: false, + modulesSpace: 1000, + assetsSpace: 1000, + reasonsSpace: 1000 + }, + minimal: { + all: false, + version: true, + timings: true, + modules: true, + modulesSpace: 0, + assets: true, + assetsSpace: 0, + errors: true, + errorsCount: true, + warnings: true, + warningsCount: true, + logging: "warn" + }, + "errors-only": { + all: false, + errors: true, + errorsCount: true, + moduleTrace: true, + logging: "error" + }, + "errors-warnings": { + all: false, + errors: true, + errorsCount: true, + warnings: true, + warningsCount: true, + logging: "warn" + }, + summary: { + all: false, + version: true, + errorsCount: true, + warningsCount: true + }, + none: { + all: false } +}; - _flatten() { - flatten(this._toMerge, this._toDeepMerge); - this._toDeepMerge.length = 0; - } +const NORMAL_ON = ({ all }) => all !== false; +const NORMAL_OFF = ({ all }) => all === true; +const ON_FOR_TO_STRING = ({ all }, { forToString }) => + forToString ? all !== false : all === true; +const OFF_FOR_TO_STRING = ({ all }, { forToString }) => + forToString ? all === true : all !== false; +const AUTO_FOR_TO_STRING = ({ all }, { forToString }) => { + if (all === false) return false; + if (all === true) return true; + if (forToString) return "auto"; + return true; +}; - _merge() { - this._flatten(); - merge(this._set, this._toMerge); - this._toMerge.clear(); - this._needMerge = false; - } +/** @type {Record any>} */ +const DEFAULTS = { + context: (options, context, compilation) => compilation.compiler.context, + requestShortener: (options, context, compilation) => + compilation.compiler.context === options.context + ? compilation.requestShortener + : new RequestShortener(options.context, compilation.compiler.root), + performance: NORMAL_ON, + hash: OFF_FOR_TO_STRING, + env: NORMAL_OFF, + version: NORMAL_ON, + timings: NORMAL_ON, + builtAt: OFF_FOR_TO_STRING, + assets: NORMAL_ON, + entrypoints: AUTO_FOR_TO_STRING, + chunkGroups: OFF_FOR_TO_STRING, + chunkGroupAuxiliary: OFF_FOR_TO_STRING, + chunkGroupChildren: OFF_FOR_TO_STRING, + chunkGroupMaxAssets: (o, { forToString }) => (forToString ? 5 : Infinity), + chunks: OFF_FOR_TO_STRING, + chunkRelations: OFF_FOR_TO_STRING, + chunkModules: ({ all, modules }) => { + if (all === false) return false; + if (all === true) return true; + if (modules) return false; + return true; + }, + dependentModules: OFF_FOR_TO_STRING, + chunkOrigins: OFF_FOR_TO_STRING, + ids: OFF_FOR_TO_STRING, + modules: ({ all, chunks, chunkModules }, { forToString }) => { + if (all === false) return false; + if (all === true) return true; + if (forToString && chunks && chunkModules) return false; + return true; + }, + nestedModules: OFF_FOR_TO_STRING, + groupModulesByType: ON_FOR_TO_STRING, + groupModulesByCacheStatus: ON_FOR_TO_STRING, + groupModulesByLayer: ON_FOR_TO_STRING, + groupModulesByAttributes: ON_FOR_TO_STRING, + groupModulesByPath: ON_FOR_TO_STRING, + groupModulesByExtension: ON_FOR_TO_STRING, + modulesSpace: (o, { forToString }) => (forToString ? 15 : Infinity), + chunkModulesSpace: (o, { forToString }) => (forToString ? 10 : Infinity), + nestedModulesSpace: (o, { forToString }) => (forToString ? 10 : Infinity), + relatedAssets: OFF_FOR_TO_STRING, + groupAssetsByEmitStatus: ON_FOR_TO_STRING, + groupAssetsByInfo: ON_FOR_TO_STRING, + groupAssetsByPath: ON_FOR_TO_STRING, + groupAssetsByExtension: ON_FOR_TO_STRING, + groupAssetsByChunk: ON_FOR_TO_STRING, + assetsSpace: (o, { forToString }) => (forToString ? 15 : Infinity), + orphanModules: OFF_FOR_TO_STRING, + runtimeModules: ({ all, runtime }, { forToString }) => + runtime !== undefined + ? runtime + : forToString + ? all === true + : all !== false, + cachedModules: ({ all, cached }, { forToString }) => + cached !== undefined ? cached : forToString ? all === true : all !== false, + moduleAssets: OFF_FOR_TO_STRING, + depth: OFF_FOR_TO_STRING, + cachedAssets: OFF_FOR_TO_STRING, + reasons: OFF_FOR_TO_STRING, + reasonsSpace: (o, { forToString }) => (forToString ? 15 : Infinity), + groupReasonsByOrigin: ON_FOR_TO_STRING, + usedExports: OFF_FOR_TO_STRING, + providedExports: OFF_FOR_TO_STRING, + optimizationBailout: OFF_FOR_TO_STRING, + children: OFF_FOR_TO_STRING, + source: NORMAL_OFF, + moduleTrace: NORMAL_ON, + errors: NORMAL_ON, + errorsCount: NORMAL_ON, + errorDetails: AUTO_FOR_TO_STRING, + errorStack: OFF_FOR_TO_STRING, + warnings: NORMAL_ON, + warningsCount: NORMAL_ON, + publicPath: OFF_FOR_TO_STRING, + logging: ({ all }, { forToString }) => + forToString && all !== false ? "info" : false, + loggingDebug: () => [], + loggingTrace: OFF_FOR_TO_STRING, + excludeModules: () => [], + excludeAssets: () => [], + modulesSort: () => "depth", + chunkModulesSort: () => "name", + nestedModulesSort: () => false, + chunksSort: () => false, + assetsSort: () => "!size", + outputPath: OFF_FOR_TO_STRING, + colors: () => false +}; - _isEmpty() { - return ( - this._set.size === 0 && - this._toMerge.size === 0 && - this._toDeepMerge.length === 0 +const normalizeFilter = item => { + if (typeof item === "string") { + const regExp = new RegExp( + `[\\\\/]${item.replace( + // eslint-disable-next-line no-useless-escape + /[-[\]{}()*+?.\\^$|]/g, + "\\$&" + )}([\\\\/]|$|!|\\?)` ); + return ident => regExp.test(ident); } - - get size() { - if (this._needMerge) this._merge(); - return this._set.size; - } - - /** - * @param {T} item an item - * @returns {this} itself - */ - add(item) { - this._set.add(item); - return this; - } - - /** - * @param {Iterable | LazySet} iterable a immutable iterable or another immutable LazySet which will eventually be merged into the Set - * @returns {this} itself - */ - addAll(iterable) { - if (this._deopt) { - const _set = this._set; - for (const item of iterable) { - _set.add(item); - } - } else { - if (iterable instanceof LazySet) { - if (iterable._isEmpty()) return this; - this._toDeepMerge.push(iterable); - this._needMerge = true; - if (this._toDeepMerge.length > 100000) { - this._flatten(); - } - } else { - this._toMerge.add(iterable); - this._needMerge = true; - } - if (this._toMerge.size > 100000) this._merge(); - } - return this; - } - - clear() { - this._set.clear(); - this._toMerge.clear(); - this._toDeepMerge.length = 0; - this._needMerge = false; - this._deopt = false; - } - - /** - * @param {T} value an item - * @returns {boolean} true, if the value was in the Set before - */ - delete(value) { - if (this._needMerge) this._merge(); - return this._set.delete(value); - } - - entries() { - this._deopt = true; - if (this._needMerge) this._merge(); - return this._set.entries(); - } - - /** - * @param {function(T, T, Set): void} callbackFn function called for each entry - * @param {any} thisArg this argument for the callbackFn - * @returns {void} - */ - forEach(callbackFn, thisArg) { - this._deopt = true; - if (this._needMerge) this._merge(); - this._set.forEach(callbackFn, thisArg); - } - - /** - * @param {T} item an item - * @returns {boolean} true, when the item is in the Set - */ - has(item) { - if (this._needMerge) this._merge(); - return this._set.has(item); - } - - keys() { - this._deopt = true; - if (this._needMerge) this._merge(); - return this._set.keys(); - } - - values() { - this._deopt = true; - if (this._needMerge) this._merge(); - return this._set.values(); + if (item && typeof item === "object" && typeof item.test === "function") { + return ident => item.test(ident); } - - [Symbol.iterator]() { - this._deopt = true; - if (this._needMerge) this._merge(); - return this._set[Symbol.iterator](); + if (typeof item === "function") { + return item; } - - /* istanbul ignore next */ - get [Symbol.toStringTag]() { - return "LazySet"; + if (typeof item === "boolean") { + return () => item; } +}; - serialize({ write }) { - if (this._needMerge) this._merge(); - write(this._set.size); - for (const item of this._set) write(item); +const NORMALIZER = { + excludeModules: value => { + if (!Array.isArray(value)) { + value = value ? [value] : []; + } + return value.map(normalizeFilter); + }, + excludeAssets: value => { + if (!Array.isArray(value)) { + value = value ? [value] : []; + } + return value.map(normalizeFilter); + }, + warningsFilter: value => { + if (!Array.isArray(value)) { + value = value ? [value] : []; + } + return value.map(filter => { + if (typeof filter === "string") { + return (warning, warningString) => warningString.includes(filter); + } + if (filter instanceof RegExp) { + return (warning, warningString) => filter.test(warningString); + } + if (typeof filter === "function") { + return filter; + } + throw new Error( + `Can only filter warnings with Strings or RegExps. (Given: ${filter})` + ); + }); + }, + logging: value => { + if (value === true) value = "log"; + return value; + }, + loggingDebug: value => { + if (!Array.isArray(value)) { + value = value ? [value] : []; + } + return value.map(normalizeFilter); } +}; - static deserialize({ read }) { - const count = read(); - const items = []; - for (let i = 0; i < count; i++) { - items.push(read()); - } - return new LazySet(items); +class DefaultStatsPresetPlugin { + /** + * Apply the plugin + * @param {Compiler} compiler the compiler instance + * @returns {void} + */ + apply(compiler) { + compiler.hooks.compilation.tap("DefaultStatsPresetPlugin", compilation => { + for (const key of Object.keys(NAMED_PRESETS)) { + const defaults = NAMED_PRESETS[key]; + compilation.hooks.statsPreset + .for(key) + .tap("DefaultStatsPresetPlugin", (options, context) => { + applyDefaults(options, defaults); + }); + } + compilation.hooks.statsNormalize.tap( + "DefaultStatsPresetPlugin", + (options, context) => { + for (const key of Object.keys(DEFAULTS)) { + if (options[key] === undefined) + options[key] = DEFAULTS[key](options, context, compilation); + } + for (const key of Object.keys(NORMALIZER)) { + options[key] = NORMALIZER[key](options[key]); + } + } + ); + }); } } - -makeSerializable(LazySet, "webpack/lib/util/LazySet"); - -module.exports = LazySet; +module.exports = DefaultStatsPresetPlugin; /***/ }), -/***/ 30498: -/***/ (function(__unused_webpack_module, exports) { +/***/ 78303: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; /* @@ -123420,847 +122293,1320 @@ module.exports = LazySet; +/** @typedef {import("../Compiler")} Compiler */ +/** @typedef {import("./StatsPrinter")} StatsPrinter */ +/** @typedef {import("./StatsPrinter").StatsPrinterContext} StatsPrinterContext */ + +const plural = (n, singular, plural) => (n === 1 ? singular : plural); + /** - * @template K - * @template V - * @param {Map} map a map - * @param {K} key the key - * @param {function(): V} computer compute value - * @returns {V} value + * @param {Record} sizes sizes by source type + * @param {Object} options options + * @param {(number) => string=} options.formatSize size formatter + * @returns {string} text */ -exports.provide = (map, key, computer) => { - const value = map.get(key); - if (value !== undefined) return value; - const newValue = computer(); - map.set(key, newValue); - return newValue; +const printSizes = (sizes, { formatSize = n => `${n}` }) => { + const keys = Object.keys(sizes); + if (keys.length > 1) { + return keys.map(key => `${formatSize(sizes[key])} (${key})`).join(" "); + } else if (keys.length === 1) { + return formatSize(sizes[keys[0]]); + } }; +const mapLines = (str, fn) => str.split("\n").map(fn).join("\n"); -/***/ }), - -/***/ 67491: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ - - - -const binarySearchBounds = __webpack_require__(44795); - -class ParallelismFactorCalculator { - constructor() { - this._rangePoints = []; - this._rangeCallbacks = []; - } +/** + * @param {number} n a number + * @returns {string} number as two digit string, leading 0 + */ +const twoDigit = n => (n >= 10 ? `${n}` : `0${n}`); - range(start, end, callback) { - if (start === end) return callback(1); - this._rangePoints.push(start); - this._rangePoints.push(end); - this._rangeCallbacks.push(callback); - } +const isValidId = id => { + return typeof id === "number" || id; +}; - calculate() { - const segments = Array.from(new Set(this._rangePoints)).sort((a, b) => - a < b ? -1 : 1 - ); - const parallelism = segments.map(() => 0); - const rangeStartIndices = []; - for (let i = 0; i < this._rangePoints.length; i += 2) { - const start = this._rangePoints[i]; - const end = this._rangePoints[i + 1]; - let idx = binarySearchBounds.eq(segments, start); - rangeStartIndices.push(idx); - do { - parallelism[idx]++; - idx++; - } while (segments[idx] < end); +/** @type {Record string | void>} */ +const SIMPLE_PRINTERS = { + "compilation.summary!": ( + _, + { + type, + bold, + green, + red, + yellow, + formatDateTime, + formatTime, + compilation: { + name, + hash, + version, + time, + builtAt, + errorsCount, + warningsCount + } } - for (let i = 0; i < this._rangeCallbacks.length; i++) { - const start = this._rangePoints[i * 2]; - const end = this._rangePoints[i * 2 + 1]; - let idx = rangeStartIndices[i]; - let sum = 0; - let totalDuration = 0; - let current = start; - do { - const p = parallelism[idx]; - idx++; - const duration = segments[idx] - current; - totalDuration += duration; - current = segments[idx]; - sum += p * duration; - } while (current < end); - this._rangeCallbacks[i](sum / totalDuration); + ) => { + const root = type === "compilation.summary!"; + const warningsMessage = + warningsCount > 0 + ? yellow( + `${warningsCount} ${plural(warningsCount, "warning", "warnings")}` + ) + : ""; + const errorsMessage = + errorsCount > 0 + ? red(`${errorsCount} ${plural(errorsCount, "error", "errors")}`) + : ""; + const timeMessage = root && time ? ` in ${formatTime(time)}` : ""; + const hashMessage = hash ? ` (${hash})` : ""; + const builtAtMessage = + root && builtAt ? `${formatDateTime(builtAt)}: ` : ""; + const versionMessage = root && version ? `webpack ${version}` : ""; + const nameMessage = + root && name + ? bold(name) + : name + ? `Child ${bold(name)}` + : root + ? "" + : "Child"; + const subjectMessage = + nameMessage && versionMessage + ? `${nameMessage} (${versionMessage})` + : versionMessage || nameMessage || "webpack"; + let statusMessage; + if (errorsMessage && warningsMessage) { + statusMessage = `compiled with ${errorsMessage} and ${warningsMessage}`; + } else if (errorsMessage) { + statusMessage = `compiled with ${errorsMessage}`; + } else if (warningsMessage) { + statusMessage = `compiled with ${warningsMessage}`; + } else if (errorsCount === 0 && warningsCount === 0) { + statusMessage = `compiled ${green("successfully")}`; + } else { + statusMessage = `compiled`; } - } -} - -module.exports = ParallelismFactorCalculator; - - -/***/ }), + if ( + builtAtMessage || + versionMessage || + errorsMessage || + warningsMessage || + (errorsCount === 0 && warningsCount === 0) || + timeMessage || + hashMessage + ) + return `${builtAtMessage}${subjectMessage} ${statusMessage}${timeMessage}${hashMessage}`; + }, + "compilation.filteredWarningDetailsCount": count => + count + ? `${count} ${plural( + count, + "warning has", + "warnings have" + )} detailed information that is not shown.\nUse 'stats.errorDetails: true' resp. '--stats-error-details' to show it.` + : undefined, + "compilation.filteredErrorDetailsCount": (count, { yellow }) => + count + ? yellow( + `${count} ${plural( + count, + "error has", + "errors have" + )} detailed information that is not shown.\nUse 'stats.errorDetails: true' resp. '--stats-error-details' to show it.` + ) + : undefined, + "compilation.env": (env, { bold }) => + env + ? `Environment (--env): ${bold(JSON.stringify(env, null, 2))}` + : undefined, + "compilation.publicPath": (publicPath, { bold }) => + `PublicPath: ${bold(publicPath || "(none)")}`, + "compilation.entrypoints": (entrypoints, context, printer) => + Array.isArray(entrypoints) + ? undefined + : printer.print(context.type, Object.values(entrypoints), { + ...context, + chunkGroupKind: "Entrypoint" + }), + "compilation.namedChunkGroups": (namedChunkGroups, context, printer) => { + if (!Array.isArray(namedChunkGroups)) { + const { + compilation: { entrypoints } + } = context; + let chunkGroups = Object.values(namedChunkGroups); + if (entrypoints) { + chunkGroups = chunkGroups.filter( + group => + !Object.prototype.hasOwnProperty.call(entrypoints, group.name) + ); + } + return printer.print(context.type, chunkGroups, { + ...context, + chunkGroupKind: "Chunk Group" + }); + } + }, + "compilation.assetsByChunkName": () => "", -/***/ 65753: -/***/ (function(module) { + "compilation.filteredModules": filteredModules => + filteredModules > 0 + ? `${filteredModules} ${plural(filteredModules, "module", "modules")}` + : undefined, + "compilation.filteredAssets": (filteredAssets, { compilation: { assets } }) => + filteredAssets > 0 + ? `${filteredAssets} ${plural(filteredAssets, "asset", "assets")}` + : undefined, + "compilation.logging": (logging, context, printer) => + Array.isArray(logging) + ? undefined + : printer.print( + context.type, + Object.entries(logging).map(([name, value]) => ({ ...value, name })), + context + ), + "compilation.warningsInChildren!": (_, { yellow, compilation }) => { + if ( + !compilation.children && + compilation.warningsCount > 0 && + compilation.warnings + ) { + const childWarnings = + compilation.warningsCount - compilation.warnings.length; + if (childWarnings > 0) { + return yellow( + `${childWarnings} ${plural( + childWarnings, + "WARNING", + "WARNINGS" + )} in child compilations${ + compilation.children + ? "" + : " (Use 'stats.children: true' resp. '--stats-children' for more details)" + }` + ); + } + } + }, + "compilation.errorsInChildren!": (_, { red, compilation }) => { + if ( + !compilation.children && + compilation.errorsCount > 0 && + compilation.errors + ) { + const childErrors = compilation.errorsCount - compilation.errors.length; + if (childErrors > 0) { + return red( + `${childErrors} ${plural( + childErrors, + "ERROR", + "ERRORS" + )} in child compilations${ + compilation.children + ? "" + : " (Use 'stats.children: true' resp. '--stats-children' for more details)" + }` + ); + } + } + }, -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ + "asset.type": type => type, + "asset.name": (name, { formatFilename, asset: { isOverSizeLimit } }) => + formatFilename(name, isOverSizeLimit), + "asset.size": ( + size, + { asset: { isOverSizeLimit }, yellow, green, formatSize } + ) => (isOverSizeLimit ? yellow(formatSize(size)) : formatSize(size)), + "asset.emitted": (emitted, { green, formatFlag }) => + emitted ? green(formatFlag("emitted")) : undefined, + "asset.comparedForEmit": (comparedForEmit, { yellow, formatFlag }) => + comparedForEmit ? yellow(formatFlag("compared for emit")) : undefined, + "asset.cached": (cached, { green, formatFlag }) => + cached ? green(formatFlag("cached")) : undefined, + "asset.isOverSizeLimit": (isOverSizeLimit, { yellow, formatFlag }) => + isOverSizeLimit ? yellow(formatFlag("big")) : undefined, + "asset.info.immutable": (immutable, { green, formatFlag }) => + immutable ? green(formatFlag("immutable")) : undefined, + "asset.info.javascriptModule": (javascriptModule, { formatFlag }) => + javascriptModule ? formatFlag("javascript module") : undefined, + "asset.info.sourceFilename": (sourceFilename, { formatFlag }) => + sourceFilename + ? formatFlag( + sourceFilename === true + ? "from source file" + : `from: ${sourceFilename}` + ) + : undefined, + "asset.info.development": (development, { green, formatFlag }) => + development ? green(formatFlag("dev")) : undefined, + "asset.info.hotModuleReplacement": ( + hotModuleReplacement, + { green, formatFlag } + ) => (hotModuleReplacement ? green(formatFlag("hmr")) : undefined), + "asset.separator!": () => "\n", + "asset.filteredRelated": (filteredRelated, { asset: { related } }) => + filteredRelated > 0 + ? `${filteredRelated} related ${plural( + filteredRelated, + "asset", + "assets" + )}` + : undefined, + "asset.filteredChildren": filteredChildren => + filteredChildren > 0 + ? `${filteredChildren} ${plural(filteredChildren, "asset", "assets")}` + : undefined, + assetChunk: (id, { formatChunkId }) => formatChunkId(id), -/** - * @template T - */ -class Queue { - /** - * @param {Iterable=} items The initial elements. - */ - constructor(items) { - /** @private @type {Set} */ - this._set = new Set(items); - /** @private @type {Iterator} */ - this._iterator = this._set[Symbol.iterator](); - } + assetChunkName: name => name, + assetChunkIdHint: name => name, - /** - * Returns the number of elements in this queue. - * @returns {number} The number of elements in this queue. - */ - get length() { - return this._set.size; - } + "module.type": type => (type !== "module" ? type : undefined), + "module.id": (id, { formatModuleId }) => + isValidId(id) ? formatModuleId(id) : undefined, + "module.name": (name, { bold }) => { + const [, prefix, resource] = /^(.*!)?([^!]*)$/.exec(name); + return (prefix || "") + bold(resource); + }, + "module.identifier": identifier => undefined, + "module.layer": (layer, { formatLayer }) => + layer ? formatLayer(layer) : undefined, + "module.sizes": printSizes, + "module.chunks[]": (id, { formatChunkId }) => formatChunkId(id), + "module.depth": (depth, { formatFlag }) => + depth !== null ? formatFlag(`depth ${depth}`) : undefined, + "module.cacheable": (cacheable, { formatFlag, red }) => + cacheable === false ? red(formatFlag("not cacheable")) : undefined, + "module.orphan": (orphan, { formatFlag, yellow }) => + orphan ? yellow(formatFlag("orphan")) : undefined, + "module.runtime": (runtime, { formatFlag, yellow }) => + runtime ? yellow(formatFlag("runtime")) : undefined, + "module.optional": (optional, { formatFlag, yellow }) => + optional ? yellow(formatFlag("optional")) : undefined, + "module.dependent": (dependent, { formatFlag, cyan }) => + dependent ? cyan(formatFlag("dependent")) : undefined, + "module.built": (built, { formatFlag, yellow }) => + built ? yellow(formatFlag("built")) : undefined, + "module.codeGenerated": (codeGenerated, { formatFlag, yellow }) => + codeGenerated ? yellow(formatFlag("code generated")) : undefined, + "module.buildTimeExecuted": (buildTimeExecuted, { formatFlag, green }) => + buildTimeExecuted ? green(formatFlag("build time executed")) : undefined, + "module.cached": (cached, { formatFlag, green }) => + cached ? green(formatFlag("cached")) : undefined, + "module.assets": (assets, { formatFlag, magenta }) => + assets && assets.length + ? magenta( + formatFlag( + `${assets.length} ${plural(assets.length, "asset", "assets")}` + ) + ) + : undefined, + "module.warnings": (warnings, { formatFlag, yellow }) => + warnings === true + ? yellow(formatFlag("warnings")) + : warnings + ? yellow( + formatFlag(`${warnings} ${plural(warnings, "warning", "warnings")}`) + ) + : undefined, + "module.errors": (errors, { formatFlag, red }) => + errors === true + ? red(formatFlag("errors")) + : errors + ? red(formatFlag(`${errors} ${plural(errors, "error", "errors")}`)) + : undefined, + "module.providedExports": (providedExports, { formatFlag, cyan }) => { + if (Array.isArray(providedExports)) { + if (providedExports.length === 0) return cyan(formatFlag("no exports")); + return cyan(formatFlag(`exports: ${providedExports.join(", ")}`)); + } + }, + "module.usedExports": (usedExports, { formatFlag, cyan, module }) => { + if (usedExports !== true) { + if (usedExports === null) return cyan(formatFlag("used exports unknown")); + if (usedExports === false) return cyan(formatFlag("module unused")); + if (Array.isArray(usedExports)) { + if (usedExports.length === 0) + return cyan(formatFlag("no exports used")); + const providedExportsCount = Array.isArray(module.providedExports) + ? module.providedExports.length + : null; + if ( + providedExportsCount !== null && + providedExportsCount === usedExports.length + ) { + return cyan(formatFlag("all exports used")); + } else { + return cyan( + formatFlag(`only some exports used: ${usedExports.join(", ")}`) + ); + } + } + } + }, + "module.optimizationBailout[]": (optimizationBailout, { yellow }) => + yellow(optimizationBailout), + "module.issuerPath": (issuerPath, { module }) => + module.profile ? undefined : "", + "module.profile": profile => undefined, + "module.filteredModules": filteredModules => + filteredModules > 0 + ? `${filteredModules} nested ${plural( + filteredModules, + "module", + "modules" + )}` + : undefined, + "module.filteredReasons": filteredReasons => + filteredReasons > 0 + ? `${filteredReasons} ${plural(filteredReasons, "reason", "reasons")}` + : undefined, + "module.filteredChildren": filteredChildren => + filteredChildren > 0 + ? `${filteredChildren} ${plural(filteredChildren, "module", "modules")}` + : undefined, + "module.separator!": () => "\n", - /** - * Appends the specified element to this queue. - * @param {T} item The element to add. - * @returns {void} - */ - enqueue(item) { - this._set.add(item); - } + "moduleIssuer.id": (id, { formatModuleId }) => formatModuleId(id), + "moduleIssuer.profile.total": (value, { formatTime }) => formatTime(value), - /** - * Retrieves and removes the head of this queue. - * @returns {T | undefined} The head of the queue of `undefined` if this queue is empty. - */ - dequeue() { - const result = this._iterator.next(); - if (result.done) return undefined; - this._set.delete(result.value); - return result.value; - } -} + "moduleReason.type": type => type, + "moduleReason.userRequest": (userRequest, { cyan }) => cyan(userRequest), + "moduleReason.moduleId": (moduleId, { formatModuleId }) => + isValidId(moduleId) ? formatModuleId(moduleId) : undefined, + "moduleReason.module": (module, { magenta }) => magenta(module), + "moduleReason.loc": loc => loc, + "moduleReason.explanation": (explanation, { cyan }) => cyan(explanation), + "moduleReason.active": (active, { formatFlag }) => + active ? undefined : formatFlag("inactive"), + "moduleReason.resolvedModule": (module, { magenta }) => magenta(module), + "moduleReason.filteredChildren": filteredChildren => + filteredChildren > 0 + ? `${filteredChildren} ${plural(filteredChildren, "reason", "reasons")}` + : undefined, -module.exports = Queue; + "module.profile.total": (value, { formatTime }) => formatTime(value), + "module.profile.resolving": (value, { formatTime }) => + `resolving: ${formatTime(value)}`, + "module.profile.restoring": (value, { formatTime }) => + `restoring: ${formatTime(value)}`, + "module.profile.integration": (value, { formatTime }) => + `integration: ${formatTime(value)}`, + "module.profile.building": (value, { formatTime }) => + `building: ${formatTime(value)}`, + "module.profile.storing": (value, { formatTime }) => + `storing: ${formatTime(value)}`, + "module.profile.additionalResolving": (value, { formatTime }) => + value ? `additional resolving: ${formatTime(value)}` : undefined, + "module.profile.additionalIntegration": (value, { formatTime }) => + value ? `additional integration: ${formatTime(value)}` : undefined, + "chunkGroup.kind!": (_, { chunkGroupKind }) => chunkGroupKind, + "chunkGroup.separator!": () => "\n", + "chunkGroup.name": (name, { bold }) => bold(name), + "chunkGroup.isOverSizeLimit": (isOverSizeLimit, { formatFlag, yellow }) => + isOverSizeLimit ? yellow(formatFlag("big")) : undefined, + "chunkGroup.assetsSize": (size, { formatSize }) => + size ? formatSize(size) : undefined, + "chunkGroup.auxiliaryAssetsSize": (size, { formatSize }) => + size ? `(${formatSize(size)})` : undefined, + "chunkGroup.filteredAssets": n => + n > 0 ? `${n} ${plural(n, "asset", "assets")}` : undefined, + "chunkGroup.filteredAuxiliaryAssets": n => + n > 0 ? `${n} auxiliary ${plural(n, "asset", "assets")}` : undefined, + "chunkGroup.is!": () => "=", + "chunkGroupAsset.name": (asset, { green }) => green(asset), + "chunkGroupAsset.size": (size, { formatSize, chunkGroup }) => + chunkGroup.assets.length > 1 || + (chunkGroup.auxiliaryAssets && chunkGroup.auxiliaryAssets.length > 0) + ? formatSize(size) + : undefined, + "chunkGroup.children": (children, context, printer) => + Array.isArray(children) + ? undefined + : printer.print( + context.type, + Object.keys(children).map(key => ({ + type: key, + children: children[key] + })), + context + ), + "chunkGroupChildGroup.type": type => `${type}:`, + "chunkGroupChild.assets[]": (file, { formatFilename }) => + formatFilename(file), + "chunkGroupChild.chunks[]": (id, { formatChunkId }) => formatChunkId(id), + "chunkGroupChild.name": name => (name ? `(name: ${name})` : undefined), -/***/ }), + "chunk.id": (id, { formatChunkId }) => formatChunkId(id), + "chunk.files[]": (file, { formatFilename }) => formatFilename(file), + "chunk.names[]": name => name, + "chunk.idHints[]": name => name, + "chunk.runtime[]": name => name, + "chunk.sizes": (sizes, context) => printSizes(sizes, context), + "chunk.parents[]": (parents, context) => + context.formatChunkId(parents, "parent"), + "chunk.siblings[]": (siblings, context) => + context.formatChunkId(siblings, "sibling"), + "chunk.children[]": (children, context) => + context.formatChunkId(children, "child"), + "chunk.childrenByOrder": (childrenByOrder, context, printer) => + Array.isArray(childrenByOrder) + ? undefined + : printer.print( + context.type, + Object.keys(childrenByOrder).map(key => ({ + type: key, + children: childrenByOrder[key] + })), + context + ), + "chunk.childrenByOrder[].type": type => `${type}:`, + "chunk.childrenByOrder[].children[]": (id, { formatChunkId }) => + isValidId(id) ? formatChunkId(id) : undefined, + "chunk.entry": (entry, { formatFlag, yellow }) => + entry ? yellow(formatFlag("entry")) : undefined, + "chunk.initial": (initial, { formatFlag, yellow }) => + initial ? yellow(formatFlag("initial")) : undefined, + "chunk.rendered": (rendered, { formatFlag, green }) => + rendered ? green(formatFlag("rendered")) : undefined, + "chunk.recorded": (recorded, { formatFlag, green }) => + recorded ? green(formatFlag("recorded")) : undefined, + "chunk.reason": (reason, { yellow }) => (reason ? yellow(reason) : undefined), + "chunk.filteredModules": filteredModules => + filteredModules > 0 + ? `${filteredModules} chunk ${plural( + filteredModules, + "module", + "modules" + )}` + : undefined, + "chunk.separator!": () => "\n", -/***/ 34715: -/***/ (function(__unused_webpack_module, exports) { + "chunkOrigin.request": request => request, + "chunkOrigin.moduleId": (moduleId, { formatModuleId }) => + isValidId(moduleId) ? formatModuleId(moduleId) : undefined, + "chunkOrigin.moduleName": (moduleName, { bold }) => bold(moduleName), + "chunkOrigin.loc": loc => loc, -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ + "error.compilerPath": (compilerPath, { bold }) => + compilerPath ? bold(`(${compilerPath})`) : undefined, + "error.chunkId": (chunkId, { formatChunkId }) => + isValidId(chunkId) ? formatChunkId(chunkId) : undefined, + "error.chunkEntry": (chunkEntry, { formatFlag }) => + chunkEntry ? formatFlag("entry") : undefined, + "error.chunkInitial": (chunkInitial, { formatFlag }) => + chunkInitial ? formatFlag("initial") : undefined, + "error.file": (file, { bold }) => bold(file), + "error.moduleName": (moduleName, { bold }) => { + return moduleName.includes("!") + ? `${bold(moduleName.replace(/^(\s|\S)*!/, ""))} (${moduleName})` + : `${bold(moduleName)}`; + }, + "error.loc": (loc, { green }) => green(loc), + "error.message": (message, { bold, formatError }) => + message.includes("\u001b[") ? message : bold(formatError(message)), + "error.details": (details, { formatError }) => formatError(details), + "error.stack": stack => stack, + "error.moduleTrace": moduleTrace => undefined, + "error.separator!": () => "\n", + "loggingEntry(error).loggingEntry.message": (message, { red }) => + mapLines(message, x => ` ${red(x)}`), + "loggingEntry(warn).loggingEntry.message": (message, { yellow }) => + mapLines(message, x => ` ${yellow(x)}`), + "loggingEntry(info).loggingEntry.message": (message, { green }) => + mapLines(message, x => ` ${green(x)}`), + "loggingEntry(log).loggingEntry.message": (message, { bold }) => + mapLines(message, x => ` ${bold(x)}`), + "loggingEntry(debug).loggingEntry.message": message => + mapLines(message, x => ` ${x}`), + "loggingEntry(trace).loggingEntry.message": message => + mapLines(message, x => ` ${x}`), + "loggingEntry(status).loggingEntry.message": (message, { magenta }) => + mapLines(message, x => ` ${magenta(x)}`), + "loggingEntry(profile).loggingEntry.message": (message, { magenta }) => + mapLines(message, x => `

${magenta(x)}`), + "loggingEntry(profileEnd).loggingEntry.message": (message, { magenta }) => + mapLines(message, x => `

${magenta(x)}`), + "loggingEntry(time).loggingEntry.message": (message, { magenta }) => + mapLines(message, x => ` ${magenta(x)}`), + "loggingEntry(group).loggingEntry.message": (message, { cyan }) => + mapLines(message, x => `<-> ${cyan(x)}`), + "loggingEntry(groupCollapsed).loggingEntry.message": (message, { cyan }) => + mapLines(message, x => `<+> ${cyan(x)}`), + "loggingEntry(clear).loggingEntry": () => " -------", + "loggingEntry(groupCollapsed).loggingEntry.children": () => "", + "loggingEntry.trace[]": trace => + trace ? mapLines(trace, x => `| ${x}`) : undefined, + "moduleTraceItem.originName": originName => originName, -/** - * intersect creates Set containing the intersection of elements between all sets - * @template T - * @param {Set[]} sets an array of sets being checked for shared elements - * @returns {Set} returns a new Set containing the intersecting items - */ -const intersect = sets => { - if (sets.length === 0) return new Set(); - if (sets.length === 1) return new Set(sets[0]); - let minSize = Infinity; - let minIndex = -1; - for (let i = 0; i < sets.length; i++) { - const size = sets[i].size; - if (size < minSize) { - minIndex = i; - minSize = size; - } - } - const current = new Set(sets[minIndex]); - for (let i = 0; i < sets.length; i++) { - if (i === minIndex) continue; - const set = sets[i]; - for (const item of current) { - if (!set.has(item)) { - current.delete(item); - } - } - } - return current; -}; + loggingGroup: loggingGroup => + loggingGroup.entries.length === 0 ? "" : undefined, + "loggingGroup.debug": (flag, { red }) => (flag ? red("DEBUG") : undefined), + "loggingGroup.name": (name, { bold }) => bold(`LOG from ${name}`), + "loggingGroup.separator!": () => "\n", + "loggingGroup.filteredEntries": filteredEntries => + filteredEntries > 0 ? `+ ${filteredEntries} hidden lines` : undefined, -/** - * Checks if a set is the subset of another set - * @template T - * @param {Set} bigSet a Set which contains the original elements to compare against - * @param {Set} smallSet the set whose elements might be contained inside of bigSet - * @returns {boolean} returns true if smallSet contains all elements inside of the bigSet - */ -const isSubset = (bigSet, smallSet) => { - if (bigSet.size < smallSet.size) return false; - for (const item of smallSet) { - if (!bigSet.has(item)) return false; - } - return true; + "moduleTraceDependency.loc": loc => loc }; -/** - * @template T - * @param {Set} set a set - * @param {function(T): boolean} fn selector function - * @returns {T | undefined} found item - */ -const find = (set, fn) => { - for (const item of set) { - if (fn(item)) return item; - } +/** @type {Record} */ +const ITEM_NAMES = { + "compilation.assets[]": "asset", + "compilation.modules[]": "module", + "compilation.chunks[]": "chunk", + "compilation.entrypoints[]": "chunkGroup", + "compilation.namedChunkGroups[]": "chunkGroup", + "compilation.errors[]": "error", + "compilation.warnings[]": "error", + "compilation.logging[]": "loggingGroup", + "compilation.children[]": "compilation", + "asset.related[]": "asset", + "asset.children[]": "asset", + "asset.chunks[]": "assetChunk", + "asset.auxiliaryChunks[]": "assetChunk", + "asset.chunkNames[]": "assetChunkName", + "asset.chunkIdHints[]": "assetChunkIdHint", + "asset.auxiliaryChunkNames[]": "assetChunkName", + "asset.auxiliaryChunkIdHints[]": "assetChunkIdHint", + "chunkGroup.assets[]": "chunkGroupAsset", + "chunkGroup.auxiliaryAssets[]": "chunkGroupAsset", + "chunkGroupChild.assets[]": "chunkGroupAsset", + "chunkGroupChild.auxiliaryAssets[]": "chunkGroupAsset", + "chunkGroup.children[]": "chunkGroupChildGroup", + "chunkGroupChildGroup.children[]": "chunkGroupChild", + "module.modules[]": "module", + "module.children[]": "module", + "module.reasons[]": "moduleReason", + "moduleReason.children[]": "moduleReason", + "module.issuerPath[]": "moduleIssuer", + "chunk.origins[]": "chunkOrigin", + "chunk.modules[]": "module", + "loggingGroup.entries[]": logEntry => + `loggingEntry(${logEntry.type}).loggingEntry`, + "loggingEntry.children[]": logEntry => + `loggingEntry(${logEntry.type}).loggingEntry`, + "error.moduleTrace[]": "moduleTraceItem", + "moduleTraceItem.dependencies[]": "moduleTraceDependency" }; -/** - * @template T - * @param {Set} set a set - * @returns {T | undefined} first item - */ -const first = set => { - const entry = set.values().next(); - return entry.done ? undefined : entry.value; -}; +const ERROR_PREFERRED_ORDER = [ + "compilerPath", + "chunkId", + "chunkEntry", + "chunkInitial", + "file", + "separator!", + "moduleName", + "loc", + "separator!", + "message", + "separator!", + "details", + "separator!", + "stack", + "separator!", + "missing", + "separator!", + "moduleTrace" +]; -/** - * @template T - * @param {Set} a first - * @param {Set} b second - * @returns {Set} combined set, may be identical to a or b - */ -const combine = (a, b) => { - if (b.size === 0) return a; - if (a.size === 0) return b; - const set = new Set(a); - for (const item of b) set.add(item); - return set; +/** @type {Record} */ +const PREFERRED_ORDERS = { + compilation: [ + "name", + "hash", + "version", + "time", + "builtAt", + "env", + "publicPath", + "assets", + "filteredAssets", + "entrypoints", + "namedChunkGroups", + "chunks", + "modules", + "filteredModules", + "children", + "logging", + "warnings", + "warningsInChildren!", + "filteredWarningDetailsCount", + "errors", + "errorsInChildren!", + "filteredErrorDetailsCount", + "summary!", + "needAdditionalPass" + ], + asset: [ + "type", + "name", + "size", + "chunks", + "auxiliaryChunks", + "emitted", + "comparedForEmit", + "cached", + "info", + "isOverSizeLimit", + "chunkNames", + "auxiliaryChunkNames", + "chunkIdHints", + "auxiliaryChunkIdHints", + "related", + "filteredRelated", + "children", + "filteredChildren" + ], + "asset.info": [ + "immutable", + "sourceFilename", + "javascriptModule", + "development", + "hotModuleReplacement" + ], + chunkGroup: [ + "kind!", + "name", + "isOverSizeLimit", + "assetsSize", + "auxiliaryAssetsSize", + "is!", + "assets", + "filteredAssets", + "auxiliaryAssets", + "filteredAuxiliaryAssets", + "separator!", + "children" + ], + chunkGroupAsset: ["name", "size"], + chunkGroupChildGroup: ["type", "children"], + chunkGroupChild: ["assets", "chunks", "name"], + module: [ + "type", + "name", + "identifier", + "id", + "layer", + "sizes", + "chunks", + "depth", + "cacheable", + "orphan", + "runtime", + "optional", + "dependent", + "built", + "codeGenerated", + "cached", + "assets", + "failed", + "warnings", + "errors", + "children", + "filteredChildren", + "providedExports", + "usedExports", + "optimizationBailout", + "reasons", + "filteredReasons", + "issuerPath", + "profile", + "modules", + "filteredModules" + ], + moduleReason: [ + "active", + "type", + "userRequest", + "moduleId", + "module", + "resolvedModule", + "loc", + "explanation", + "children", + "filteredChildren" + ], + "module.profile": [ + "total", + "separator!", + "resolving", + "restoring", + "integration", + "building", + "storing", + "additionalResolving", + "additionalIntegration" + ], + chunk: [ + "id", + "runtime", + "files", + "names", + "idHints", + "sizes", + "parents", + "siblings", + "children", + "childrenByOrder", + "entry", + "initial", + "rendered", + "recorded", + "reason", + "separator!", + "origins", + "separator!", + "modules", + "separator!", + "filteredModules" + ], + chunkOrigin: ["request", "moduleId", "moduleName", "loc"], + error: ERROR_PREFERRED_ORDER, + warning: ERROR_PREFERRED_ORDER, + "chunk.childrenByOrder[]": ["type", "children"], + loggingGroup: [ + "debug", + "name", + "separator!", + "entries", + "separator!", + "filteredEntries" + ], + loggingEntry: ["message", "trace", "children"] }; -exports.intersect = intersect; -exports.isSubset = isSubset; -exports.find = find; -exports.first = first; -exports.combine = combine; - - -/***/ }), - -/***/ 67563: -/***/ (function(module) { - -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ - - - -const NONE = Symbol("not sorted"); - -/** - * A subset of Set that offers sorting functionality - * @template T item type in set - * @extends {Set} - */ -class SortableSet extends Set { - /** - * Create a new sortable set - * @param {Iterable=} initialIterable The initial iterable value - * @typedef {function(T, T): number} SortFunction - * @param {SortFunction=} defaultSort Default sorting function - */ - constructor(initialIterable, defaultSort) { - super(initialIterable); - /** @private @type {undefined | function(T, T): number}} */ - this._sortFn = defaultSort; - /** @private @type {typeof NONE | undefined | function(T, T): number}} */ - this._lastActiveSortFn = NONE; - /** @private @type {Map | undefined} */ - this._cache = undefined; - /** @private @type {Map | undefined} */ - this._cacheOrderIndependent = undefined; - } - - /** - * @param {T} value value to add to set - * @returns {this} returns itself - */ - add(value) { - this._lastActiveSortFn = NONE; - this._invalidateCache(); - this._invalidateOrderedCache(); - super.add(value); - return this; - } - - /** - * @param {T} value value to delete - * @returns {boolean} true if value existed in set, false otherwise - */ - delete(value) { - this._invalidateCache(); - this._invalidateOrderedCache(); - return super.delete(value); - } - - /** - * @returns {void} - */ - clear() { - this._invalidateCache(); - this._invalidateOrderedCache(); - return super.clear(); - } - - /** - * Sort with a comparer function - * @param {SortFunction} sortFn Sorting comparer function - * @returns {void} - */ - sortWith(sortFn) { - if (this.size <= 1 || sortFn === this._lastActiveSortFn) { - // already sorted - nothing to do - return; - } - - const sortedArray = Array.from(this).sort(sortFn); - super.clear(); - for (let i = 0; i < sortedArray.length; i += 1) { - super.add(sortedArray[i]); - } - this._lastActiveSortFn = sortFn; - this._invalidateCache(); - } +const itemsJoinOneLine = items => items.filter(Boolean).join(" "); +const itemsJoinOneLineBrackets = items => + items.length > 0 ? `(${items.filter(Boolean).join(" ")})` : undefined; +const itemsJoinMoreSpacing = items => items.filter(Boolean).join("\n\n"); +const itemsJoinComma = items => items.filter(Boolean).join(", "); +const itemsJoinCommaBrackets = items => + items.length > 0 ? `(${items.filter(Boolean).join(", ")})` : undefined; +const itemsJoinCommaBracketsWithName = name => items => + items.length > 0 + ? `(${name}: ${items.filter(Boolean).join(", ")})` + : undefined; - sort() { - this.sortWith(this._sortFn); - return this; - } +/** @type {Record string>} */ +const SIMPLE_ITEMS_JOINER = { + "chunk.parents": itemsJoinOneLine, + "chunk.siblings": itemsJoinOneLine, + "chunk.children": itemsJoinOneLine, + "chunk.names": itemsJoinCommaBrackets, + "chunk.idHints": itemsJoinCommaBracketsWithName("id hint"), + "chunk.runtime": itemsJoinCommaBracketsWithName("runtime"), + "chunk.files": itemsJoinComma, + "chunk.childrenByOrder": itemsJoinOneLine, + "chunk.childrenByOrder[].children": itemsJoinOneLine, + "chunkGroup.assets": itemsJoinOneLine, + "chunkGroup.auxiliaryAssets": itemsJoinOneLineBrackets, + "chunkGroupChildGroup.children": itemsJoinComma, + "chunkGroupChild.assets": itemsJoinOneLine, + "chunkGroupChild.auxiliaryAssets": itemsJoinOneLineBrackets, + "asset.chunks": itemsJoinComma, + "asset.auxiliaryChunks": itemsJoinCommaBrackets, + "asset.chunkNames": itemsJoinCommaBracketsWithName("name"), + "asset.auxiliaryChunkNames": itemsJoinCommaBracketsWithName("auxiliary name"), + "asset.chunkIdHints": itemsJoinCommaBracketsWithName("id hint"), + "asset.auxiliaryChunkIdHints": + itemsJoinCommaBracketsWithName("auxiliary id hint"), + "module.chunks": itemsJoinOneLine, + "module.issuerPath": items => + items + .filter(Boolean) + .map(item => `${item} ->`) + .join(" "), + "compilation.errors": itemsJoinMoreSpacing, + "compilation.warnings": itemsJoinMoreSpacing, + "compilation.logging": itemsJoinMoreSpacing, + "compilation.children": items => indent(itemsJoinMoreSpacing(items), " "), + "moduleTraceItem.dependencies": itemsJoinOneLine, + "loggingEntry.children": items => + indent(items.filter(Boolean).join("\n"), " ", false) +}; - /** - * Get data from cache - * @template R - * @param {function(SortableSet): R} fn function to calculate value - * @returns {R} returns result of fn(this), cached until set changes - */ - getFromCache(fn) { - if (this._cache === undefined) { - this._cache = new Map(); - } else { - const result = this._cache.get(fn); - const data = /** @type {R} */ (result); - if (data !== undefined) { - return data; - } - } - const newData = fn(this); - this._cache.set(fn, newData); - return newData; - } +const joinOneLine = items => + items + .map(item => item.content) + .filter(Boolean) + .join(" "); - /** - * Get data from cache (ignoring sorting) - * @template R - * @param {function(SortableSet): R} fn function to calculate value - * @returns {R} returns result of fn(this), cached until set changes - */ - getFromUnorderedCache(fn) { - if (this._cacheOrderIndependent === undefined) { - this._cacheOrderIndependent = new Map(); - } else { - const result = this._cacheOrderIndependent.get(fn); - const data = /** @type {R} */ (result); - if (data !== undefined) { - return data; +const joinInBrackets = items => { + const res = []; + let mode = 0; + for (const item of items) { + if (item.element === "separator!") { + switch (mode) { + case 0: + case 1: + mode += 2; + break; + case 4: + res.push(")"); + mode = 3; + break; } } - const newData = fn(this); - this._cacheOrderIndependent.set(fn, newData); - return newData; - } - - /** - * @private - * @returns {void} - */ - _invalidateCache() { - if (this._cache !== undefined) { - this._cache.clear(); - } - } - - /** - * @private - * @returns {void} - */ - _invalidateOrderedCache() { - if (this._cacheOrderIndependent !== undefined) { - this._cacheOrderIndependent.clear(); + if (!item.content) continue; + switch (mode) { + case 0: + mode = 1; + break; + case 1: + res.push(" "); + break; + case 2: + res.push("("); + mode = 4; + break; + case 3: + res.push(" ("); + mode = 4; + break; + case 4: + res.push(", "); + break; } + res.push(item.content); } + if (mode === 4) res.push(")"); + return res.join(""); +}; - /** - * @returns {T[]} the raw array - */ - toJSON() { - return Array.from(this); - } -} - -module.exports = SortableSet; - - -/***/ }), - -/***/ 26009: -/***/ (function(module) { - -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ - - +const indent = (str, prefix, noPrefixInFirstLine) => { + const rem = str.replace(/\n([^\n])/g, "\n" + prefix + "$1"); + if (noPrefixInFirstLine) return rem; + const ind = str[0] === "\n" ? "" : prefix; + return ind + rem; +}; -/** - * @template K - * @template V - */ -class StackedCacheMap { - constructor() { - /** @type {Map} */ - this.map = new Map(); - /** @type {ReadonlyMap[]} */ - this.stack = []; - } +const joinExplicitNewLine = (items, indenter) => { + let firstInLine = true; + let first = true; + return items + .map(item => { + if (!item || !item.content) return; + let content = indent(item.content, first ? "" : indenter, !firstInLine); + if (firstInLine) { + content = content.replace(/^\n+/, ""); + } + if (!content) return; + first = false; + const noJoiner = firstInLine || content.startsWith("\n"); + firstInLine = content.endsWith("\n"); + return noJoiner ? content : " " + content; + }) + .filter(Boolean) + .join("") + .trim(); +}; - /** - * @param {ReadonlyMap} map map to add - * @param {boolean} immutable if 'map' is immutable and StackedCacheMap can keep referencing it - */ - addAll(map, immutable) { - if (immutable) { - this.stack.push(map); +const joinError = + error => + (items, { red, yellow }) => + `${error ? red("ERROR") : yellow("WARNING")} in ${joinExplicitNewLine( + items, + "" + )}`; - // largest map should go first - for (let i = this.stack.length - 1; i > 0; i--) { - const beforeLast = this.stack[i - 1]; - if (beforeLast.size >= map.size) break; - this.stack[i] = beforeLast; - this.stack[i - 1] = map; - } - } else { - for (const [key, value] of map) { - this.map.set(key, value); +/** @type {Record string>} */ +const SIMPLE_ELEMENT_JOINERS = { + compilation: items => { + const result = []; + let lastNeedMore = false; + for (const item of items) { + if (!item.content) continue; + const needMoreSpace = + item.element === "warnings" || + item.element === "filteredWarningDetailsCount" || + item.element === "errors" || + item.element === "filteredErrorDetailsCount" || + item.element === "logging"; + if (result.length !== 0) { + result.push(needMoreSpace || lastNeedMore ? "\n\n" : "\n"); } + result.push(item.content); + lastNeedMore = needMoreSpace; } - } - - /** - * @param {K} item the key of the element to add - * @param {V} value the value of the element to add - * @returns {void} - */ - set(item, value) { - this.map.set(item, value); - } - - /** - * @param {K} item the item to delete - * @returns {void} - */ - delete(item) { - throw new Error("Items can't be deleted from a StackedCacheMap"); - } - - /** - * @param {K} item the item to test - * @returns {boolean} true if the item exists in this set - */ - has(item) { - throw new Error( - "Checking StackedCacheMap.has before reading is inefficient, use StackedCacheMap.get and check for undefined" + if (lastNeedMore) result.push("\n"); + return result.join(""); + }, + asset: items => + joinExplicitNewLine( + items.map(item => { + if ( + (item.element === "related" || item.element === "children") && + item.content + ) { + return { + ...item, + content: `\n${item.content}\n` + }; + } + return item; + }), + " " + ), + "asset.info": joinOneLine, + module: (items, { module }) => { + let hasName = false; + return joinExplicitNewLine( + items.map(item => { + switch (item.element) { + case "id": + if (module.id === module.name) { + if (hasName) return false; + if (item.content) hasName = true; + } + break; + case "name": + if (hasName) return false; + if (item.content) hasName = true; + break; + case "providedExports": + case "usedExports": + case "optimizationBailout": + case "reasons": + case "issuerPath": + case "profile": + case "children": + case "modules": + if (item.content) { + return { + ...item, + content: `\n${item.content}\n` + }; + } + break; + } + return item; + }), + " " ); - } - - /** - * @param {K} item the key of the element to return - * @returns {V} the value of the element - */ - get(item) { - for (const map of this.stack) { - const value = map.get(item); - if (value !== undefined) return value; - } - return this.map.get(item); - } - - clear() { - this.stack.length = 0; - this.map.clear(); - } - - get size() { - let size = this.map.size; - for (const map of this.stack) { - size += map.size; - } - return size; - } - - [Symbol.iterator]() { - const iterators = this.stack.map(map => map[Symbol.iterator]()); - let current = this.map[Symbol.iterator](); - return { - next() { - let result = current.next(); - while (result.done && iterators.length > 0) { - current = iterators.pop(); - result = current.next(); + }, + chunk: items => { + let hasEntry = false; + return ( + "chunk " + + joinExplicitNewLine( + items.filter(item => { + switch (item.element) { + case "entry": + if (item.content) hasEntry = true; + break; + case "initial": + if (hasEntry) return false; + break; + } + return true; + }), + " " + ) + ); + }, + "chunk.childrenByOrder[]": items => `(${joinOneLine(items)})`, + chunkGroup: items => joinExplicitNewLine(items, " "), + chunkGroupAsset: joinOneLine, + chunkGroupChildGroup: joinOneLine, + chunkGroupChild: joinOneLine, + // moduleReason: (items, { moduleReason }) => { + // let hasName = false; + // return joinOneLine( + // items.filter(item => { + // switch (item.element) { + // case "moduleId": + // if (moduleReason.moduleId === moduleReason.module && item.content) + // hasName = true; + // break; + // case "module": + // if (hasName) return false; + // break; + // case "resolvedModule": + // return ( + // moduleReason.module !== moduleReason.resolvedModule && + // item.content + // ); + // } + // return true; + // }) + // ); + // }, + moduleReason: (items, { moduleReason }) => { + let hasName = false; + return joinExplicitNewLine( + items.map(item => { + switch (item.element) { + case "moduleId": + if (moduleReason.moduleId === moduleReason.module && item.content) + hasName = true; + break; + case "module": + if (hasName) return false; + break; + case "resolvedModule": + if (moduleReason.module === moduleReason.resolvedModule) + return false; + break; + case "children": + if (item.content) { + return { + ...item, + content: `\n${item.content}\n` + }; + } + break; } - return result; - } - }; - } -} - -module.exports = StackedCacheMap; - - -/***/ }), - -/***/ 60798: -/***/ (function(module) { - -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ - - - -const TOMBSTONE = Symbol("tombstone"); -const UNDEFINED_MARKER = Symbol("undefined"); - -/** - * @template T - * @typedef {T | undefined} Cell - */ - -/** - * @template T - * @typedef {T | typeof TOMBSTONE | typeof UNDEFINED_MARKER} InternalCell - */ - -/** - * @template K - * @template V - * @param {[K, InternalCell]} pair the internal cell - * @returns {[K, Cell]} its “safe” representation - */ -const extractPair = pair => { - const key = pair[0]; - const val = pair[1]; - if (val === UNDEFINED_MARKER || val === TOMBSTONE) { - return [key, undefined]; - } else { - return /** @type {[K, Cell]} */ (pair); - } + return item; + }), + " " + ); + }, + "module.profile": joinInBrackets, + moduleIssuer: joinOneLine, + chunkOrigin: items => "> " + joinOneLine(items), + "errors[].error": joinError(true), + "warnings[].error": joinError(false), + loggingGroup: items => joinExplicitNewLine(items, "").trimRight(), + moduleTraceItem: items => " @ " + joinOneLine(items), + moduleTraceDependency: joinOneLine }; -/** - * @template K - * @template V - */ -class StackedMap { - /** - * @param {Map>[]=} parentStack an optional parent - */ - constructor(parentStack) { - /** @type {Map>} */ - this.map = new Map(); - /** @type {Map>[]} */ - this.stack = parentStack === undefined ? [] : parentStack.slice(); - this.stack.push(this.map); - } - - /** - * @param {K} item the key of the element to add - * @param {V} value the value of the element to add - * @returns {void} - */ - set(item, value) { - this.map.set(item, value === undefined ? UNDEFINED_MARKER : value); - } +const AVAILABLE_COLORS = { + bold: "\u001b[1m", + yellow: "\u001b[1m\u001b[33m", + red: "\u001b[1m\u001b[31m", + green: "\u001b[1m\u001b[32m", + cyan: "\u001b[1m\u001b[36m", + magenta: "\u001b[1m\u001b[35m" +}; - /** - * @param {K} item the item to delete - * @returns {void} - */ - delete(item) { - if (this.stack.length > 1) { - this.map.set(item, TOMBSTONE); - } else { - this.map.delete(item); +const AVAILABLE_FORMATS = { + formatChunkId: (id, { yellow }, direction) => { + switch (direction) { + case "parent": + return `<{${yellow(id)}}>`; + case "sibling": + return `={${yellow(id)}}=`; + case "child": + return `>{${yellow(id)}}<`; + default: + return `{${yellow(id)}}`; } - } - - /** - * @param {K} item the item to test - * @returns {boolean} true if the item exists in this set - */ - has(item) { - const topValue = this.map.get(item); - if (topValue !== undefined) { - return topValue !== TOMBSTONE; + }, + formatModuleId: id => `[${id}]`, + formatFilename: (filename, { green, yellow }, oversize) => + (oversize ? yellow : green)(filename), + formatFlag: flag => `[${flag}]`, + formatLayer: layer => `(in ${layer})`, + formatSize: __webpack_require__(15979).formatSize, + formatDateTime: (dateTime, { bold }) => { + const d = new Date(dateTime); + const x = twoDigit; + const date = `${d.getFullYear()}-${x(d.getMonth() + 1)}-${x(d.getDate())}`; + const time = `${x(d.getHours())}:${x(d.getMinutes())}:${x(d.getSeconds())}`; + return `${date} ${bold(time)}`; + }, + formatTime: ( + time, + { timeReference, bold, green, yellow, red }, + boldQuantity + ) => { + const unit = " ms"; + if (timeReference && time !== timeReference) { + const times = [ + timeReference / 2, + timeReference / 4, + timeReference / 8, + timeReference / 16 + ]; + if (time < times[3]) return `${time}${unit}`; + else if (time < times[2]) return bold(`${time}${unit}`); + else if (time < times[1]) return green(`${time}${unit}`); + else if (time < times[0]) return yellow(`${time}${unit}`); + else return red(`${time}${unit}`); + } else { + return `${boldQuantity ? bold(time) : time}${unit}`; } - if (this.stack.length > 1) { - for (let i = this.stack.length - 2; i >= 0; i--) { - const value = this.stack[i].get(item); - if (value !== undefined) { - this.map.set(item, value); - return value !== TOMBSTONE; - } + }, + formatError: (message, { green, yellow, red }) => { + if (message.includes("\u001b[")) return message; + const highlights = [ + { regExp: /(Did you mean .+)/g, format: green }, + { + regExp: /(Set 'mode' option to 'development' or 'production')/g, + format: green + }, + { regExp: /(\(module has no exports\))/g, format: red }, + { regExp: /\(possible exports: (.+)\)/g, format: green }, + { regExp: /\s*([^\s].* doesn't exist)/g, format: red }, + { regExp: /('\w+' option has not been set)/g, format: red }, + { + regExp: /(Emitted value instead of an instance of Error)/g, + format: yellow + }, + { regExp: /(Used? .+ instead)/gi, format: yellow }, + { regExp: /\b(deprecated|must|required)\b/g, format: yellow }, + { + regExp: /\b(BREAKING CHANGE)\b/gi, + format: red + }, + { + regExp: + /\b(error|failed|unexpected|invalid|not found|not supported|not available|not possible|not implemented|doesn't support|conflict|conflicting|not existing|duplicate)\b/gi, + format: red } - this.map.set(item, TOMBSTONE); + ]; + for (const { regExp, format } of highlights) { + message = message.replace(regExp, (match, content) => { + return match.replace(content, format(content)); + }); } - return false; + return message; } +}; - /** - * @param {K} item the key of the element to return - * @returns {Cell} the value of the element - */ - get(item) { - const topValue = this.map.get(item); - if (topValue !== undefined) { - return topValue === TOMBSTONE || topValue === UNDEFINED_MARKER - ? undefined - : topValue; - } - if (this.stack.length > 1) { - for (let i = this.stack.length - 2; i >= 0; i--) { - const value = this.stack[i].get(item); - if (value !== undefined) { - this.map.set(item, value); - return value === TOMBSTONE || value === UNDEFINED_MARKER - ? undefined - : value; - } - } - this.map.set(item, TOMBSTONE); - } - return undefined; +const RESULT_MODIFIER = { + "module.modules": result => { + return indent(result, "| "); } +}; - _compress() { - if (this.stack.length === 1) return; - this.map = new Map(); - for (const data of this.stack) { - for (const pair of data) { - if (pair[1] === TOMBSTONE) { - this.map.delete(pair[0]); - } else { - this.map.set(pair[0], pair[1]); - } - } +const createOrder = (array, preferredOrder) => { + const originalArray = array.slice(); + const set = new Set(array); + const usedSet = new Set(); + array.length = 0; + for (const element of preferredOrder) { + if (element.endsWith("!") || set.has(element)) { + array.push(element); + usedSet.add(element); } - this.stack = [this.map]; - } - - asArray() { - this._compress(); - return Array.from(this.map.keys()); - } - - asSet() { - this._compress(); - return new Set(this.map.keys()); - } - - asPairArray() { - this._compress(); - return Array.from(this.map.entries(), extractPair); - } - - asMap() { - return new Map(this.asPairArray()); - } - - get size() { - this._compress(); - return this.map.size; - } - - createChild() { - return new StackedMap(this.stack); } -} - -module.exports = StackedMap; - - -/***/ }), - -/***/ 23877: -/***/ (function(module) { - -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ - - - -class StringXor { - constructor() { - this._value = undefined; + for (const element of originalArray) { + if (!usedSet.has(element)) { + array.push(element); + } } + return array; +}; +class DefaultStatsPrinterPlugin { /** - * @param {string} str string + * Apply the plugin + * @param {Compiler} compiler the compiler instance * @returns {void} */ - add(str) { - const len = str.length; - const value = this._value; - if (value === undefined) { - const newValue = (this._value = Buffer.allocUnsafe(len)); - for (let i = 0; i < len; i++) { - newValue[i] = str.charCodeAt(i); - } - return; - } - const valueLen = value.length; - if (valueLen < len) { - const newValue = (this._value = Buffer.allocUnsafe(len)); - let i; - for (i = 0; i < valueLen; i++) { - newValue[i] = value[i] ^ str.charCodeAt(i); - } - for (; i < len; i++) { - newValue[i] = str.charCodeAt(i); - } - } else { - for (let i = 0; i < len; i++) { - value[i] = value[i] ^ str.charCodeAt(i); - } - } - } - - toString() { - const value = this._value; - return value === undefined ? "" : value.toString("latin1"); - } - - updateHash(hash) { - const value = this._value; - if (value !== undefined) hash.update(value); - } -} - -module.exports = StringXor; - - -/***/ }), - -/***/ 54345: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ - - - -const TupleSet = __webpack_require__(39322); + apply(compiler) { + compiler.hooks.compilation.tap("DefaultStatsPrinterPlugin", compilation => { + compilation.hooks.statsPrinter.tap( + "DefaultStatsPrinterPlugin", + (stats, options, context) => { + // Put colors into context + stats.hooks.print + .for("compilation") + .tap("DefaultStatsPrinterPlugin", (compilation, context) => { + for (const color of Object.keys(AVAILABLE_COLORS)) { + let start; + if (options.colors) { + if ( + typeof options.colors === "object" && + typeof options.colors[color] === "string" + ) { + start = options.colors[color]; + } else { + start = AVAILABLE_COLORS[color]; + } + } + if (start) { + context[color] = str => + `${start}${ + typeof str === "string" + ? str.replace( + /((\u001b\[39m|\u001b\[22m|\u001b\[0m)+)/g, + `$1${start}` + ) + : str + }\u001b[39m\u001b[22m`; + } else { + context[color] = str => str; + } + } + for (const format of Object.keys(AVAILABLE_FORMATS)) { + context[format] = (content, ...args) => + AVAILABLE_FORMATS[format](content, context, ...args); + } + context.timeReference = compilation.time; + }); -/** - * @template {any[]} T - */ -class TupleQueue { - /** - * @param {Iterable=} items The initial elements. - */ - constructor(items) { - /** @private @type {TupleSet} */ - this._set = new TupleSet(items); - /** @private @type {Iterator} */ - this._iterator = this._set[Symbol.iterator](); - } + for (const key of Object.keys(SIMPLE_PRINTERS)) { + stats.hooks.print + .for(key) + .tap("DefaultStatsPrinterPlugin", (obj, ctx) => + SIMPLE_PRINTERS[key](obj, ctx, stats) + ); + } - /** - * Returns the number of elements in this queue. - * @returns {number} The number of elements in this queue. - */ - get length() { - return this._set.size; - } + for (const key of Object.keys(PREFERRED_ORDERS)) { + const preferredOrder = PREFERRED_ORDERS[key]; + stats.hooks.sortElements + .for(key) + .tap("DefaultStatsPrinterPlugin", (elements, context) => { + createOrder(elements, preferredOrder); + }); + } - /** - * Appends the specified element to this queue. - * @param {T} item The element to add. - * @returns {void} - */ - enqueue(...item) { - this._set.add(...item); - } + for (const key of Object.keys(ITEM_NAMES)) { + const itemName = ITEM_NAMES[key]; + stats.hooks.getItemName + .for(key) + .tap( + "DefaultStatsPrinterPlugin", + typeof itemName === "string" ? () => itemName : itemName + ); + } - /** - * Retrieves and removes the head of this queue. - * @returns {T | undefined} The head of the queue of `undefined` if this queue is empty. - */ - dequeue() { - const result = this._iterator.next(); - if (result.done) { - if (this._set.size > 0) { - this._iterator = this._set[Symbol.iterator](); - const value = this._iterator.next().value; - this._set.delete(...value); - return value; - } - return undefined; - } - this._set.delete(...result.value); - return result.value; + for (const key of Object.keys(SIMPLE_ITEMS_JOINER)) { + const joiner = SIMPLE_ITEMS_JOINER[key]; + stats.hooks.printItems + .for(key) + .tap("DefaultStatsPrinterPlugin", joiner); + } + + for (const key of Object.keys(SIMPLE_ELEMENT_JOINERS)) { + const joiner = SIMPLE_ELEMENT_JOINERS[key]; + stats.hooks.printElements + .for(key) + .tap("DefaultStatsPrinterPlugin", joiner); + } + + for (const key of Object.keys(RESULT_MODIFIER)) { + const modifier = RESULT_MODIFIER[key]; + stats.hooks.result + .for(key) + .tap("DefaultStatsPrinterPlugin", modifier); + } + } + ); + }); } } - -module.exports = TupleQueue; +module.exports = DefaultStatsPrinterPlugin; /***/ }), -/***/ 39322: -/***/ (function(module) { +/***/ 69646: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; /* @@ -124270,250 +123616,297 @@ module.exports = TupleQueue; +const { HookMap, SyncBailHook, SyncWaterfallHook } = __webpack_require__(34718); +const { concatComparators, keepOriginalOrder } = __webpack_require__(26296); +const smartGrouping = __webpack_require__(84820); + +/** @typedef {import("../Chunk")} Chunk */ +/** @typedef {import("../Compilation")} Compilation */ +/** @typedef {import("../Module")} Module */ +/** @typedef {import("../WebpackError")} WebpackError */ +/** @typedef {import("../util/runtime").RuntimeSpec} RuntimeSpec */ + +/** @typedef {import("../util/smartGrouping").GroupConfig} GroupConfig */ + /** - * @template {any[]} T + * @typedef {Object} KnownStatsFactoryContext + * @property {string} type + * @property {function(string): string=} makePathsRelative + * @property {Compilation=} compilation + * @property {Set=} rootModules + * @property {Map=} compilationFileToChunks + * @property {Map=} compilationAuxiliaryFileToChunks + * @property {RuntimeSpec=} runtime + * @property {function(Compilation): WebpackError[]=} cachedGetErrors + * @property {function(Compilation): WebpackError[]=} cachedGetWarnings */ -class TupleSet { - constructor(init) { - this._map = new Map(); - this.size = 0; - if (init) { - for (const tuple of init) { - this.add(...tuple); - } + +/** @typedef {KnownStatsFactoryContext & Record} StatsFactoryContext */ + +class StatsFactory { + constructor() { + this.hooks = Object.freeze({ + /** @type {HookMap>} */ + extract: new HookMap( + () => new SyncBailHook(["object", "data", "context"]) + ), + /** @type {HookMap>} */ + filter: new HookMap( + () => new SyncBailHook(["item", "context", "index", "unfilteredIndex"]) + ), + /** @type {HookMap>} */ + sort: new HookMap(() => new SyncBailHook(["comparators", "context"])), + /** @type {HookMap>} */ + filterSorted: new HookMap( + () => new SyncBailHook(["item", "context", "index", "unfilteredIndex"]) + ), + /** @type {HookMap>} */ + groupResults: new HookMap( + () => new SyncBailHook(["groupConfigs", "context"]) + ), + /** @type {HookMap>} */ + sortResults: new HookMap( + () => new SyncBailHook(["comparators", "context"]) + ), + /** @type {HookMap>} */ + filterResults: new HookMap( + () => new SyncBailHook(["item", "context", "index", "unfilteredIndex"]) + ), + /** @type {HookMap>} */ + merge: new HookMap(() => new SyncBailHook(["items", "context"])), + /** @type {HookMap>} */ + result: new HookMap(() => new SyncWaterfallHook(["result", "context"])), + /** @type {HookMap>} */ + getItemName: new HookMap(() => new SyncBailHook(["item", "context"])), + /** @type {HookMap>} */ + getItemFactory: new HookMap(() => new SyncBailHook(["item", "context"])) + }); + const hooks = this.hooks; + this._caches = + /** @type {Record[]>>} */ ({}); + for (const key of Object.keys(hooks)) { + this._caches[key] = new Map(); } + this._inCreate = false; } - /** - * @param {T} args tuple - * @returns {void} - */ - add(...args) { - let map = this._map; - for (let i = 0; i < args.length - 2; i++) { - const arg = args[i]; - const innerMap = map.get(arg); - if (innerMap === undefined) { - map.set(arg, (map = new Map())); - } else { - map = innerMap; - } + _getAllLevelHooks(hookMap, cache, type) { + const cacheEntry = cache.get(type); + if (cacheEntry !== undefined) { + return cacheEntry; } - - const beforeLast = args[args.length - 2]; - let set = map.get(beforeLast); - if (set === undefined) { - map.set(beforeLast, (set = new Set())); + const hooks = []; + const typeParts = type.split("."); + for (let i = 0; i < typeParts.length; i++) { + const hook = hookMap.get(typeParts.slice(i).join(".")); + if (hook) { + hooks.push(hook); + } } - - const last = args[args.length - 1]; - this.size -= set.size; - set.add(last); - this.size += set.size; + cache.set(type, hooks); + return hooks; } - /** - * @param {T} args tuple - * @returns {boolean} true, if the tuple is in the Set - */ - has(...args) { - let map = this._map; - for (let i = 0; i < args.length - 2; i++) { - const arg = args[i]; - map = map.get(arg); - if (map === undefined) { - return false; - } + _forEachLevel(hookMap, cache, type, fn) { + for (const hook of this._getAllLevelHooks(hookMap, cache, type)) { + const result = fn(hook); + if (result !== undefined) return result; } + } - const beforeLast = args[args.length - 2]; - let set = map.get(beforeLast); - if (set === undefined) { - return false; + _forEachLevelWaterfall(hookMap, cache, type, data, fn) { + for (const hook of this._getAllLevelHooks(hookMap, cache, type)) { + data = fn(hook, data); } + return data; + } - const last = args[args.length - 1]; - return set.has(last); + _forEachLevelFilter(hookMap, cache, type, items, fn, forceClone) { + const hooks = this._getAllLevelHooks(hookMap, cache, type); + if (hooks.length === 0) return forceClone ? items.slice() : items; + let i = 0; + return items.filter((item, idx) => { + for (const hook of hooks) { + const r = fn(hook, item, idx, i); + if (r !== undefined) { + if (r) i++; + return r; + } + } + i++; + return true; + }); } /** - * @param {T} args tuple - * @returns {void} + * @param {string} type type + * @param {any} data factory data + * @param {Omit} baseContext context used as base + * @returns {any} created object */ - delete(...args) { - let map = this._map; - for (let i = 0; i < args.length - 2; i++) { - const arg = args[i]; - map = map.get(arg); - if (map === undefined) { - return; + create(type, data, baseContext) { + if (this._inCreate) { + return this._create(type, data, baseContext); + } else { + try { + this._inCreate = true; + return this._create(type, data, baseContext); + } finally { + for (const key of Object.keys(this._caches)) this._caches[key].clear(); + this._inCreate = false; } } - - const beforeLast = args[args.length - 2]; - let set = map.get(beforeLast); - if (set === undefined) { - return; - } - - const last = args[args.length - 1]; - this.size -= set.size; - set.delete(last); - this.size += set.size; } - /** - * @returns {Iterator} iterator - */ - [Symbol.iterator]() { - const iteratorStack = []; - const tuple = []; - let currentSetIterator = undefined; - - const next = it => { - const result = it.next(); - if (result.done) { - if (iteratorStack.length === 0) return false; - tuple.pop(); - return next(iteratorStack.pop()); - } - const [key, value] = result.value; - iteratorStack.push(it); - tuple.push(key); - if (value instanceof Set) { - currentSetIterator = value[Symbol.iterator](); - return true; - } else { - return next(value[Symbol.iterator]()); - } + _create(type, data, baseContext) { + const context = { + ...baseContext, + type, + [type]: data }; + if (Array.isArray(data)) { + // run filter on unsorted items + const items = this._forEachLevelFilter( + this.hooks.filter, + this._caches.filter, + type, + data, + (h, r, idx, i) => h.call(r, context, idx, i), + true + ); - next(this._map[Symbol.iterator]()); - - return { - next() { - while (currentSetIterator) { - const result = currentSetIterator.next(); - if (result.done) { - tuple.pop(); - if (!next(iteratorStack.pop())) { - currentSetIterator = undefined; - } - } else { - return { - done: false, - value: /** @type {T} */ (tuple.concat(result.value)) - }; - } - } - return { done: true, value: undefined }; + // sort items + const comparators = []; + this._forEachLevel(this.hooks.sort, this._caches.sort, type, h => + h.call(comparators, context) + ); + if (comparators.length > 0) { + items.sort( + // @ts-expect-error number of arguments is correct + concatComparators(...comparators, keepOriginalOrder(items)) + ); } - }; - } -} - -module.exports = TupleSet; - -/***/ }), + // run filter on sorted items + const items2 = this._forEachLevelFilter( + this.hooks.filterSorted, + this._caches.filterSorted, + type, + items, + (h, r, idx, i) => h.call(r, context, idx, i), + false + ); -/***/ 49606: -/***/ (function(__unused_webpack_module, exports) { + // for each item + let resultItems = items2.map((item, i) => { + const itemContext = { + ...context, + _index: i + }; -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Ivan Kopeykin @vankop -*/ + // run getItemName + const itemName = this._forEachLevel( + this.hooks.getItemName, + this._caches.getItemName, + `${type}[]`, + h => h.call(item, itemContext) + ); + if (itemName) itemContext[itemName] = item; + const innerType = itemName ? `${type}[].${itemName}` : `${type}[]`; + // run getItemFactory + const itemFactory = + this._forEachLevel( + this.hooks.getItemFactory, + this._caches.getItemFactory, + innerType, + h => h.call(item, itemContext) + ) || this; + // run item factory + return itemFactory.create(innerType, item, itemContext); + }); -/** @typedef {import("./fs").InputFileSystem} InputFileSystem */ -/** @typedef {(error: Error|null, result?: Buffer) => void} ErrorFirstCallback */ + // sort result items + const comparators2 = []; + this._forEachLevel( + this.hooks.sortResults, + this._caches.sortResults, + type, + h => h.call(comparators2, context) + ); + if (comparators2.length > 0) { + resultItems.sort( + // @ts-expect-error number of arguments is correct + concatComparators(...comparators2, keepOriginalOrder(resultItems)) + ); + } -const backSlashCharCode = "\\".charCodeAt(0); -const slashCharCode = "/".charCodeAt(0); -const aLowerCaseCharCode = "a".charCodeAt(0); -const zLowerCaseCharCode = "z".charCodeAt(0); -const aUpperCaseCharCode = "A".charCodeAt(0); -const zUpperCaseCharCode = "Z".charCodeAt(0); -const _0CharCode = "0".charCodeAt(0); -const _9CharCode = "9".charCodeAt(0); -const plusCharCode = "+".charCodeAt(0); -const hyphenCharCode = "-".charCodeAt(0); -const colonCharCode = ":".charCodeAt(0); -const hashCharCode = "#".charCodeAt(0); -const queryCharCode = "?".charCodeAt(0); -/** - * Get scheme if specifier is an absolute URL specifier - * e.g. Absolute specifiers like 'file:///user/webpack/index.js' - * https://tools.ietf.org/html/rfc3986#section-3.1 - * @param {string} specifier specifier - * @returns {string|undefined} scheme if absolute URL specifier provided - */ -function getScheme(specifier) { - const start = specifier.charCodeAt(0); + // group result items + const groupConfigs = []; + this._forEachLevel( + this.hooks.groupResults, + this._caches.groupResults, + type, + h => h.call(groupConfigs, context) + ); + if (groupConfigs.length > 0) { + resultItems = smartGrouping(resultItems, groupConfigs); + } - // First char maybe only a letter - if ( - (start < aLowerCaseCharCode || start > zLowerCaseCharCode) && - (start < aUpperCaseCharCode || start > zUpperCaseCharCode) - ) { - return undefined; - } + // run filter on sorted result items + const finalResultItems = this._forEachLevelFilter( + this.hooks.filterResults, + this._caches.filterResults, + type, + resultItems, + (h, r, idx, i) => h.call(r, context, idx, i), + false + ); - let i = 1; - let ch = specifier.charCodeAt(i); + // run merge on mapped items + let result = this._forEachLevel( + this.hooks.merge, + this._caches.merge, + type, + h => h.call(finalResultItems, context) + ); + if (result === undefined) result = finalResultItems; - while ( - (ch >= aLowerCaseCharCode && ch <= zLowerCaseCharCode) || - (ch >= aUpperCaseCharCode && ch <= zUpperCaseCharCode) || - (ch >= _0CharCode && ch <= _9CharCode) || - ch === plusCharCode || - ch === hyphenCharCode - ) { - if (++i === specifier.length) return undefined; - ch = specifier.charCodeAt(i); - } + // run result on merged items + return this._forEachLevelWaterfall( + this.hooks.result, + this._caches.result, + type, + result, + (h, r) => h.call(r, context) + ); + } else { + const object = {}; - // Scheme must end with colon - if (ch !== colonCharCode) return undefined; + // run extract on value + this._forEachLevel(this.hooks.extract, this._caches.extract, type, h => + h.call(object, data, context) + ); - // Check for Windows absolute path - // https://url.spec.whatwg.org/#url-miscellaneous - if (i === 1) { - const nextChar = i + 1 < specifier.length ? specifier.charCodeAt(i + 1) : 0; - if ( - nextChar === 0 || - nextChar === backSlashCharCode || - nextChar === slashCharCode || - nextChar === hashCharCode || - nextChar === queryCharCode - ) { - return undefined; + // run result on extracted object + return this._forEachLevelWaterfall( + this.hooks.result, + this._caches.result, + type, + object, + (h, r) => h.call(r, context) + ); } } - - return specifier.slice(0, i).toLowerCase(); -} - -/** - * @param {string} specifier specifier - * @returns {string|null} protocol if absolute URL specifier provided - */ -function getProtocol(specifier) { - const scheme = getScheme(specifier); - return scheme === undefined ? undefined : scheme + ":"; } - -exports.getScheme = getScheme; -exports.getProtocol = getProtocol; +module.exports = StatsFactory; /***/ }), -/***/ 73963: -/***/ (function(module) { +/***/ 61025: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; /* @@ -124523,270 +123916,292 @@ exports.getProtocol = getProtocol; -const isWeakKey = thing => typeof thing === "object" && thing !== null; +const { HookMap, SyncWaterfallHook, SyncBailHook } = __webpack_require__(34718); + +/** @template T @typedef {import("tapable").AsArray} AsArray */ +/** @typedef {import("tapable").Hook} Hook */ +/** @typedef {import("./DefaultStatsFactoryPlugin").StatsAsset} StatsAsset */ +/** @typedef {import("./DefaultStatsFactoryPlugin").StatsChunk} StatsChunk */ +/** @typedef {import("./DefaultStatsFactoryPlugin").StatsChunkGroup} StatsChunkGroup */ +/** @typedef {import("./DefaultStatsFactoryPlugin").StatsCompilation} StatsCompilation */ +/** @typedef {import("./DefaultStatsFactoryPlugin").StatsModule} StatsModule */ +/** @typedef {import("./DefaultStatsFactoryPlugin").StatsModuleReason} StatsModuleReason */ /** - * @template {any[]} T - * @template V + * @typedef {Object} PrintedElement + * @property {string} element + * @property {string} content + */ + +/** + * @typedef {Object} KnownStatsPrinterContext + * @property {string=} type + * @property {StatsCompilation=} compilation + * @property {StatsChunkGroup=} chunkGroup + * @property {StatsAsset=} asset + * @property {StatsModule=} module + * @property {StatsChunk=} chunk + * @property {StatsModuleReason=} moduleReason + * @property {(str: string) => string=} bold + * @property {(str: string) => string=} yellow + * @property {(str: string) => string=} red + * @property {(str: string) => string=} green + * @property {(str: string) => string=} magenta + * @property {(str: string) => string=} cyan + * @property {(file: string, oversize?: boolean) => string=} formatFilename + * @property {(id: string) => string=} formatModuleId + * @property {(id: string, direction?: "parent"|"child"|"sibling") => string=} formatChunkId + * @property {(size: number) => string=} formatSize + * @property {(dateTime: number) => string=} formatDateTime + * @property {(flag: string) => string=} formatFlag + * @property {(time: number, boldQuantity?: boolean) => string=} formatTime + * @property {string=} chunkGroupKind */ -class WeakTupleMap { + +/** @typedef {KnownStatsPrinterContext & Record} StatsPrinterContext */ + +class StatsPrinter { constructor() { - /** @private */ - this.f = 0; - /** @private @type {any} */ - this.v = undefined; - /** @private @type {Map> | undefined} */ - this.m = undefined; - /** @private @type {WeakMap> | undefined} */ - this.w = undefined; + this.hooks = Object.freeze({ + /** @type {HookMap>} */ + sortElements: new HookMap( + () => new SyncBailHook(["elements", "context"]) + ), + /** @type {HookMap>} */ + printElements: new HookMap( + () => new SyncBailHook(["printedElements", "context"]) + ), + /** @type {HookMap>} */ + sortItems: new HookMap(() => new SyncBailHook(["items", "context"])), + /** @type {HookMap>} */ + getItemName: new HookMap(() => new SyncBailHook(["item", "context"])), + /** @type {HookMap>} */ + printItems: new HookMap( + () => new SyncBailHook(["printedItems", "context"]) + ), + /** @type {HookMap>} */ + print: new HookMap(() => new SyncBailHook(["object", "context"])), + /** @type {HookMap>} */ + result: new HookMap(() => new SyncWaterfallHook(["result", "context"])) + }); + /** @type {Map, Map>} */ + this._levelHookCache = new Map(); + this._inPrint = false; } /** - * @param {[...T, V]} args tuple - * @returns {void} + * get all level hooks + * @private + * @template {Hook} T + * @param {HookMap} hookMap HookMap + * @param {string} type type + * @returns {T[]} hooks */ - set(...args) { - /** @type {WeakTupleMap} */ - let node = this; - for (let i = 0; i < args.length - 1; i++) { - node = node._get(args[i]); + _getAllLevelHooks(hookMap, type) { + let cache = /** @type {Map} */ ( + this._levelHookCache.get(hookMap) + ); + if (cache === undefined) { + cache = new Map(); + this._levelHookCache.set(hookMap, cache); } - node._setValue(args[args.length - 1]); - } - - /** - * @param {T} args tuple - * @returns {boolean} true, if the tuple is in the Set - */ - has(...args) { - /** @type {WeakTupleMap} */ - let node = this; - for (let i = 0; i < args.length; i++) { - node = node._peek(args[i]); - if (node === undefined) return false; + const cacheEntry = cache.get(type); + if (cacheEntry !== undefined) { + return cacheEntry; } - return node._hasValue(); + /** @type {T[]} */ + const hooks = []; + const typeParts = type.split("."); + for (let i = 0; i < typeParts.length; i++) { + const hook = hookMap.get(typeParts.slice(i).join(".")); + if (hook) { + hooks.push(hook); + } + } + cache.set(type, hooks); + return hooks; } /** - * @param {T} args tuple - * @returns {V} the value + * Run `fn` for each level + * @private + * @template T + * @template R + * @param {HookMap>} hookMap HookMap + * @param {string} type type + * @param {(hook: SyncBailHook) => R} fn function + * @returns {R} result of `fn` */ - get(...args) { - /** @type {WeakTupleMap} */ - let node = this; - for (let i = 0; i < args.length; i++) { - node = node._peek(args[i]); - if (node === undefined) return undefined; + _forEachLevel(hookMap, type, fn) { + for (const hook of this._getAllLevelHooks(hookMap, type)) { + const result = fn(hook); + if (result !== undefined) return result; } - return node._getValue(); } /** - * @param {[...T, function(): V]} args tuple - * @returns {V} the value + * Run `fn` for each level + * @private + * @template T + * @param {HookMap>} hookMap HookMap + * @param {string} type type + * @param {AsArray[0]} data data + * @param {(hook: SyncWaterfallHook, data: AsArray[0]) => AsArray[0]} fn function + * @returns {AsArray[0]} result of `fn` */ - provide(...args) { - /** @type {WeakTupleMap} */ - let node = this; - for (let i = 0; i < args.length - 1; i++) { - node = node._get(args[i]); + _forEachLevelWaterfall(hookMap, type, data, fn) { + for (const hook of this._getAllLevelHooks(hookMap, type)) { + data = fn(hook, data); } - if (node._hasValue()) return node._getValue(); - const fn = args[args.length - 1]; - const newValue = fn(...args.slice(0, -1)); - node._setValue(newValue); - return newValue; + return data; } /** - * @param {T} args tuple - * @returns {void} + * @param {string} type The type + * @param {Object} object Object to print + * @param {Object=} baseContext The base context + * @returns {string} printed result */ - delete(...args) { - /** @type {WeakTupleMap} */ - let node = this; - for (let i = 0; i < args.length; i++) { - node = node._peek(args[i]); - if (node === undefined) return; + print(type, object, baseContext) { + if (this._inPrint) { + return this._print(type, object, baseContext); + } else { + try { + this._inPrint = true; + return this._print(type, object, baseContext); + } finally { + this._levelHookCache.clear(); + this._inPrint = false; + } } - node._deleteValue(); } /** - * @returns {void} + * @private + * @param {string} type type + * @param {Object} object object + * @param {Object=} baseContext context + * @returns {string} printed result */ - clear() { - this.f = 0; - this.v = undefined; - this.w = undefined; - this.m = undefined; - } - - _getValue() { - return this.v; - } - - _hasValue() { - return (this.f & 1) === 1; - } - - _setValue(v) { - this.f |= 1; - this.v = v; - } - - _deleteValue() { - this.f &= 6; - this.v = undefined; - } - - _peek(thing) { - if (isWeakKey(thing)) { - if ((this.f & 4) !== 4) return undefined; - return this.w.get(thing); - } else { - if ((this.f & 2) !== 2) return undefined; - return this.m.get(thing); - } - } + _print(type, object, baseContext) { + const context = { + ...baseContext, + type, + [type]: object + }; - _get(thing) { - if (isWeakKey(thing)) { - if ((this.f & 4) !== 4) { - const newMap = new WeakMap(); - this.f |= 4; - const newNode = new WeakTupleMap(); - (this.w = newMap).set(thing, newNode); - return newNode; - } - const entry = this.w.get(thing); - if (entry !== undefined) { - return entry; - } - const newNode = new WeakTupleMap(); - this.w.set(thing, newNode); - return newNode; - } else { - if ((this.f & 2) !== 2) { - const newMap = new Map(); - this.f |= 2; - const newNode = new WeakTupleMap(); - (this.m = newMap).set(thing, newNode); - return newNode; - } - const entry = this.m.get(thing); - if (entry !== undefined) { - return entry; + let printResult = this._forEachLevel(this.hooks.print, type, hook => + hook.call(object, context) + ); + if (printResult === undefined) { + if (Array.isArray(object)) { + const sortedItems = object.slice(); + this._forEachLevel(this.hooks.sortItems, type, h => + h.call(sortedItems, context) + ); + const printedItems = sortedItems.map((item, i) => { + const itemContext = { + ...context, + _index: i + }; + const itemName = this._forEachLevel( + this.hooks.getItemName, + `${type}[]`, + h => h.call(item, itemContext) + ); + if (itemName) itemContext[itemName] = item; + return this.print( + itemName ? `${type}[].${itemName}` : `${type}[]`, + item, + itemContext + ); + }); + printResult = this._forEachLevel(this.hooks.printItems, type, h => + h.call(printedItems, context) + ); + if (printResult === undefined) { + const result = printedItems.filter(Boolean); + if (result.length > 0) printResult = result.join("\n"); + } + } else if (object !== null && typeof object === "object") { + const elements = Object.keys(object).filter( + key => object[key] !== undefined + ); + this._forEachLevel(this.hooks.sortElements, type, h => + h.call(elements, context) + ); + const printedElements = elements.map(element => { + const content = this.print(`${type}.${element}`, object[element], { + ...context, + _parent: object, + _element: element, + [element]: object[element] + }); + return { element, content }; + }); + printResult = this._forEachLevel(this.hooks.printElements, type, h => + h.call(printedElements, context) + ); + if (printResult === undefined) { + const result = printedElements.map(e => e.content).filter(Boolean); + if (result.length > 0) printResult = result.join("\n"); + } } - const newNode = new WeakTupleMap(); - this.m.set(thing, newNode); - return newNode; } + + return this._forEachLevelWaterfall( + this.hooks.result, + type, + printResult, + (h, r) => h.call(r, context) + ); } } - -module.exports = WeakTupleMap; +module.exports = StatsPrinter; /***/ }), -/***/ 44795: -/***/ (function(module) { +/***/ 21537: +/***/ (function(__unused_webpack_module, exports) { "use strict"; /* MIT License http://www.opensource.org/licenses/mit-license.php - Author Mikola Lysenko @mikolalysenko + Author Tobias Koppers @sokra */ -/* cspell:disable-next-line */ -// Refactor: Peter Somogyvari @petermetz - -const compileSearch = (funcName, predicate, reversed, extraArgs, earlyOut) => { - const code = [ - "function ", - funcName, - "(a,l,h,", - extraArgs.join(","), - "){", - earlyOut ? "" : "var i=", - reversed ? "l-1" : "h+1", - ";while(l<=h){var m=(l+h)>>>1,x=a[m]" - ]; - - if (earlyOut) { - if (predicate.indexOf("c") < 0) { - code.push(";if(x===y){return m}else if(x<=y){"); - } else { - code.push(";var p=c(x,y);if(p===0){return m}else if(p<=0){"); - } - } else { - code.push(";if(", predicate, "){i=m;"); - } - if (reversed) { - code.push("l=m+1}else{h=m-1}"); - } else { - code.push("h=m-1}else{l=m+1}"); - } - code.push("}"); - if (earlyOut) { - code.push("return -1};"); - } else { - code.push("return i};"); +exports.equals = (a, b) => { + if (a.length !== b.length) return false; + for (let i = 0; i < a.length; i++) { + if (a[i] !== b[i]) return false; } - return code.join(""); + return true; }; -const compileBoundsSearch = (predicate, reversed, suffix, earlyOut) => { - const arg1 = compileSearch( - "A", - "x" + predicate + "y", - reversed, - ["y"], - earlyOut - ); - - const arg2 = compileSearch( - "P", - "c(x,y)" + predicate + "0", - reversed, - ["y", "c"], - earlyOut +/** + * + * @param {Array} arr Array of values to be partitioned + * @param {(value: any) => boolean} fn Partition function which partitions based on truthiness of result. + * @returns {[Array, Array]} returns the values of `arr` partitioned into two new arrays based on fn predicate. + */ +exports.groupBy = (arr = [], fn) => { + return arr.reduce( + (groups, value) => { + groups[fn(value) ? 0 : 1].push(value); + return groups; + }, + [[], []] ); - - const fnHeader = "function dispatchBinarySearch"; - - const fnBody = - "(a,y,c,l,h){\ -if(typeof(c)==='function'){\ -return P(a,(l===void 0)?0:l|0,(h===void 0)?a.length-1:h|0,y,c)\ -}else{\ -return A(a,(c===void 0)?0:c|0,(l===void 0)?a.length-1:l|0,y)\ -}}\ -return dispatchBinarySearch"; - - const fnArgList = [arg1, arg2, fnHeader, suffix, fnBody, suffix]; - const fnSource = fnArgList.join(""); - const result = new Function(fnSource); - return result(); -}; - -module.exports = { - ge: compileBoundsSearch(">=", false, "GE"), - gt: compileBoundsSearch(">", false, "GT"), - lt: compileBoundsSearch("<", true, "LT"), - le: compileBoundsSearch("<=", true, "LE"), - eq: compileBoundsSearch("-", true, "EQ", true) }; /***/ }), -/***/ 11217: -/***/ (function(__unused_webpack_module, exports) { +/***/ 29704: +/***/ (function(module) { "use strict"; /* @@ -124796,573 +124211,497 @@ module.exports = { -/** @type {WeakMap>} */ -const mergeCache = new WeakMap(); -/** @type {WeakMap>>} */ -const setPropertyCache = new WeakMap(); -const DELETE = Symbol("DELETE"); -const DYNAMIC_INFO = Symbol("cleverMerge dynamic info"); - /** - * Merges two given objects and caches the result to avoid computation if same objects passed as arguments again. * @template T - * @template O - * @example - * // performs cleverMerge(first, second), stores the result in WeakMap and returns result - * cachedCleverMerge({a: 1}, {a: 2}) - * {a: 2} - * // when same arguments passed, gets the result from WeakMap and returns it. - * cachedCleverMerge({a: 1}, {a: 2}) - * {a: 2} - * @param {T} first first object - * @param {O} second second object - * @returns {T & O | T | O} merged object of first and second object */ -const cachedCleverMerge = (first, second) => { - if (second === undefined) return first; - if (first === undefined) return second; - if (typeof second !== "object" || second === null) return second; - if (typeof first !== "object" || first === null) return first; +class ArrayQueue { + /** + * @param {Iterable=} items The initial elements. + */ + constructor(items) { + /** @private @type {T[]} */ + this._list = items ? Array.from(items) : []; + /** @private @type {T[]} */ + this._listReversed = []; + } - let innerCache = mergeCache.get(first); - if (innerCache === undefined) { - innerCache = new WeakMap(); - mergeCache.set(first, innerCache); + /** + * Returns the number of elements in this queue. + * @returns {number} The number of elements in this queue. + */ + get length() { + return this._list.length + this._listReversed.length; + } + + /** + * Empties the queue. + */ + clear() { + this._list.length = 0; + this._listReversed.length = 0; + } + + /** + * Appends the specified element to this queue. + * @param {T} item The element to add. + * @returns {void} + */ + enqueue(item) { + this._list.push(item); + } + + /** + * Retrieves and removes the head of this queue. + * @returns {T | undefined} The head of the queue of `undefined` if this queue is empty. + */ + dequeue() { + if (this._listReversed.length === 0) { + if (this._list.length === 0) return undefined; + if (this._list.length === 1) return this._list.pop(); + if (this._list.length < 16) return this._list.shift(); + const temp = this._listReversed; + this._listReversed = this._list; + this._listReversed.reverse(); + this._list = temp; + } + return this._listReversed.pop(); + } + + /** + * Finds and removes an item + * @param {T} item the item + * @returns {void} + */ + delete(item) { + const i = this._list.indexOf(item); + if (i >= 0) { + this._list.splice(i, 1); + } else { + const i = this._listReversed.indexOf(item); + if (i >= 0) this._listReversed.splice(i, 1); + } + } + + [Symbol.iterator]() { + let i = -1; + let reversed = false; + return { + next: () => { + if (!reversed) { + i++; + if (i < this._list.length) { + return { + done: false, + value: this._list[i] + }; + } + reversed = true; + i = this._listReversed.length; + } + i--; + if (i < 0) { + return { + done: true, + value: undefined + }; + } + return { + done: false, + value: this._listReversed[i] + }; + } + }; } - const prevMerge = innerCache.get(second); - if (prevMerge !== undefined) return prevMerge; - const newMerge = _cleverMerge(first, second, true); - innerCache.set(second, newMerge); - return newMerge; -}; +} -/** - * @template T - * @param {Partial} obj object - * @param {string} property property - * @param {string|number|boolean} value assignment value - * @returns {T} new object - */ -const cachedSetProperty = (obj, property, value) => { - let mapByProperty = setPropertyCache.get(obj); +module.exports = ArrayQueue; - if (mapByProperty === undefined) { - mapByProperty = new Map(); - setPropertyCache.set(obj, mapByProperty); - } - let mapByValue = mapByProperty.get(property); +/***/ }), - if (mapByValue === undefined) { - mapByValue = new Map(); - mapByProperty.set(property, mapByValue); - } +/***/ 55531: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - let result = mapByValue.get(value); +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ - if (result) return result; - result = { - ...obj, - [property]: value - }; - mapByValue.set(value, result); - return result; -}; +const { SyncHook, AsyncSeriesHook } = __webpack_require__(34718); +const { makeWebpackError } = __webpack_require__(89935); +const WebpackError = __webpack_require__(68422); +const ArrayQueue = __webpack_require__(29704); -/** - * @typedef {Object} ObjectParsedPropertyEntry - * @property {any | undefined} base base value - * @property {string | undefined} byProperty the name of the selector property - * @property {Map} byValues value depending on selector property, merged with base - */ +const QUEUED_STATE = 0; +const PROCESSING_STATE = 1; +const DONE_STATE = 2; + +let inHandleResult = 0; /** - * @typedef {Object} ParsedObject - * @property {Map} static static properties (key is property name) - * @property {{ byProperty: string, fn: Function } | undefined} dynamic dynamic part + * @template T + * @callback Callback + * @param {WebpackError=} err + * @param {T=} result */ -/** @type {WeakMap} */ -const parseCache = new WeakMap(); - /** - * @param {object} obj the object - * @returns {ParsedObject} parsed object + * @template T + * @template K + * @template R */ -const cachedParseObject = obj => { - const entry = parseCache.get(obj); - if (entry !== undefined) return entry; - const result = parseObject(obj); - parseCache.set(obj, result); - return result; -}; +class AsyncQueueEntry { + /** + * @param {T} item the item + * @param {Callback} callback the callback + */ + constructor(item, callback) { + this.item = item; + /** @type {typeof QUEUED_STATE | typeof PROCESSING_STATE | typeof DONE_STATE} */ + this.state = QUEUED_STATE; + this.callback = callback; + /** @type {Callback[] | undefined} */ + this.callbacks = undefined; + this.result = undefined; + /** @type {WebpackError | undefined} */ + this.error = undefined; + } +} /** - * @param {object} obj the object - * @returns {ParsedObject} parsed object + * @template T + * @template K + * @template R */ -const parseObject = obj => { - const info = new Map(); - let dynamicInfo; - const getInfo = p => { - const entry = info.get(p); - if (entry !== undefined) return entry; - const newEntry = { - base: undefined, - byProperty: undefined, - byValues: undefined +class AsyncQueue { + /** + * @param {Object} options options object + * @param {string=} options.name name of the queue + * @param {number=} options.parallelism how many items should be processed at once + * @param {AsyncQueue=} options.parent parent queue, which will have priority over this queue and with shared parallelism + * @param {function(T): K=} options.getKey extract key from item + * @param {function(T, Callback): void} options.processor async function to process items + */ + constructor({ name, parallelism, parent, processor, getKey }) { + this._name = name; + this._parallelism = parallelism || 1; + this._processor = processor; + this._getKey = + getKey || /** @type {(T) => K} */ (item => /** @type {any} */ (item)); + /** @type {Map>} */ + this._entries = new Map(); + /** @type {ArrayQueue>} */ + this._queued = new ArrayQueue(); + /** @type {AsyncQueue[]} */ + this._children = undefined; + this._activeTasks = 0; + this._willEnsureProcessing = false; + this._needProcessing = false; + this._stopped = false; + this._root = parent ? parent._root : this; + if (parent) { + if (this._root._children === undefined) { + this._root._children = [this]; + } else { + this._root._children.push(this); + } + } + + this.hooks = { + /** @type {AsyncSeriesHook<[T]>} */ + beforeAdd: new AsyncSeriesHook(["item"]), + /** @type {SyncHook<[T]>} */ + added: new SyncHook(["item"]), + /** @type {AsyncSeriesHook<[T]>} */ + beforeStart: new AsyncSeriesHook(["item"]), + /** @type {SyncHook<[T]>} */ + started: new SyncHook(["item"]), + /** @type {SyncHook<[T, Error, R]>} */ + result: new SyncHook(["item", "error", "result"]) }; - info.set(p, newEntry); - return newEntry; - }; - for (const key of Object.keys(obj)) { - if (key.startsWith("by")) { - const byProperty = key; - const byObj = obj[byProperty]; - if (typeof byObj === "object") { - for (const byValue of Object.keys(byObj)) { - const obj = byObj[byValue]; - for (const key of Object.keys(obj)) { - const entry = getInfo(key); - if (entry.byProperty === undefined) { - entry.byProperty = byProperty; - entry.byValues = new Map(); - } else if (entry.byProperty !== byProperty) { - throw new Error( - `${byProperty} and ${entry.byProperty} for a single property is not supported` - ); - } - entry.byValues.set(byValue, obj[key]); - if (byValue === "default") { - for (const otherByValue of Object.keys(byObj)) { - if (!entry.byValues.has(otherByValue)) - entry.byValues.set(otherByValue, undefined); - } - } + + this._ensureProcessing = this._ensureProcessing.bind(this); + } + + /** + * @param {T} item an item + * @param {Callback} callback callback function + * @returns {void} + */ + add(item, callback) { + if (this._stopped) return callback(new WebpackError("Queue was stopped")); + this.hooks.beforeAdd.callAsync(item, err => { + if (err) { + callback( + makeWebpackError(err, `AsyncQueue(${this._name}).hooks.beforeAdd`) + ); + return; + } + const key = this._getKey(item); + const entry = this._entries.get(key); + if (entry !== undefined) { + if (entry.state === DONE_STATE) { + if (inHandleResult++ > 3) { + process.nextTick(() => callback(entry.error, entry.result)); + } else { + callback(entry.error, entry.result); } - } - } else if (typeof byObj === "function") { - if (dynamicInfo === undefined) { - dynamicInfo = { - byProperty: key, - fn: byObj - }; + inHandleResult--; + } else if (entry.callbacks === undefined) { + entry.callbacks = [callback]; } else { - throw new Error( - `${key} and ${dynamicInfo.byProperty} when both are functions is not supported` - ); + entry.callbacks.push(callback); } + return; + } + const newEntry = new AsyncQueueEntry(item, callback); + if (this._stopped) { + this.hooks.added.call(item); + this._root._activeTasks++; + process.nextTick(() => + this._handleResult(newEntry, new WebpackError("Queue was stopped")) + ); } else { - const entry = getInfo(key); - entry.base = obj[key]; + this._entries.set(key, newEntry); + this._queued.enqueue(newEntry); + const root = this._root; + root._needProcessing = true; + if (root._willEnsureProcessing === false) { + root._willEnsureProcessing = true; + setImmediate(root._ensureProcessing); + } + this.hooks.added.call(item); } - } else { - const entry = getInfo(key); - entry.base = obj[key]; - } + }); } - return { - static: info, - dynamic: dynamicInfo - }; -}; -/** - * @param {Map} info static properties (key is property name) - * @param {{ byProperty: string, fn: Function } | undefined} dynamicInfo dynamic part - * @returns {object} the object - */ -const serializeObject = (info, dynamicInfo) => { - const obj = {}; - // Setup byProperty structure - for (const entry of info.values()) { - if (entry.byProperty !== undefined) { - const byObj = (obj[entry.byProperty] = obj[entry.byProperty] || {}); - for (const byValue of entry.byValues.keys()) { - byObj[byValue] = byObj[byValue] || {}; - } + /** + * @param {T} item an item + * @returns {void} + */ + invalidate(item) { + const key = this._getKey(item); + const entry = this._entries.get(key); + this._entries.delete(key); + if (entry.state === QUEUED_STATE) { + this._queued.delete(entry); } } - for (const [key, entry] of info) { - if (entry.base !== undefined) { - obj[key] = entry.base; + + /** + * Waits for an already started item + * @param {T} item an item + * @param {Callback} callback callback function + * @returns {void} + */ + waitFor(item, callback) { + const key = this._getKey(item); + const entry = this._entries.get(key); + if (entry === undefined) { + return callback( + new WebpackError( + "waitFor can only be called for an already started item" + ) + ); } - // Fill byProperty structure - if (entry.byProperty !== undefined) { - const byObj = (obj[entry.byProperty] = obj[entry.byProperty] || {}); - for (const byValue of Object.keys(byObj)) { - const value = getFromByValues(entry.byValues, byValue); - if (value !== undefined) byObj[byValue][key] = value; - } + if (entry.state === DONE_STATE) { + process.nextTick(() => callback(entry.error, entry.result)); + } else if (entry.callbacks === undefined) { + entry.callbacks = [callback]; + } else { + entry.callbacks.push(callback); } } - if (dynamicInfo !== undefined) { - obj[dynamicInfo.byProperty] = dynamicInfo.fn; - } - return obj; -}; -const VALUE_TYPE_UNDEFINED = 0; -const VALUE_TYPE_ATOM = 1; -const VALUE_TYPE_ARRAY_EXTEND = 2; -const VALUE_TYPE_OBJECT = 3; -const VALUE_TYPE_DELETE = 4; - -/** - * @param {any} value a single value - * @returns {VALUE_TYPE_UNDEFINED | VALUE_TYPE_ATOM | VALUE_TYPE_ARRAY_EXTEND | VALUE_TYPE_OBJECT | VALUE_TYPE_DELETE} value type - */ -const getValueType = value => { - if (value === undefined) { - return VALUE_TYPE_UNDEFINED; - } else if (value === DELETE) { - return VALUE_TYPE_DELETE; - } else if (Array.isArray(value)) { - if (value.lastIndexOf("...") !== -1) return VALUE_TYPE_ARRAY_EXTEND; - return VALUE_TYPE_ATOM; - } else if ( - typeof value === "object" && - value !== null && - (!value.constructor || value.constructor === Object) - ) { - return VALUE_TYPE_OBJECT; + /** + * @returns {void} + */ + stop() { + this._stopped = true; + const queue = this._queued; + this._queued = new ArrayQueue(); + const root = this._root; + for (const entry of queue) { + this._entries.delete(this._getKey(entry.item)); + root._activeTasks++; + this._handleResult(entry, new WebpackError("Queue was stopped")); + } } - return VALUE_TYPE_ATOM; -}; - -/** - * Merges two objects. Objects are deeply clever merged. - * Arrays might reference the old value with "...". - * Non-object values take preference over object values. - * @template T - * @template O - * @param {T} first first object - * @param {O} second second object - * @returns {T & O | T | O} merged object of first and second object - */ -const cleverMerge = (first, second) => { - if (second === undefined) return first; - if (first === undefined) return second; - if (typeof second !== "object" || second === null) return second; - if (typeof first !== "object" || first === null) return first; - - return _cleverMerge(first, second, false); -}; - -/** - * Merges two objects. Objects are deeply clever merged. - * @param {object} first first object - * @param {object} second second object - * @param {boolean} internalCaching should parsing of objects and nested merges be cached - * @returns {object} merged object of first and second object - */ -const _cleverMerge = (first, second, internalCaching = false) => { - const firstObject = internalCaching - ? cachedParseObject(first) - : parseObject(first); - const { static: firstInfo, dynamic: firstDynamicInfo } = firstObject; - // If the first argument has a dynamic part we modify the dynamic part to merge the second argument - if (firstDynamicInfo !== undefined) { - let { byProperty, fn } = firstDynamicInfo; - const fnInfo = fn[DYNAMIC_INFO]; - if (fnInfo) { - second = internalCaching - ? cachedCleverMerge(fnInfo[1], second) - : cleverMerge(fnInfo[1], second); - fn = fnInfo[0]; + /** + * @returns {void} + */ + increaseParallelism() { + const root = this._root; + root._parallelism++; + /* istanbul ignore next */ + if (root._willEnsureProcessing === false && root._needProcessing) { + root._willEnsureProcessing = true; + setImmediate(root._ensureProcessing); } - const newFn = (...args) => { - const fnResult = fn(...args); - return internalCaching - ? cachedCleverMerge(fnResult, second) - : cleverMerge(fnResult, second); - }; - newFn[DYNAMIC_INFO] = [fn, second]; - return serializeObject(firstObject.static, { byProperty, fn: newFn }); } - // If the first part is static only, we merge the static parts and keep the dynamic part of the second argument - const secondObject = internalCaching - ? cachedParseObject(second) - : parseObject(second); - const { static: secondInfo, dynamic: secondDynamicInfo } = secondObject; - /** @type {Map} */ - const resultInfo = new Map(); - for (const [key, firstEntry] of firstInfo) { - const secondEntry = secondInfo.get(key); - const entry = - secondEntry !== undefined - ? mergeEntries(firstEntry, secondEntry, internalCaching) - : firstEntry; - resultInfo.set(key, entry); + /** + * @returns {void} + */ + decreaseParallelism() { + const root = this._root; + root._parallelism--; } - for (const [key, secondEntry] of secondInfo) { - if (!firstInfo.has(key)) { - resultInfo.set(key, secondEntry); - } + + /** + * @param {T} item an item + * @returns {boolean} true, if the item is currently being processed + */ + isProcessing(item) { + const key = this._getKey(item); + const entry = this._entries.get(key); + return entry !== undefined && entry.state === PROCESSING_STATE; } - return serializeObject(resultInfo, secondDynamicInfo); -}; -/** - * @param {ObjectParsedPropertyEntry} firstEntry a - * @param {ObjectParsedPropertyEntry} secondEntry b - * @param {boolean} internalCaching should parsing of objects and nested merges be cached - * @returns {ObjectParsedPropertyEntry} new entry - */ -const mergeEntries = (firstEntry, secondEntry, internalCaching) => { - switch (getValueType(secondEntry.base)) { - case VALUE_TYPE_ATOM: - case VALUE_TYPE_DELETE: - // No need to consider firstEntry at all - // second value override everything - // = second.base + second.byProperty - return secondEntry; - case VALUE_TYPE_UNDEFINED: - if (!firstEntry.byProperty) { - // = first.base + second.byProperty - return { - base: firstEntry.base, - byProperty: secondEntry.byProperty, - byValues: secondEntry.byValues - }; - } else if (firstEntry.byProperty !== secondEntry.byProperty) { - throw new Error( - `${firstEntry.byProperty} and ${secondEntry.byProperty} for a single property is not supported` - ); - } else { - // = first.base + (first.byProperty + second.byProperty) - // need to merge first and second byValues - const newByValues = new Map(firstEntry.byValues); - for (const [key, value] of secondEntry.byValues) { - const firstValue = getFromByValues(firstEntry.byValues, key); - newByValues.set( - key, - mergeSingleValue(firstValue, value, internalCaching) - ); + /** + * @param {T} item an item + * @returns {boolean} true, if the item is currently queued + */ + isQueued(item) { + const key = this._getKey(item); + const entry = this._entries.get(key); + return entry !== undefined && entry.state === QUEUED_STATE; + } + + /** + * @param {T} item an item + * @returns {boolean} true, if the item is currently queued + */ + isDone(item) { + const key = this._getKey(item); + const entry = this._entries.get(key); + return entry !== undefined && entry.state === DONE_STATE; + } + + /** + * @returns {void} + */ + _ensureProcessing() { + while (this._activeTasks < this._parallelism) { + const entry = this._queued.dequeue(); + if (entry === undefined) break; + this._activeTasks++; + entry.state = PROCESSING_STATE; + this._startProcessing(entry); + } + this._willEnsureProcessing = false; + if (this._queued.length > 0) return; + if (this._children !== undefined) { + for (const child of this._children) { + while (this._activeTasks < this._parallelism) { + const entry = child._queued.dequeue(); + if (entry === undefined) break; + this._activeTasks++; + entry.state = PROCESSING_STATE; + child._startProcessing(entry); } - return { - base: firstEntry.base, - byProperty: firstEntry.byProperty, - byValues: newByValues - }; - } - default: { - if (!firstEntry.byProperty) { - // The simple case - // = (first.base + second.base) + second.byProperty - return { - base: mergeSingleValue( - firstEntry.base, - secondEntry.base, - internalCaching - ), - byProperty: secondEntry.byProperty, - byValues: secondEntry.byValues - }; - } - let newBase; - const intermediateByValues = new Map(firstEntry.byValues); - for (const [key, value] of intermediateByValues) { - intermediateByValues.set( - key, - mergeSingleValue(value, secondEntry.base, internalCaching) - ); - } - if ( - Array.from(firstEntry.byValues.values()).every(value => { - const type = getValueType(value); - return type === VALUE_TYPE_ATOM || type === VALUE_TYPE_DELETE; - }) - ) { - // = (first.base + second.base) + ((first.byProperty + second.base) + second.byProperty) - newBase = mergeSingleValue( - firstEntry.base, - secondEntry.base, - internalCaching - ); - } else { - // = first.base + ((first.byProperty (+default) + second.base) + second.byProperty) - newBase = firstEntry.base; - if (!intermediateByValues.has("default")) - intermediateByValues.set("default", secondEntry.base); + if (child._queued.length > 0) return; } - if (!secondEntry.byProperty) { - // = first.base + (first.byProperty + second.base) - return { - base: newBase, - byProperty: firstEntry.byProperty, - byValues: intermediateByValues - }; - } else if (firstEntry.byProperty !== secondEntry.byProperty) { - throw new Error( - `${firstEntry.byProperty} and ${secondEntry.byProperty} for a single property is not supported` + } + if (!this._willEnsureProcessing) this._needProcessing = false; + } + + /** + * @param {AsyncQueueEntry} entry the entry + * @returns {void} + */ + _startProcessing(entry) { + this.hooks.beforeStart.callAsync(entry.item, err => { + if (err) { + this._handleResult( + entry, + makeWebpackError(err, `AsyncQueue(${this._name}).hooks.beforeStart`) ); + return; } - const newByValues = new Map(intermediateByValues); - for (const [key, value] of secondEntry.byValues) { - const firstValue = getFromByValues(intermediateByValues, key); - newByValues.set( - key, - mergeSingleValue(firstValue, value, internalCaching) - ); + let inCallback = false; + try { + this._processor(entry.item, (e, r) => { + inCallback = true; + this._handleResult(entry, e, r); + }); + } catch (err) { + if (inCallback) throw err; + this._handleResult(entry, err, null); } - return { - base: newBase, - byProperty: firstEntry.byProperty, - byValues: newByValues - }; - } + this.hooks.started.call(entry.item); + }); } -}; -/** - * @param {Map} byValues all values - * @param {string} key value of the selector - * @returns {any | undefined} value - */ -const getFromByValues = (byValues, key) => { - if (key !== "default" && byValues.has(key)) { - return byValues.get(key); - } - return byValues.get("default"); -}; + /** + * @param {AsyncQueueEntry} entry the entry + * @param {WebpackError=} err error, if any + * @param {R=} result result, if any + * @returns {void} + */ + _handleResult(entry, err, result) { + this.hooks.result.callAsync(entry.item, err, result, hookError => { + const error = hookError + ? makeWebpackError(hookError, `AsyncQueue(${this._name}).hooks.result`) + : err; -/** - * @param {any} a value - * @param {any} b value - * @param {boolean} internalCaching should parsing of objects and nested merges be cached - * @returns {any} value - */ -const mergeSingleValue = (a, b, internalCaching) => { - const bType = getValueType(b); - const aType = getValueType(a); - switch (bType) { - case VALUE_TYPE_DELETE: - case VALUE_TYPE_ATOM: - return b; - case VALUE_TYPE_OBJECT: { - return aType !== VALUE_TYPE_OBJECT - ? b - : internalCaching - ? cachedCleverMerge(a, b) - : cleverMerge(a, b); - } - case VALUE_TYPE_UNDEFINED: - return a; - case VALUE_TYPE_ARRAY_EXTEND: - switch ( - aType !== VALUE_TYPE_ATOM - ? aType - : Array.isArray(a) - ? VALUE_TYPE_ARRAY_EXTEND - : VALUE_TYPE_OBJECT - ) { - case VALUE_TYPE_UNDEFINED: - return b; - case VALUE_TYPE_DELETE: - return b.filter(item => item !== "..."); - case VALUE_TYPE_ARRAY_EXTEND: { - const newArray = []; - for (const item of b) { - if (item === "...") { - for (const item of a) { - newArray.push(item); - } - } else { - newArray.push(item); + const callback = entry.callback; + const callbacks = entry.callbacks; + entry.state = DONE_STATE; + entry.callback = undefined; + entry.callbacks = undefined; + entry.result = result; + entry.error = error; + + const root = this._root; + root._activeTasks--; + if (root._willEnsureProcessing === false && root._needProcessing) { + root._willEnsureProcessing = true; + setImmediate(root._ensureProcessing); + } + + if (inHandleResult++ > 3) { + process.nextTick(() => { + callback(error, result); + if (callbacks !== undefined) { + for (const callback of callbacks) { + callback(error, result); } } - return newArray; + }); + } else { + callback(error, result); + if (callbacks !== undefined) { + for (const callback of callbacks) { + callback(error, result); + } } - case VALUE_TYPE_OBJECT: - return b.map(item => (item === "..." ? a : item)); - default: - throw new Error("Not implemented"); } - default: - throw new Error("Not implemented"); - } -}; - -/** - * @template T - * @param {T} obj the object - * @returns {T} the object without operations like "..." or DELETE - */ -const removeOperations = obj => { - const newObj = /** @type {T} */ ({}); - for (const key of Object.keys(obj)) { - const value = obj[key]; - const type = getValueType(value); - switch (type) { - case VALUE_TYPE_UNDEFINED: - case VALUE_TYPE_DELETE: - break; - case VALUE_TYPE_OBJECT: - newObj[key] = removeOperations(value); - break; - case VALUE_TYPE_ARRAY_EXTEND: - newObj[key] = value.filter(i => i !== "..."); - break; - default: - newObj[key] = value; - break; - } + inHandleResult--; + }); } - return newObj; -}; -/** - * @template T - * @template {string} P - * @param {T} obj the object - * @param {P} byProperty the by description - * @param {...any} values values - * @returns {Omit} object with merged byProperty - */ -const resolveByProperty = (obj, byProperty, ...values) => { - if (typeof obj !== "object" || obj === null || !(byProperty in obj)) { - return obj; - } - const { [byProperty]: _byValue, ..._remaining } = /** @type {object} */ (obj); - const remaining = /** @type {T} */ (_remaining); - const byValue = /** @type {Record | function(...any[]): T} */ ( - _byValue - ); - if (typeof byValue === "object") { - const key = values[0]; - if (key in byValue) { - return cachedCleverMerge(remaining, byValue[key]); - } else if ("default" in byValue) { - return cachedCleverMerge(remaining, byValue.default); - } else { - return /** @type {T} */ (remaining); - } - } else if (typeof byValue === "function") { - const result = byValue.apply(null, values); - return cachedCleverMerge( - remaining, - resolveByProperty(result, byProperty, ...values) - ); + clear() { + this._entries.clear(); + this._queued.clear(); + this._activeTasks = 0; + this._willEnsureProcessing = false; + this._needProcessing = false; + this._stopped = false; } -}; +} -exports.cachedSetProperty = cachedSetProperty; -exports.cachedCleverMerge = cachedCleverMerge; -exports.cleverMerge = cleverMerge; -exports.resolveByProperty = resolveByProperty; -exports.removeOperations = removeOperations; -exports.DELETE = DELETE; +module.exports = AsyncQueue; /***/ }), -/***/ 26296: -/***/ (function(__unused_webpack_module, exports, __webpack_require__) { +/***/ 21301: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; /* @@ -125372,464 +124711,338 @@ exports.DELETE = DELETE; -const { compareRuntime } = __webpack_require__(19655); - -/** @typedef {import("../Chunk")} Chunk */ -/** @typedef {import("../ChunkGraph")} ChunkGraph */ -/** @typedef {import("../ChunkGroup")} ChunkGroup */ -/** @typedef {import("../Dependency").DependencyLocation} DependencyLocation */ -/** @typedef {import("../Module")} Module */ -/** @typedef {import("../ModuleGraph")} ModuleGraph */ - -/** @template T @typedef {function(T, T): -1|0|1} Comparator */ -/** @template TArg @template T @typedef {function(TArg, T, T): -1|0|1} RawParameterizedComparator */ -/** @template TArg @template T @typedef {function(TArg): Comparator} ParameterizedComparator */ - -/** - * @template T - * @param {RawParameterizedComparator} fn comparator with argument - * @returns {ParameterizedComparator} comparator - */ -const createCachedParameterizedComparator = fn => { - /** @type {WeakMap>} */ - const map = new WeakMap(); - return arg => { - const cachedResult = map.get(arg); - if (cachedResult !== undefined) return cachedResult; - /** - * @param {T} a first item - * @param {T} b second item - * @returns {-1|0|1} compare result - */ - const result = fn.bind(null, arg); - map.set(arg, result); - return result; - }; -}; +class Hash { + /* istanbul ignore next */ + /** + * Update hash {@link https://nodejs.org/api/crypto.html#crypto_hash_update_data_inputencoding} + * @abstract + * @param {string|Buffer} data data + * @param {string=} inputEncoding data encoding + * @returns {this} updated hash + */ + update(data, inputEncoding) { + const AbstractMethodError = __webpack_require__(570); + throw new AbstractMethodError(); + } -/** - * @param {Chunk} a chunk - * @param {Chunk} b chunk - * @returns {-1|0|1} compare result - */ -exports.compareChunksById = (a, b) => { - return compareIds(a.id, b.id); -}; + /* istanbul ignore next */ + /** + * Calculates the digest {@link https://nodejs.org/api/crypto.html#crypto_hash_digest_encoding} + * @abstract + * @param {string=} encoding encoding of the return value + * @returns {string|Buffer} digest + */ + digest(encoding) { + const AbstractMethodError = __webpack_require__(570); + throw new AbstractMethodError(); + } +} -/** - * @param {Module} a module - * @param {Module} b module - * @returns {-1|0|1} compare result - */ -exports.compareModulesByIdentifier = (a, b) => { - return compareIds(a.identifier(), b.identifier()); -}; +module.exports = Hash; -/** - * @param {ChunkGraph} chunkGraph the chunk graph - * @param {Module} a module - * @param {Module} b module - * @returns {-1|0|1} compare result - */ -const compareModulesById = (chunkGraph, a, b) => { - return compareIds(chunkGraph.getModuleId(a), chunkGraph.getModuleId(b)); -}; -/** @type {ParameterizedComparator} */ -exports.compareModulesById = - createCachedParameterizedComparator(compareModulesById); -/** - * @param {number} a number - * @param {number} b number - * @returns {-1|0|1} compare result - */ -const compareNumbers = (a, b) => { - if (typeof a !== typeof b) { - return typeof a < typeof b ? -1 : 1; - } - if (a < b) return -1; - if (a > b) return 1; - return 0; -}; -exports.compareNumbers = compareNumbers; +/***/ }), -/** - * @param {string} a string - * @param {string} b string - * @returns {-1|0|1} compare result - */ -const compareStringsNumeric = (a, b) => { - const partsA = a.split(/(\d+)/); - const partsB = b.split(/(\d+)/); - const len = Math.min(partsA.length, partsB.length); - for (let i = 0; i < len; i++) { - const pA = partsA[i]; - const pB = partsB[i]; - if (i % 2 === 0) { - if (pA.length > pB.length) { - if (pA.slice(0, pB.length) > pB) return 1; - return -1; - } else if (pB.length > pA.length) { - if (pB.slice(0, pA.length) > pA) return -1; - return 1; - } else { - if (pA < pB) return -1; - if (pA > pB) return 1; - } - } else { - const nA = +pA; - const nB = +pB; - if (nA < nB) return -1; - if (nA > nB) return 1; - } - } - if (partsB.length < partsA.length) return 1; - if (partsB.length > partsA.length) return -1; - return 0; -}; -exports.compareStringsNumeric = compareStringsNumeric; +/***/ 31065: +/***/ (function(__unused_webpack_module, exports) { -/** - * @param {ModuleGraph} moduleGraph the module graph - * @param {Module} a module - * @param {Module} b module - * @returns {-1|0|1} compare result - */ -const compareModulesByPostOrderIndexOrIdentifier = (moduleGraph, a, b) => { - const cmp = compareNumbers( - moduleGraph.getPostOrderIndex(a), - moduleGraph.getPostOrderIndex(b) - ); - if (cmp !== 0) return cmp; - return compareIds(a.identifier(), b.identifier()); -}; -/** @type {ParameterizedComparator} */ -exports.compareModulesByPostOrderIndexOrIdentifier = - createCachedParameterizedComparator( - compareModulesByPostOrderIndexOrIdentifier - ); +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ -/** - * @param {ModuleGraph} moduleGraph the module graph - * @param {Module} a module - * @param {Module} b module - * @returns {-1|0|1} compare result - */ -const compareModulesByPreOrderIndexOrIdentifier = (moduleGraph, a, b) => { - const cmp = compareNumbers( - moduleGraph.getPreOrderIndex(a), - moduleGraph.getPreOrderIndex(b) - ); - if (cmp !== 0) return cmp; - return compareIds(a.identifier(), b.identifier()); -}; -/** @type {ParameterizedComparator} */ -exports.compareModulesByPreOrderIndexOrIdentifier = - createCachedParameterizedComparator( - compareModulesByPreOrderIndexOrIdentifier - ); -/** - * @param {ChunkGraph} chunkGraph the chunk graph - * @param {Module} a module - * @param {Module} b module - * @returns {-1|0|1} compare result - */ -const compareModulesByIdOrIdentifier = (chunkGraph, a, b) => { - const cmp = compareIds(chunkGraph.getModuleId(a), chunkGraph.getModuleId(b)); - if (cmp !== 0) return cmp; - return compareIds(a.identifier(), b.identifier()); -}; -/** @type {ParameterizedComparator} */ -exports.compareModulesByIdOrIdentifier = createCachedParameterizedComparator( - compareModulesByIdOrIdentifier -); /** - * @param {ChunkGraph} chunkGraph the chunk graph - * @param {Chunk} a chunk - * @param {Chunk} b chunk - * @returns {-1|0|1} compare result + * @template T + * @param {Iterable} set a set + * @returns {T | undefined} last item */ -const compareChunks = (chunkGraph, a, b) => { - return chunkGraph.compareChunks(a, b); +const last = set => { + let last; + for (const item of set) last = item; + return last; }; -/** @type {ParameterizedComparator} */ -exports.compareChunks = createCachedParameterizedComparator(compareChunks); /** - * @param {string|number} a first id - * @param {string|number} b second id - * @returns {-1|0|1} compare result + * @template T + * @param {Iterable} iterable iterable + * @param {function(T): boolean} filter predicate + * @returns {boolean} true, if some items match the filter predicate */ -const compareIds = (a, b) => { - if (typeof a !== typeof b) { - return typeof a < typeof b ? -1 : 1; +const someInIterable = (iterable, filter) => { + for (const item of iterable) { + if (filter(item)) return true; } - if (a < b) return -1; - if (a > b) return 1; - return 0; + return false; }; -exports.compareIds = compareIds; - /** - * @param {string} a first string - * @param {string} b second string - * @returns {-1|0|1} compare result + * @template T + * @param {Iterable} iterable an iterable + * @returns {number} count of items */ -const compareStrings = (a, b) => { - if (a < b) return -1; - if (a > b) return 1; - return 0; +const countIterable = iterable => { + let i = 0; + // eslint-disable-next-line no-unused-vars + for (const _ of iterable) i++; + return i; }; -exports.compareStrings = compareStrings; +exports.last = last; +exports.someInIterable = someInIterable; +exports.countIterable = countIterable; -/** - * @param {ChunkGroup} a first chunk group - * @param {ChunkGroup} b second chunk group - * @returns {-1|0|1} compare result - */ -const compareChunkGroupsByIndex = (a, b) => { - return a.index < b.index ? -1 : 1; -}; -exports.compareChunkGroupsByIndex = compareChunkGroupsByIndex; +/***/ }), + +/***/ 79300: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ + + + +const { first } = __webpack_require__(34715); +const SortableSet = __webpack_require__(67563); /** - * @template K1 {Object} - * @template K2 + * Multi layer bucket sorted set: + * Supports adding non-existing items (DO NOT ADD ITEM TWICE), + * Supports removing exiting items (DO NOT REMOVE ITEM NOT IN SET), + * Supports popping the first items according to defined order, + * Supports iterating all items without order, + * Supports updating an item in an efficient way, + * Supports size property, which is the number of items, + * Items are lazy partially sorted when needed * @template T + * @template K */ -class TwoKeyWeakMap { - constructor() { - /** @private @type {WeakMap>} */ - this._map = new WeakMap(); +class LazyBucketSortedSet { + /** + * @param {function(T): K} getKey function to get key from item + * @param {function(K, K): number} comparator comparator to sort keys + * @param {...((function(T): any) | (function(any, any): number))} args more pairs of getKey and comparator plus optional final comparator for the last layer + */ + constructor(getKey, comparator, ...args) { + this._getKey = getKey; + this._innerArgs = args; + this._leaf = args.length <= 1; + this._keys = new SortableSet(undefined, comparator); + /** @type {Map | SortableSet>} */ + this._map = new Map(); + this._unsortedItems = new Set(); + this.size = 0; } /** - * @param {K1} key1 first key - * @param {K2} key2 second key - * @returns {T | undefined} value + * @param {T} item an item + * @returns {void} */ - get(key1, key2) { - const childMap = this._map.get(key1); - if (childMap === undefined) { - return undefined; - } - return childMap.get(key2); + add(item) { + this.size++; + this._unsortedItems.add(item); } /** - * @param {K1} key1 first key - * @param {K2} key2 second key - * @param {T | undefined} value new value + * @param {K} key key of item + * @param {T} item the item * @returns {void} */ - set(key1, key2, value) { - let childMap = this._map.get(key1); - if (childMap === undefined) { - childMap = new WeakMap(); - this._map.set(key1, childMap); + _addInternal(key, item) { + let entry = this._map.get(key); + if (entry === undefined) { + entry = this._leaf + ? new SortableSet(undefined, this._innerArgs[0]) + : new /** @type {any} */ (LazyBucketSortedSet)(...this._innerArgs); + this._keys.add(key); + this._map.set(key, entry); } - childMap.set(key2, value); + entry.add(item); } -} - -/** @type {TwoKeyWeakMap, Comparator, Comparator>}} */ -const concatComparatorsCache = new TwoKeyWeakMap(); -/** - * @template T - * @param {Comparator} c1 comparator - * @param {Comparator} c2 comparator - * @param {Comparator[]} cRest comparators - * @returns {Comparator} comparator - */ -const concatComparators = (c1, c2, ...cRest) => { - if (cRest.length > 0) { - const [c3, ...cRest2] = cRest; - return concatComparators(c1, concatComparators(c2, c3, ...cRest2)); - } - const cacheEntry = /** @type {Comparator} */ ( - concatComparatorsCache.get(c1, c2) - ); - if (cacheEntry !== undefined) return cacheEntry; /** - * @param {T} a first value - * @param {T} b second value - * @returns {-1|0|1} compare result + * @param {T} item an item + * @returns {void} */ - const result = (a, b) => { - const res = c1(a, b); - if (res !== 0) return res; - return c2(a, b); - }; - concatComparatorsCache.set(c1, c2, result); - return result; -}; -exports.concatComparators = concatComparators; - -/** @template A, B @typedef {(input: A) => B} Selector */ + delete(item) { + this.size--; + if (this._unsortedItems.has(item)) { + this._unsortedItems.delete(item); + return; + } + const key = this._getKey(item); + const entry = this._map.get(key); + entry.delete(item); + if (entry.size === 0) { + this._deleteKey(key); + } + } -/** @type {TwoKeyWeakMap, Comparator, Comparator>}} */ -const compareSelectCache = new TwoKeyWeakMap(); + /** + * @param {K} key key to be removed + * @returns {void} + */ + _deleteKey(key) { + this._keys.delete(key); + this._map.delete(key); + } -/** - * @template T - * @template R - * @param {Selector} getter getter for value - * @param {Comparator} comparator comparator - * @returns {Comparator} comparator - */ -const compareSelect = (getter, comparator) => { - const cacheEntry = compareSelectCache.get(getter, comparator); - if (cacheEntry !== undefined) return cacheEntry; /** - * @param {T} a first value - * @param {T} b second value - * @returns {-1|0|1} compare result + * @returns {T | undefined} an item */ - const result = (a, b) => { - const aValue = getter(a); - const bValue = getter(b); - if (aValue !== undefined && aValue !== null) { - if (bValue !== undefined && bValue !== null) { - return comparator(aValue, bValue); + popFirst() { + if (this.size === 0) return undefined; + this.size--; + if (this._unsortedItems.size > 0) { + for (const item of this._unsortedItems) { + const key = this._getKey(item); + this._addInternal(key, item); } - return -1; + this._unsortedItems.clear(); + } + this._keys.sort(); + const key = first(this._keys); + const entry = this._map.get(key); + if (this._leaf) { + const leafEntry = /** @type {SortableSet} */ (entry); + leafEntry.sort(); + const item = first(leafEntry); + leafEntry.delete(item); + if (leafEntry.size === 0) { + this._deleteKey(key); + } + return item; } else { - if (bValue !== undefined && bValue !== null) { - return 1; + const nodeEntry = /** @type {LazyBucketSortedSet} */ (entry); + const item = nodeEntry.popFirst(); + if (nodeEntry.size === 0) { + this._deleteKey(key); } - return 0; + return item; } - }; - compareSelectCache.set(getter, comparator, result); - return result; -}; -exports.compareSelect = compareSelect; + } -/** @type {WeakMap, Comparator>>} */ -const compareIteratorsCache = new WeakMap(); + /** + * @param {T} item to be updated item + * @returns {function(true=): void} finish update + */ + startUpdate(item) { + if (this._unsortedItems.has(item)) { + return remove => { + if (remove) { + this._unsortedItems.delete(item); + this.size--; + return; + } + }; + } + const key = this._getKey(item); + if (this._leaf) { + const oldEntry = /** @type {SortableSet} */ (this._map.get(key)); + return remove => { + if (remove) { + this.size--; + oldEntry.delete(item); + if (oldEntry.size === 0) { + this._deleteKey(key); + } + return; + } + const newKey = this._getKey(item); + if (key === newKey) { + // This flags the sortable set as unordered + oldEntry.add(item); + } else { + oldEntry.delete(item); + if (oldEntry.size === 0) { + this._deleteKey(key); + } + this._addInternal(newKey, item); + } + }; + } else { + const oldEntry = /** @type {LazyBucketSortedSet} */ ( + this._map.get(key) + ); + const finishUpdate = oldEntry.startUpdate(item); + return remove => { + if (remove) { + this.size--; + finishUpdate(true); + if (oldEntry.size === 0) { + this._deleteKey(key); + } + return; + } + const newKey = this._getKey(item); + if (key === newKey) { + finishUpdate(); + } else { + finishUpdate(true); + if (oldEntry.size === 0) { + this._deleteKey(key); + } + this._addInternal(newKey, item); + } + }; + } + } -/** - * @template T - * @param {Comparator} elementComparator comparator for elements - * @returns {Comparator>} comparator for iterables of elements - */ -const compareIterables = elementComparator => { - const cacheEntry = compareIteratorsCache.get(elementComparator); - if (cacheEntry !== undefined) return cacheEntry; /** - * @param {Iterable} a first value - * @param {Iterable} b second value - * @returns {-1|0|1} compare result + * @param {Iterator[]} iterators list of iterators to append to + * @returns {void} */ - const result = (a, b) => { - const aI = a[Symbol.iterator](); - const bI = b[Symbol.iterator](); - // eslint-disable-next-line no-constant-condition - while (true) { - const aItem = aI.next(); - const bItem = bI.next(); - if (aItem.done) { - return bItem.done ? 0 : -1; - } else if (bItem.done) { - return 1; + _appendIterators(iterators) { + if (this._unsortedItems.size > 0) + iterators.push(this._unsortedItems[Symbol.iterator]()); + for (const key of this._keys) { + const entry = this._map.get(key); + if (this._leaf) { + const leafEntry = /** @type {SortableSet} */ (entry); + const iterator = leafEntry[Symbol.iterator](); + iterators.push(iterator); + } else { + const nodeEntry = /** @type {LazyBucketSortedSet} */ (entry); + nodeEntry._appendIterators(iterators); } - const res = elementComparator(aItem.value, bItem.value); - if (res !== 0) return res; } - }; - compareIteratorsCache.set(elementComparator, result); - return result; -}; -exports.compareIterables = compareIterables; - -// TODO this is no longer needed when minimum node.js version is >= 12 -// since these versions ship with a stable sort function -/** - * @template T - * @param {Iterable} iterable original ordered list - * @returns {Comparator} comparator - */ -exports.keepOriginalOrder = iterable => { - /** @type {Map} */ - const map = new Map(); - let i = 0; - for (const item of iterable) { - map.set(item, i++); } - return (a, b) => compareNumbers(map.get(a), map.get(b)); -}; - -/** - * @param {ChunkGraph} chunkGraph the chunk graph - * @returns {Comparator} comparator - */ -exports.compareChunksNatural = chunkGraph => { - const cmpFn = exports.compareModulesById(chunkGraph); - const cmpIterableFn = compareIterables(cmpFn); - return concatComparators( - compareSelect(chunk => chunk.name, compareIds), - compareSelect(chunk => chunk.runtime, compareRuntime), - compareSelect( - /** - * @param {Chunk} chunk a chunk - * @returns {Iterable} modules - */ - chunk => chunkGraph.getOrderedChunkModulesIterable(chunk, cmpFn), - cmpIterableFn - ) - ); -}; -/** - * Compare two locations - * @param {DependencyLocation} a A location node - * @param {DependencyLocation} b A location node - * @returns {-1|0|1} sorting comparator value - */ -exports.compareLocations = (a, b) => { - let isObjectA = typeof a === "object" && a !== null; - let isObjectB = typeof b === "object" && b !== null; - if (!isObjectA || !isObjectB) { - if (isObjectA) return 1; - if (isObjectB) return -1; - return 0; + /** + * @returns {Iterator} the iterator + */ + [Symbol.iterator]() { + const iterators = []; + this._appendIterators(iterators); + iterators.reverse(); + let currentIterator = iterators.pop(); + return { + next: () => { + const res = currentIterator.next(); + if (res.done) { + if (iterators.length === 0) return res; + currentIterator = iterators.pop(); + return currentIterator.next(); + } + return res; + } + }; } - if ("start" in a) { - if ("start" in b) { - const ap = a.start; - const bp = b.start; - if (ap.line < bp.line) return -1; - if (ap.line > bp.line) return 1; - if (ap.column < bp.column) return -1; - if (ap.column > bp.column) return 1; - } else return -1; - } else if ("start" in b) return 1; - if ("name" in a) { - if ("name" in b) { - if (a.name < b.name) return -1; - if (a.name > b.name) return 1; - } else return -1; - } else if ("name" in b) return 1; - if ("index" in a) { - if ("index" in b) { - if (a.index < b.index) return -1; - if (a.index > b.index) return 1; - } else return -1; - } else if ("index" in b) return 1; - return 0; -}; +} + +module.exports = LazyBucketSortedSet; /***/ }), -/***/ 356: -/***/ (function(module) { +/***/ 59534: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; /* @@ -125839,211 +125052,213 @@ exports.compareLocations = (a, b) => { -const quoteMeta = str => { - return str.replace(/[-[\]\\/{}()*+?.^$|]/g, "\\$&"); -}; +const makeSerializable = __webpack_require__(26522); + +/** + * @template T + * @param {Set} targetSet set where items should be added + * @param {Set>} toMerge iterables to be merged + * @returns {void} + */ +const merge = (targetSet, toMerge) => { + for (const set of toMerge) { + for (const item of set) { + targetSet.add(item); + } + } +}; + +/** + * @template T + * @param {Set>} targetSet set where iterables should be added + * @param {Array>} toDeepMerge lazy sets to be flattened + * @returns {void} + */ +const flatten = (targetSet, toDeepMerge) => { + for (const set of toDeepMerge) { + if (set._set.size > 0) targetSet.add(set._set); + if (set._needMerge) { + for (const mergedSet of set._toMerge) { + targetSet.add(mergedSet); + } + flatten(targetSet, set._toDeepMerge); + } + } +}; + +/** + * Like Set but with an addAll method to eventually add items from another iterable. + * Access methods make sure that all delayed operations are executed. + * Iteration methods deopts to normal Set performance until clear is called again (because of the chance of modifications during iteration). + * @template T + */ +class LazySet { + /** + * @param {Iterable=} iterable init iterable + */ + constructor(iterable) { + /** @type {Set} */ + this._set = new Set(iterable); + /** @type {Set>} */ + this._toMerge = new Set(); + /** @type {Array>} */ + this._toDeepMerge = []; + this._needMerge = false; + this._deopt = false; + } + + _flatten() { + flatten(this._toMerge, this._toDeepMerge); + this._toDeepMerge.length = 0; + } + + _merge() { + this._flatten(); + merge(this._set, this._toMerge); + this._toMerge.clear(); + this._needMerge = false; + } -const toSimpleString = str => { - if (`${+str}` === str) { - return str; + _isEmpty() { + return ( + this._set.size === 0 && + this._toMerge.size === 0 && + this._toDeepMerge.length === 0 + ); } - return JSON.stringify(str); -}; -/** - * @param {Record} map value map - * @returns {true|false|function(string): string} true/false, when unconditionally true/false, or a template function to determine the value at runtime - */ -const compileBooleanMatcher = map => { - const positiveItems = Object.keys(map).filter(i => map[i]); - const negativeItems = Object.keys(map).filter(i => !map[i]); - if (positiveItems.length === 0) return false; - if (negativeItems.length === 0) return true; - return compileBooleanMatcherFromLists(positiveItems, negativeItems); -}; + get size() { + if (this._needMerge) this._merge(); + return this._set.size; + } -/** - * @param {string[]} positiveItems positive items - * @param {string[]} negativeItems negative items - * @returns {function(string): string} a template function to determine the value at runtime - */ -const compileBooleanMatcherFromLists = (positiveItems, negativeItems) => { - if (positiveItems.length === 0) return () => "false"; - if (negativeItems.length === 0) return () => "true"; - if (positiveItems.length === 1) - return value => `${toSimpleString(positiveItems[0])} == ${value}`; - if (negativeItems.length === 1) - return value => `${toSimpleString(negativeItems[0])} != ${value}`; - const positiveRegexp = itemsToRegexp(positiveItems); - const negativeRegexp = itemsToRegexp(negativeItems); - if (positiveRegexp.length <= negativeRegexp.length) { - return value => `/^${positiveRegexp}$/.test(${value})`; - } else { - return value => `!/^${negativeRegexp}$/.test(${value})`; + /** + * @param {T} item an item + * @returns {this} itself + */ + add(item) { + this._set.add(item); + return this; } -}; -const popCommonItems = (itemsSet, getKey, condition) => { - const map = new Map(); - for (const item of itemsSet) { - const key = getKey(item); - if (key) { - let list = map.get(key); - if (list === undefined) { - list = []; - map.set(key, list); + /** + * @param {Iterable | LazySet} iterable a immutable iterable or another immutable LazySet which will eventually be merged into the Set + * @returns {this} itself + */ + addAll(iterable) { + if (this._deopt) { + const _set = this._set; + for (const item of iterable) { + _set.add(item); } - list.push(item); - } - } - const result = []; - for (const list of map.values()) { - if (condition(list)) { - for (const item of list) { - itemsSet.delete(item); + } else { + if (iterable instanceof LazySet) { + if (iterable._isEmpty()) return this; + this._toDeepMerge.push(iterable); + this._needMerge = true; + if (this._toDeepMerge.length > 100000) { + this._flatten(); + } + } else { + this._toMerge.add(iterable); + this._needMerge = true; } - result.push(list); + if (this._toMerge.size > 100000) this._merge(); } + return this; } - return result; -}; -const getCommonPrefix = items => { - let prefix = items[0]; - for (let i = 1; i < items.length; i++) { - const item = items[i]; - for (let p = 0; p < prefix.length; p++) { - if (item[p] !== prefix[p]) { - prefix = prefix.slice(0, p); - break; - } - } + clear() { + this._set.clear(); + this._toMerge.clear(); + this._toDeepMerge.length = 0; + this._needMerge = false; + this._deopt = false; } - return prefix; -}; -const getCommonSuffix = items => { - let suffix = items[0]; - for (let i = 1; i < items.length; i++) { - const item = items[i]; - for (let p = item.length - 1, s = suffix.length - 1; s >= 0; p--, s--) { - if (item[p] !== suffix[s]) { - suffix = suffix.slice(s + 1); - break; - } - } + /** + * @param {T} value an item + * @returns {boolean} true, if the value was in the Set before + */ + delete(value) { + if (this._needMerge) this._merge(); + return this._set.delete(value); } - return suffix; -}; -const itemsToRegexp = itemsArr => { - if (itemsArr.length === 1) { - return quoteMeta(itemsArr[0]); + entries() { + this._deopt = true; + if (this._needMerge) this._merge(); + return this._set.entries(); } - const finishedItems = []; - // merge single char items: (a|b|c|d|ef) => ([abcd]|ef) - let countOfSingleCharItems = 0; - for (const item of itemsArr) { - if (item.length === 1) { - countOfSingleCharItems++; - } + /** + * @param {function(T, T, Set): void} callbackFn function called for each entry + * @param {any} thisArg this argument for the callbackFn + * @returns {void} + */ + forEach(callbackFn, thisArg) { + this._deopt = true; + if (this._needMerge) this._merge(); + this._set.forEach(callbackFn, thisArg); } - // special case for only single char items - if (countOfSingleCharItems === itemsArr.length) { - return `[${quoteMeta(itemsArr.sort().join(""))}]`; + + /** + * @param {T} item an item + * @returns {boolean} true, when the item is in the Set + */ + has(item) { + if (this._needMerge) this._merge(); + return this._set.has(item); } - const items = new Set(itemsArr.sort()); - if (countOfSingleCharItems > 2) { - let singleCharItems = ""; - for (const item of items) { - if (item.length === 1) { - singleCharItems += item; - items.delete(item); - } - } - finishedItems.push(`[${quoteMeta(singleCharItems)}]`); + + keys() { + this._deopt = true; + if (this._needMerge) this._merge(); + return this._set.keys(); } - // special case for 2 items with common prefix/suffix - if (finishedItems.length === 0 && items.size === 2) { - const prefix = getCommonPrefix(itemsArr); - const suffix = getCommonSuffix( - itemsArr.map(item => item.slice(prefix.length)) - ); - if (prefix.length > 0 || suffix.length > 0) { - return `${quoteMeta(prefix)}${itemsToRegexp( - itemsArr.map(i => i.slice(prefix.length, -suffix.length || undefined)) - )}${quoteMeta(suffix)}`; - } + values() { + this._deopt = true; + if (this._needMerge) this._merge(); + return this._set.values(); } - // special case for 2 items with common suffix - if (finishedItems.length === 0 && items.size === 2) { - const it = items[Symbol.iterator](); - const a = it.next().value; - const b = it.next().value; - if (a.length > 0 && b.length > 0 && a.slice(-1) === b.slice(-1)) { - return `${itemsToRegexp([a.slice(0, -1), b.slice(0, -1)])}${quoteMeta( - a.slice(-1) - )}`; - } + [Symbol.iterator]() { + this._deopt = true; + if (this._needMerge) this._merge(); + return this._set[Symbol.iterator](); } - // find common prefix: (a1|a2|a3|a4|b5) => (a(1|2|3|4)|b5) - const prefixed = popCommonItems( - items, - item => (item.length >= 1 ? item[0] : false), - list => { - if (list.length >= 3) return true; - if (list.length <= 1) return false; - return list[0][1] === list[1][1]; - } - ); - for (const prefixedItems of prefixed) { - const prefix = getCommonPrefix(prefixedItems); - finishedItems.push( - `${quoteMeta(prefix)}${itemsToRegexp( - prefixedItems.map(i => i.slice(prefix.length)) - )}` - ); + /* istanbul ignore next */ + get [Symbol.toStringTag]() { + return "LazySet"; } - // find common suffix: (a1|b1|c1|d1|e2) => ((a|b|c|d)1|e2) - const suffixed = popCommonItems( - items, - item => (item.length >= 1 ? item.slice(-1) : false), - list => { - if (list.length >= 3) return true; - if (list.length <= 1) return false; - return list[0].slice(-2) === list[1].slice(-2); + serialize({ write }) { + if (this._needMerge) this._merge(); + write(this._set.size); + for (const item of this._set) write(item); + } + + static deserialize({ read }) { + const count = read(); + const items = []; + for (let i = 0; i < count; i++) { + items.push(read()); } - ); - for (const suffixedItems of suffixed) { - const suffix = getCommonSuffix(suffixedItems); - finishedItems.push( - `${itemsToRegexp( - suffixedItems.map(i => i.slice(0, -suffix.length)) - )}${quoteMeta(suffix)}` - ); + return new LazySet(items); } +} - // TODO further optimize regexp, i. e. - // use ranges: (1|2|3|4|a) => [1-4a] - const conditional = finishedItems.concat(Array.from(items, quoteMeta)); - if (conditional.length === 1) return conditional[0]; - return `(${conditional.join("|")})`; -}; +makeSerializable(LazySet, "webpack/lib/util/LazySet"); -compileBooleanMatcher.fromLists = compileBooleanMatcherFromLists; -compileBooleanMatcher.itemsToRegexp = itemsToRegexp; -module.exports = compileBooleanMatcher; +module.exports = LazySet; /***/ }), -/***/ 77695: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { +/***/ 30498: +/***/ (function(__unused_webpack_module, exports) { "use strict"; /* @@ -126053,32 +125268,26 @@ module.exports = compileBooleanMatcher; -const memoize = __webpack_require__(84297); - -const getValidate = memoize(() => __webpack_require__(79286).validate); - -const createSchemaValidation = (check, getSchema, options) => { - getSchema = memoize(getSchema); - return value => { - if (check && !check(value)) { - getValidate()(getSchema(), value, options); - if (check) { - __webpack_require__(31669).deprecate( - () => {}, - "webpack bug: Pre-compiled schema reports error while real schema is happy. This has performance drawbacks.", - "DEP_WEBPACK_PRE_COMPILED_SCHEMA_INVALID" - )(); - } - } - }; +/** + * @template K + * @template V + * @param {Map} map a map + * @param {K} key the key + * @param {function(): V} computer compute value + * @returns {V} value + */ +exports.provide = (map, key, computer) => { + const value = map.get(key); + if (value !== undefined) return value; + const newValue = computer(); + map.set(key, newValue); + return newValue; }; -module.exports = createSchemaValidation; - /***/ }), -/***/ 24123: +/***/ 67491: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; @@ -126089,176 +125298,64 @@ module.exports = createSchemaValidation; -const Hash = __webpack_require__(21301); - -const BULK_SIZE = 2000; - -// We are using an object instead of a Map as this will stay static during the runtime -// so access to it can be optimized by v8 -const digestCaches = {}; - -class BulkUpdateDecorator extends Hash { - /** - * @param {Hash | function(): Hash} hashOrFactory function to create a hash - * @param {string=} hashKey key for caching - */ - constructor(hashOrFactory, hashKey) { - super(); - this.hashKey = hashKey; - if (typeof hashOrFactory === "function") { - this.hashFactory = hashOrFactory; - this.hash = undefined; - } else { - this.hashFactory = undefined; - this.hash = hashOrFactory; - } - this.buffer = ""; - } - - /** - * Update hash {@link https://nodejs.org/api/crypto.html#crypto_hash_update_data_inputencoding} - * @param {string|Buffer} data data - * @param {string=} inputEncoding data encoding - * @returns {this} updated hash - */ - update(data, inputEncoding) { - if ( - inputEncoding !== undefined || - typeof data !== "string" || - data.length > BULK_SIZE - ) { - if (this.hash === undefined) this.hash = this.hashFactory(); - if (this.buffer.length > 0) { - this.hash.update(this.buffer); - this.buffer = ""; - } - this.hash.update(data, inputEncoding); - } else { - this.buffer += data; - if (this.buffer.length > BULK_SIZE) { - if (this.hash === undefined) this.hash = this.hashFactory(); - this.hash.update(this.buffer); - this.buffer = ""; - } - } - return this; - } - - /** - * Calculates the digest {@link https://nodejs.org/api/crypto.html#crypto_hash_digest_encoding} - * @param {string=} encoding encoding of the return value - * @returns {string|Buffer} digest - */ - digest(encoding) { - let digestCache; - const buffer = this.buffer; - if (this.hash === undefined) { - // short data for hash, we can use caching - const cacheKey = `${this.hashKey}-${encoding}`; - digestCache = digestCaches[cacheKey]; - if (digestCache === undefined) { - digestCache = digestCaches[cacheKey] = new Map(); - } - const cacheEntry = digestCache.get(buffer); - if (cacheEntry !== undefined) return cacheEntry; - this.hash = this.hashFactory(); - } - if (buffer.length > 0) { - this.hash.update(buffer); - } - const digestResult = this.hash.digest(encoding); - const result = - typeof digestResult === "string" ? digestResult : digestResult.toString(); - if (digestCache !== undefined) { - digestCache.set(buffer, result); - } - return result; - } -} +const binarySearchBounds = __webpack_require__(44795); -/* istanbul ignore next */ -class DebugHash extends Hash { +class ParallelismFactorCalculator { constructor() { - super(); - this.string = ""; - } - - /** - * Update hash {@link https://nodejs.org/api/crypto.html#crypto_hash_update_data_inputencoding} - * @param {string|Buffer} data data - * @param {string=} inputEncoding data encoding - * @returns {this} updated hash - */ - update(data, inputEncoding) { - if (typeof data !== "string") data = data.toString("utf-8"); - if (data.startsWith("debug-digest-")) { - data = Buffer.from(data.slice("debug-digest-".length), "hex").toString(); - } - this.string += `[${data}](${new Error().stack.split("\n", 3)[2]})\n`; - return this; + this._rangePoints = []; + this._rangeCallbacks = []; } - /** - * Calculates the digest {@link https://nodejs.org/api/crypto.html#crypto_hash_digest_encoding} - * @param {string=} encoding encoding of the return value - * @returns {string|Buffer} digest - */ - digest(encoding) { - return "debug-digest-" + Buffer.from(this.string).toString("hex"); + range(start, end, callback) { + if (start === end) return callback(1); + this._rangePoints.push(start); + this._rangePoints.push(end); + this._rangeCallbacks.push(callback); } -} - -let crypto = undefined; -let createXXHash64 = undefined; -let createMd4 = undefined; -let BatchedHash = undefined; -/** - * Creates a hash by name or function - * @param {string | typeof Hash} algorithm the algorithm name or a constructor creating a hash - * @returns {Hash} the hash - */ -module.exports = algorithm => { - if (typeof algorithm === "function") { - return new BulkUpdateDecorator(() => new algorithm()); - } - switch (algorithm) { - // TODO add non-cryptographic algorithm here - case "debug": - return new DebugHash(); - case "xxhash64": - if (createXXHash64 === undefined) { - createXXHash64 = __webpack_require__(37364); - if (BatchedHash === undefined) { - BatchedHash = __webpack_require__(32928); - } - } - return new BatchedHash(createXXHash64()); - case "md4": - if (createMd4 === undefined) { - createMd4 = __webpack_require__(20487); - if (BatchedHash === undefined) { - BatchedHash = __webpack_require__(32928); - } - } - return new BatchedHash(createMd4()); - case "native-md4": - if (crypto === undefined) crypto = __webpack_require__(76417); - return new BulkUpdateDecorator(() => crypto.createHash("md4"), "md4"); - default: - if (crypto === undefined) crypto = __webpack_require__(76417); - return new BulkUpdateDecorator( - () => crypto.createHash(algorithm), - algorithm - ); + calculate() { + const segments = Array.from(new Set(this._rangePoints)).sort((a, b) => + a < b ? -1 : 1 + ); + const parallelism = segments.map(() => 0); + const rangeStartIndices = []; + for (let i = 0; i < this._rangePoints.length; i += 2) { + const start = this._rangePoints[i]; + const end = this._rangePoints[i + 1]; + let idx = binarySearchBounds.eq(segments, start); + rangeStartIndices.push(idx); + do { + parallelism[idx]++; + idx++; + } while (segments[idx] < end); + } + for (let i = 0; i < this._rangeCallbacks.length; i++) { + const start = this._rangePoints[i * 2]; + const end = this._rangePoints[i * 2 + 1]; + let idx = rangeStartIndices[i]; + let sum = 0; + let totalDuration = 0; + let current = start; + do { + const p = parallelism[idx]; + idx++; + const duration = segments[idx] - current; + totalDuration += duration; + current = segments[idx]; + sum += p * duration; + } while (current < end); + this._rangeCallbacks[i](sum / totalDuration); + } } -}; +} + +module.exports = ParallelismFactorCalculator; /***/ }), -/***/ 2594: -/***/ (function(__unused_webpack_module, exports, __webpack_require__) { +/***/ 65753: +/***/ (function(module) { "use strict"; /* @@ -126268,268 +125365,157 @@ module.exports = algorithm => { -const util = __webpack_require__(31669); - -/** @type {Map} */ -const deprecationCache = new Map(); - /** - * @typedef {Object} FakeHookMarker - * @property {true} _fakeHook it's a fake hook + * @template T */ +class Queue { + /** + * @param {Iterable=} items The initial elements. + */ + constructor(items) { + /** @private @type {Set} */ + this._set = new Set(items); + /** @private @type {Iterator} */ + this._iterator = this._set[Symbol.iterator](); + } -/** @template T @typedef {T & FakeHookMarker} FakeHook */ + /** + * Returns the number of elements in this queue. + * @returns {number} The number of elements in this queue. + */ + get length() { + return this._set.size; + } -/** - * @param {string} message deprecation message - * @param {string} code deprecation code - * @returns {Function} function to trigger deprecation - */ -const createDeprecation = (message, code) => { - const cached = deprecationCache.get(message); - if (cached !== undefined) return cached; - const fn = util.deprecate( - () => {}, - message, - "DEP_WEBPACK_DEPRECATION_" + code - ); - deprecationCache.set(message, fn); - return fn; -}; + /** + * Appends the specified element to this queue. + * @param {T} item The element to add. + * @returns {void} + */ + enqueue(item) { + this._set.add(item); + } + + /** + * Retrieves and removes the head of this queue. + * @returns {T | undefined} The head of the queue of `undefined` if this queue is empty. + */ + dequeue() { + const result = this._iterator.next(); + if (result.done) return undefined; + this._set.delete(result.value); + return result.value; + } +} + +module.exports = Queue; + + +/***/ }), + +/***/ 34715: +/***/ (function(__unused_webpack_module, exports) { + +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ -const COPY_METHODS = [ - "concat", - "entry", - "filter", - "find", - "findIndex", - "includes", - "indexOf", - "join", - "lastIndexOf", - "map", - "reduce", - "reduceRight", - "slice", - "some" -]; -const DISABLED_METHODS = [ - "copyWithin", - "entries", - "fill", - "keys", - "pop", - "reverse", - "shift", - "splice", - "sort", - "unshift" -]; /** - * @param {any} set new set - * @param {string} name property name - * @returns {void} + * intersect creates Set containing the intersection of elements between all sets + * @template T + * @param {Set[]} sets an array of sets being checked for shared elements + * @returns {Set} returns a new Set containing the intersecting items */ -exports.arrayToSetDeprecation = (set, name) => { - for (const method of COPY_METHODS) { - if (set[method]) continue; - const d = createDeprecation( - `${name} was changed from Array to Set (using Array method '${method}' is deprecated)`, - "ARRAY_TO_SET" - ); - /** - * @deprecated - * @this {Set} - * @returns {number} count - */ - set[method] = function () { - d(); - const array = Array.from(this); - return Array.prototype[method].apply(array, arguments); - }; - } - const dPush = createDeprecation( - `${name} was changed from Array to Set (using Array method 'push' is deprecated)`, - "ARRAY_TO_SET_PUSH" - ); - const dLength = createDeprecation( - `${name} was changed from Array to Set (using Array property 'length' is deprecated)`, - "ARRAY_TO_SET_LENGTH" - ); - const dIndexer = createDeprecation( - `${name} was changed from Array to Set (indexing Array is deprecated)`, - "ARRAY_TO_SET_INDEXER" - ); - /** - * @deprecated - * @this {Set} - * @returns {number} count - */ - set.push = function () { - dPush(); - for (const item of Array.from(arguments)) { - this.add(item); +const intersect = sets => { + if (sets.length === 0) return new Set(); + if (sets.length === 1) return new Set(sets[0]); + let minSize = Infinity; + let minIndex = -1; + for (let i = 0; i < sets.length; i++) { + const size = sets[i].size; + if (size < minSize) { + minIndex = i; + minSize = size; } - return this.size; - }; - for (const method of DISABLED_METHODS) { - if (set[method]) continue; - set[method] = () => { - throw new Error( - `${name} was changed from Array to Set (using Array method '${method}' is not possible)` - ); - }; } - const createIndexGetter = index => { - /** - * @this {Set} a Set - * @returns {any} the value at this location - */ - const fn = function () { - dIndexer(); - let i = 0; - for (const item of this) { - if (i++ === index) return item; - } - return undefined; - }; - return fn; - }; - const defineIndexGetter = index => { - Object.defineProperty(set, index, { - get: createIndexGetter(index), - set(value) { - throw new Error( - `${name} was changed from Array to Set (indexing Array with write is not possible)` - ); - } - }); - }; - defineIndexGetter(0); - let indexerDefined = 1; - Object.defineProperty(set, "length", { - get() { - dLength(); - const length = this.size; - for (indexerDefined; indexerDefined < length + 1; indexerDefined++) { - defineIndexGetter(indexerDefined); + const current = new Set(sets[minIndex]); + for (let i = 0; i < sets.length; i++) { + if (i === minIndex) continue; + const set = sets[i]; + for (const item of current) { + if (!set.has(item)) { + current.delete(item); } - return length; - }, - set(value) { - throw new Error( - `${name} was changed from Array to Set (writing to Array property 'length' is not possible)` - ); } - }); - set[Symbol.isConcatSpreadable] = true; + } + return current; }; -exports.createArrayToSetDeprecationSet = name => { - let initialized = false; - class SetDeprecatedArray extends Set { - constructor(items) { - super(items); - if (!initialized) { - initialized = true; - exports.arrayToSetDeprecation(SetDeprecatedArray.prototype, name); - } - } +/** + * Checks if a set is the subset of another set + * @template T + * @param {Set} bigSet a Set which contains the original elements to compare against + * @param {Set} smallSet the set whose elements might be contained inside of bigSet + * @returns {boolean} returns true if smallSet contains all elements inside of the bigSet + */ +const isSubset = (bigSet, smallSet) => { + if (bigSet.size < smallSet.size) return false; + for (const item of smallSet) { + if (!bigSet.has(item)) return false; } - return SetDeprecatedArray; + return true; }; -exports.soonFrozenObjectDeprecation = (obj, name, code, note = "") => { - const message = `${name} will be frozen in future, all modifications are deprecated.${ - note && `\n${note}` - }`; - return new Proxy(obj, { - set: util.deprecate( - (target, property, value, receiver) => - Reflect.set(target, property, value, receiver), - message, - code - ), - defineProperty: util.deprecate( - (target, property, descriptor) => - Reflect.defineProperty(target, property, descriptor), - message, - code - ), - deleteProperty: util.deprecate( - (target, property) => Reflect.deleteProperty(target, property), - message, - code - ), - setPrototypeOf: util.deprecate( - (target, proto) => Reflect.setPrototypeOf(target, proto), - message, - code - ) - }); +/** + * @template T + * @param {Set} set a set + * @param {function(T): boolean} fn selector function + * @returns {T | undefined} found item + */ +const find = (set, fn) => { + for (const item of set) { + if (fn(item)) return item; + } }; /** * @template T - * @param {T} obj object - * @param {string} message deprecation message - * @param {string} code deprecation code - * @returns {T} object with property access deprecated + * @param {Set} set a set + * @returns {T | undefined} first item */ -const deprecateAllProperties = (obj, message, code) => { - const newObj = {}; - const descriptors = Object.getOwnPropertyDescriptors(obj); - for (const name of Object.keys(descriptors)) { - const descriptor = descriptors[name]; - if (typeof descriptor.value === "function") { - Object.defineProperty(newObj, name, { - ...descriptor, - value: util.deprecate(descriptor.value, message, code) - }); - } else if (descriptor.get || descriptor.set) { - Object.defineProperty(newObj, name, { - ...descriptor, - get: descriptor.get && util.deprecate(descriptor.get, message, code), - set: descriptor.set && util.deprecate(descriptor.set, message, code) - }); - } else { - let value = descriptor.value; - Object.defineProperty(newObj, name, { - configurable: descriptor.configurable, - enumerable: descriptor.enumerable, - get: util.deprecate(() => value, message, code), - set: descriptor.writable - ? util.deprecate(v => (value = v), message, code) - : undefined - }); - } - } - return /** @type {T} */ (newObj); +const first = set => { + const entry = set.values().next(); + return entry.done ? undefined : entry.value; }; -exports.deprecateAllProperties = deprecateAllProperties; /** * @template T - * @param {T} fakeHook fake hook implementation - * @param {string=} message deprecation message (not deprecated when unset) - * @param {string=} code deprecation code (not deprecated when unset) - * @returns {FakeHook} fake hook which redirects + * @param {Set} a first + * @param {Set} b second + * @returns {Set} combined set, may be identical to a or b */ -exports.createFakeHook = (fakeHook, message, code) => { - if (message && code) { - fakeHook = deprecateAllProperties(fakeHook, message, code); - } - return Object.freeze( - Object.assign(fakeHook, { _fakeHook: /** @type {true} */ (true) }) - ); +const combine = (a, b) => { + if (b.size === 0) return a; + if (a.size === 0) return b; + const set = new Set(a); + for (const item of b) set.add(item); + return set; }; +exports.intersect = intersect; +exports.isSubset = isSubset; +exports.find = find; +exports.first = first; +exports.combine = combine; + /***/ }), -/***/ 37906: +/***/ 67563: /***/ (function(module) { "use strict"; @@ -126540,536 +125526,520 @@ exports.createFakeHook = (fakeHook, message, code) => { -// Simulations show these probabilities for a single change -// 93.1% that one group is invalidated -// 4.8% that two groups are invalidated -// 1.1% that 3 groups are invalidated -// 0.1% that 4 or more groups are invalidated -// -// And these for removing/adding 10 lexically adjacent files -// 64.5% that one group is invalidated -// 24.8% that two groups are invalidated -// 7.8% that 3 groups are invalidated -// 2.7% that 4 or more groups are invalidated -// -// And these for removing/adding 3 random files -// 0% that one group is invalidated -// 3.7% that two groups are invalidated -// 80.8% that 3 groups are invalidated -// 12.3% that 4 groups are invalidated -// 3.2% that 5 or more groups are invalidated +const NONE = Symbol("not sorted"); /** - * - * @param {string} a key - * @param {string} b key - * @returns {number} the similarity as number + * A subset of Set that offers sorting functionality + * @template T item type in set + * @extends {Set} */ -const similarity = (a, b) => { - const l = Math.min(a.length, b.length); - let dist = 0; - for (let i = 0; i < l; i++) { - const ca = a.charCodeAt(i); - const cb = b.charCodeAt(i); - dist += Math.max(0, 10 - Math.abs(ca - cb)); +class SortableSet extends Set { + /** + * Create a new sortable set + * @param {Iterable=} initialIterable The initial iterable value + * @typedef {function(T, T): number} SortFunction + * @param {SortFunction=} defaultSort Default sorting function + */ + constructor(initialIterable, defaultSort) { + super(initialIterable); + /** @private @type {undefined | function(T, T): number}} */ + this._sortFn = defaultSort; + /** @private @type {typeof NONE | undefined | function(T, T): number}} */ + this._lastActiveSortFn = NONE; + /** @private @type {Map | undefined} */ + this._cache = undefined; + /** @private @type {Map | undefined} */ + this._cacheOrderIndependent = undefined; } - return dist; -}; -/** - * @param {string} a key - * @param {string} b key - * @param {Set} usedNames set of already used names - * @returns {string} the common part and a single char for the difference - */ -const getName = (a, b, usedNames) => { - const l = Math.min(a.length, b.length); - let i = 0; - while (i < l) { - if (a.charCodeAt(i) !== b.charCodeAt(i)) { - i++; - break; - } - i++; - } - while (i < l) { - const name = a.slice(0, i); - const lowerName = name.toLowerCase(); - if (!usedNames.has(lowerName)) { - usedNames.add(lowerName); - return name; - } - i++; + /** + * @param {T} value value to add to set + * @returns {this} returns itself + */ + add(value) { + this._lastActiveSortFn = NONE; + this._invalidateCache(); + this._invalidateOrderedCache(); + super.add(value); + return this; } - // names always contain a hash, so this is always unique - // we don't need to check usedNames nor add it - return a; -}; -/** - * @param {Record} total total size - * @param {Record} size single size - * @returns {void} - */ -const addSizeTo = (total, size) => { - for (const key of Object.keys(size)) { - total[key] = (total[key] || 0) + size[key]; + /** + * @param {T} value value to delete + * @returns {boolean} true if value existed in set, false otherwise + */ + delete(value) { + this._invalidateCache(); + this._invalidateOrderedCache(); + return super.delete(value); } -}; -/** - * @param {Record} total total size - * @param {Record} size single size - * @returns {void} - */ -const subtractSizeFrom = (total, size) => { - for (const key of Object.keys(size)) { - total[key] -= size[key]; + /** + * @returns {void} + */ + clear() { + this._invalidateCache(); + this._invalidateOrderedCache(); + return super.clear(); } -}; -/** - * @param {Iterable} nodes some nodes - * @returns {Record} total size - */ -const sumSize = nodes => { - const sum = Object.create(null); - for (const node of nodes) { - addSizeTo(sum, node.size); + /** + * Sort with a comparer function + * @param {SortFunction} sortFn Sorting comparer function + * @returns {void} + */ + sortWith(sortFn) { + if (this.size <= 1 || sortFn === this._lastActiveSortFn) { + // already sorted - nothing to do + return; + } + + const sortedArray = Array.from(this).sort(sortFn); + super.clear(); + for (let i = 0; i < sortedArray.length; i += 1) { + super.add(sortedArray[i]); + } + this._lastActiveSortFn = sortFn; + this._invalidateCache(); } - return sum; -}; -const isTooBig = (size, maxSize) => { - for (const key of Object.keys(size)) { - const s = size[key]; - if (s === 0) continue; - const maxSizeValue = maxSize[key]; - if (typeof maxSizeValue === "number") { - if (s > maxSizeValue) return true; - } + sort() { + this.sortWith(this._sortFn); + return this; } - return false; -}; -const isTooSmall = (size, minSize) => { - for (const key of Object.keys(size)) { - const s = size[key]; - if (s === 0) continue; - const minSizeValue = minSize[key]; - if (typeof minSizeValue === "number") { - if (s < minSizeValue) return true; + /** + * Get data from cache + * @template R + * @param {function(SortableSet): R} fn function to calculate value + * @returns {R} returns result of fn(this), cached until set changes + */ + getFromCache(fn) { + if (this._cache === undefined) { + this._cache = new Map(); + } else { + const result = this._cache.get(fn); + const data = /** @type {R} */ (result); + if (data !== undefined) { + return data; + } } + const newData = fn(this); + this._cache.set(fn, newData); + return newData; } - return false; -}; -const getTooSmallTypes = (size, minSize) => { - const types = new Set(); - for (const key of Object.keys(size)) { - const s = size[key]; - if (s === 0) continue; - const minSizeValue = minSize[key]; - if (typeof minSizeValue === "number") { - if (s < minSizeValue) types.add(key); + /** + * Get data from cache (ignoring sorting) + * @template R + * @param {function(SortableSet): R} fn function to calculate value + * @returns {R} returns result of fn(this), cached until set changes + */ + getFromUnorderedCache(fn) { + if (this._cacheOrderIndependent === undefined) { + this._cacheOrderIndependent = new Map(); + } else { + const result = this._cacheOrderIndependent.get(fn); + const data = /** @type {R} */ (result); + if (data !== undefined) { + return data; + } } + const newData = fn(this); + this._cacheOrderIndependent.set(fn, newData); + return newData; } - return types; -}; -const getNumberOfMatchingSizeTypes = (size, types) => { - let i = 0; - for (const key of Object.keys(size)) { - if (size[key] !== 0 && types.has(key)) i++; + /** + * @private + * @returns {void} + */ + _invalidateCache() { + if (this._cache !== undefined) { + this._cache.clear(); + } } - return i; -}; -const selectiveSizeSum = (size, types) => { - let sum = 0; - for (const key of Object.keys(size)) { - if (size[key] !== 0 && types.has(key)) sum += size[key]; + /** + * @private + * @returns {void} + */ + _invalidateOrderedCache() { + if (this._cacheOrderIndependent !== undefined) { + this._cacheOrderIndependent.clear(); + } } - return sum; -}; -/** - * @template T - */ -class Node { /** - * @param {T} item item - * @param {string} key key - * @param {Record} size size + * @returns {T[]} the raw array */ - constructor(item, key, size) { - this.item = item; - this.key = key; - this.size = size; + toJSON() { + return Array.from(this); } } +module.exports = SortableSet; + + +/***/ }), + +/***/ 26009: +/***/ (function(module) { + +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ + + + /** - * @template T + * @template K + * @template V */ -class Group { - /** - * @param {Node[]} nodes nodes - * @param {number[]} similarities similarities between the nodes (length = nodes.length - 1) - * @param {Record=} size size of the group - */ - constructor(nodes, similarities, size) { - this.nodes = nodes; - this.similarities = similarities; - this.size = size || sumSize(nodes); - /** @type {string} */ - this.key = undefined; +class StackedCacheMap { + constructor() { + /** @type {Map} */ + this.map = new Map(); + /** @type {ReadonlyMap[]} */ + this.stack = []; } /** - * @param {function(Node): boolean} filter filter function - * @returns {Node[]} removed nodes + * @param {ReadonlyMap} map map to add + * @param {boolean} immutable if 'map' is immutable and StackedCacheMap can keep referencing it */ - popNodes(filter) { - const newNodes = []; - const newSimilarities = []; - const resultNodes = []; - let lastNode; - for (let i = 0; i < this.nodes.length; i++) { - const node = this.nodes[i]; - if (filter(node)) { - resultNodes.push(node); - } else { - if (newNodes.length > 0) { - newSimilarities.push( - lastNode === this.nodes[i - 1] - ? this.similarities[i - 1] - : similarity(lastNode.key, node.key) - ); - } - newNodes.push(node); - lastNode = node; + addAll(map, immutable) { + if (immutable) { + this.stack.push(map); + + // largest map should go first + for (let i = this.stack.length - 1; i > 0; i--) { + const beforeLast = this.stack[i - 1]; + if (beforeLast.size >= map.size) break; + this.stack[i] = beforeLast; + this.stack[i - 1] = map; + } + } else { + for (const [key, value] of map) { + this.map.set(key, value); } } - if (resultNodes.length === this.nodes.length) return undefined; - this.nodes = newNodes; - this.similarities = newSimilarities; - this.size = sumSize(newNodes); - return resultNodes; } -} -/** - * @param {Iterable} nodes nodes - * @returns {number[]} similarities - */ -const getSimilarities = nodes => { - // calculate similarities between lexically adjacent nodes - /** @type {number[]} */ - const similarities = []; - let last = undefined; - for (const node of nodes) { - if (last !== undefined) { - similarities.push(similarity(last.key, node.key)); - } - last = node; + /** + * @param {K} item the key of the element to add + * @param {V} value the value of the element to add + * @returns {void} + */ + set(item, value) { + this.map.set(item, value); } - return similarities; -}; - -/** - * @template T - * @typedef {Object} GroupedItems - * @property {string} key - * @property {T[]} items - * @property {Record} size - */ -/** - * @template T - * @typedef {Object} Options - * @property {Record} maxSize maximum size of a group - * @property {Record} minSize minimum size of a group (preferred over maximum size) - * @property {Iterable} items a list of items - * @property {function(T): Record} getSize function to get size of an item - * @property {function(T): string} getKey function to get the key of an item - */ - -/** - * @template T - * @param {Options} options options object - * @returns {GroupedItems[]} grouped items - */ -module.exports = ({ maxSize, minSize, items, getSize, getKey }) => { - /** @type {Group[]} */ - const result = []; + /** + * @param {K} item the item to delete + * @returns {void} + */ + delete(item) { + throw new Error("Items can't be deleted from a StackedCacheMap"); + } - const nodes = Array.from( - items, - item => new Node(item, getKey(item), getSize(item)) - ); + /** + * @param {K} item the item to test + * @returns {boolean} true if the item exists in this set + */ + has(item) { + throw new Error( + "Checking StackedCacheMap.has before reading is inefficient, use StackedCacheMap.get and check for undefined" + ); + } - /** @type {Node[]} */ - const initialNodes = []; + /** + * @param {K} item the key of the element to return + * @returns {V} the value of the element + */ + get(item) { + for (const map of this.stack) { + const value = map.get(item); + if (value !== undefined) return value; + } + return this.map.get(item); + } - // lexically ordering of keys - nodes.sort((a, b) => { - if (a.key < b.key) return -1; - if (a.key > b.key) return 1; - return 0; - }); + clear() { + this.stack.length = 0; + this.map.clear(); + } - // return nodes bigger than maxSize directly as group - // But make sure that minSize is not violated - for (const node of nodes) { - if (isTooBig(node.size, maxSize) && !isTooSmall(node.size, minSize)) { - result.push(new Group([node], [])); - } else { - initialNodes.push(node); + get size() { + let size = this.map.size; + for (const map of this.stack) { + size += map.size; } + return size; } - if (initialNodes.length > 0) { - const initialGroup = new Group(initialNodes, getSimilarities(initialNodes)); - - const removeProblematicNodes = (group, consideredSize = group.size) => { - const problemTypes = getTooSmallTypes(consideredSize, minSize); - if (problemTypes.size > 0) { - // We hit an edge case where the working set is already smaller than minSize - // We merge problematic nodes with the smallest result node to keep minSize intact - const problemNodes = group.popNodes( - n => getNumberOfMatchingSizeTypes(n.size, problemTypes) > 0 - ); - if (problemNodes === undefined) return false; - // Only merge it with result nodes that have the problematic size type - const possibleResultGroups = result.filter( - n => getNumberOfMatchingSizeTypes(n.size, problemTypes) > 0 - ); - if (possibleResultGroups.length > 0) { - const bestGroup = possibleResultGroups.reduce((min, group) => { - const minMatches = getNumberOfMatchingSizeTypes(min, problemTypes); - const groupMatches = getNumberOfMatchingSizeTypes( - group, - problemTypes - ); - if (minMatches !== groupMatches) - return minMatches < groupMatches ? group : min; - if ( - selectiveSizeSum(min.size, problemTypes) > - selectiveSizeSum(group.size, problemTypes) - ) - return group; - return min; - }); - for (const node of problemNodes) bestGroup.nodes.push(node); - bestGroup.nodes.sort((a, b) => { - if (a.key < b.key) return -1; - if (a.key > b.key) return 1; - return 0; - }); - } else { - // There are no other nodes with the same size types - // We create a new group and have to accept that it's smaller than minSize - result.push(new Group(problemNodes, null)); + [Symbol.iterator]() { + const iterators = this.stack.map(map => map[Symbol.iterator]()); + let current = this.map[Symbol.iterator](); + return { + next() { + let result = current.next(); + while (result.done && iterators.length > 0) { + current = iterators.pop(); + result = current.next(); } - return true; - } else { - return false; + return result; } }; + } +} - if (initialGroup.nodes.length > 0) { - const queue = [initialGroup]; +module.exports = StackedCacheMap; - while (queue.length) { - const group = queue.pop(); - // only groups bigger than maxSize need to be splitted - if (!isTooBig(group.size, maxSize)) { - result.push(group); - continue; - } - // If the group is already too small - // we try to work only with the unproblematic nodes - if (removeProblematicNodes(group)) { - // This changed something, so we try this group again - queue.push(group); - continue; - } - // find unsplittable area from left and right - // going minSize from left and right - // at least one node need to be included otherwise we get stuck - let left = 1; - let leftSize = Object.create(null); - addSizeTo(leftSize, group.nodes[0].size); - while (left < group.nodes.length && isTooSmall(leftSize, minSize)) { - addSizeTo(leftSize, group.nodes[left].size); - left++; - } - let right = group.nodes.length - 2; - let rightSize = Object.create(null); - addSizeTo(rightSize, group.nodes[group.nodes.length - 1].size); - while (right >= 0 && isTooSmall(rightSize, minSize)) { - addSizeTo(rightSize, group.nodes[right].size); - right--; - } +/***/ }), - // left v v right - // [ O O O ] O O O [ O O O ] - // ^^^^^^^^^ leftSize - // rightSize ^^^^^^^^^ - // leftSize > minSize - // rightSize > minSize +/***/ 60798: +/***/ (function(module) { - // Perfect split: [ O O O ] [ O O O ] - // right === left - 1 +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ - if (left - 1 > right) { - // We try to remove some problematic nodes to "fix" that - let prevSize; - if (right < group.nodes.length - left) { - subtractSizeFrom(rightSize, group.nodes[right + 1].size); - prevSize = rightSize; - } else { - subtractSizeFrom(leftSize, group.nodes[left - 1].size); - prevSize = leftSize; - } - if (removeProblematicNodes(group, prevSize)) { - // This changed something, so we try this group again - queue.push(group); - continue; - } - // can't split group while holding minSize - // because minSize is preferred of maxSize we return - // the problematic nodes as result here even while it's too big - // To avoid this make sure maxSize > minSize * 3 - result.push(group); - continue; - } - if (left <= right) { - // when there is a area between left and right - // we look for best split point - // we split at the minimum similarity - // here key space is separated the most - // But we also need to make sure to not create too small groups - let best = -1; - let bestSimilarity = Infinity; - let pos = left; - let rightSize = sumSize(group.nodes.slice(pos)); - // pos v v right - // [ O O O ] O O O [ O O O ] - // ^^^^^^^^^ leftSize - // rightSize ^^^^^^^^^^^^^^^ - while (pos <= right + 1) { - const similarity = group.similarities[pos - 1]; - if ( - similarity < bestSimilarity && - !isTooSmall(leftSize, minSize) && - !isTooSmall(rightSize, minSize) - ) { - best = pos; - bestSimilarity = similarity; - } - addSizeTo(leftSize, group.nodes[pos].size); - subtractSizeFrom(rightSize, group.nodes[pos].size); - pos++; - } - if (best < 0) { - // This can't happen - // but if that assumption is wrong - // fallback to a big group - result.push(group); - continue; - } - left = best; - right = best - 1; +const TOMBSTONE = Symbol("tombstone"); +const UNDEFINED_MARKER = Symbol("undefined"); + +/** + * @template T + * @typedef {T | undefined} Cell + */ + +/** + * @template T + * @typedef {T | typeof TOMBSTONE | typeof UNDEFINED_MARKER} InternalCell + */ + +/** + * @template K + * @template V + * @param {[K, InternalCell]} pair the internal cell + * @returns {[K, Cell]} its “safe” representation + */ +const extractPair = pair => { + const key = pair[0]; + const val = pair[1]; + if (val === UNDEFINED_MARKER || val === TOMBSTONE) { + return [key, undefined]; + } else { + return /** @type {[K, Cell]} */ (pair); + } +}; + +/** + * @template K + * @template V + */ +class StackedMap { + /** + * @param {Map>[]=} parentStack an optional parent + */ + constructor(parentStack) { + /** @type {Map>} */ + this.map = new Map(); + /** @type {Map>[]} */ + this.stack = parentStack === undefined ? [] : parentStack.slice(); + this.stack.push(this.map); + } + + /** + * @param {K} item the key of the element to add + * @param {V} value the value of the element to add + * @returns {void} + */ + set(item, value) { + this.map.set(item, value === undefined ? UNDEFINED_MARKER : value); + } + + /** + * @param {K} item the item to delete + * @returns {void} + */ + delete(item) { + if (this.stack.length > 1) { + this.map.set(item, TOMBSTONE); + } else { + this.map.delete(item); + } + } + + /** + * @param {K} item the item to test + * @returns {boolean} true if the item exists in this set + */ + has(item) { + const topValue = this.map.get(item); + if (topValue !== undefined) { + return topValue !== TOMBSTONE; + } + if (this.stack.length > 1) { + for (let i = this.stack.length - 2; i >= 0; i--) { + const value = this.stack[i].get(item); + if (value !== undefined) { + this.map.set(item, value); + return value !== TOMBSTONE; } + } + this.map.set(item, TOMBSTONE); + } + return false; + } - // create two new groups for left and right area - // and queue them up - const rightNodes = [group.nodes[right + 1]]; - /** @type {number[]} */ - const rightSimilarities = []; - for (let i = right + 2; i < group.nodes.length; i++) { - rightSimilarities.push(group.similarities[i - 1]); - rightNodes.push(group.nodes[i]); + /** + * @param {K} item the key of the element to return + * @returns {Cell} the value of the element + */ + get(item) { + const topValue = this.map.get(item); + if (topValue !== undefined) { + return topValue === TOMBSTONE || topValue === UNDEFINED_MARKER + ? undefined + : topValue; + } + if (this.stack.length > 1) { + for (let i = this.stack.length - 2; i >= 0; i--) { + const value = this.stack[i].get(item); + if (value !== undefined) { + this.map.set(item, value); + return value === TOMBSTONE || value === UNDEFINED_MARKER + ? undefined + : value; } - queue.push(new Group(rightNodes, rightSimilarities)); + } + this.map.set(item, TOMBSTONE); + } + return undefined; + } - const leftNodes = [group.nodes[0]]; - /** @type {number[]} */ - const leftSimilarities = []; - for (let i = 1; i < left; i++) { - leftSimilarities.push(group.similarities[i - 1]); - leftNodes.push(group.nodes[i]); + _compress() { + if (this.stack.length === 1) return; + this.map = new Map(); + for (const data of this.stack) { + for (const pair of data) { + if (pair[1] === TOMBSTONE) { + this.map.delete(pair[0]); + } else { + this.map.set(pair[0], pair[1]); } - queue.push(new Group(leftNodes, leftSimilarities)); } } + this.stack = [this.map]; } - // lexically ordering - result.sort((a, b) => { - if (a.nodes[0].key < b.nodes[0].key) return -1; - if (a.nodes[0].key > b.nodes[0].key) return 1; - return 0; - }); + asArray() { + this._compress(); + return Array.from(this.map.keys()); + } - // give every group a name - const usedNames = new Set(); - for (let i = 0; i < result.length; i++) { - const group = result[i]; - if (group.nodes.length === 1) { - group.key = group.nodes[0].key; - } else { - const first = group.nodes[0]; - const last = group.nodes[group.nodes.length - 1]; - const name = getName(first.key, last.key, usedNames); - group.key = name; - } + asSet() { + this._compress(); + return new Set(this.map.keys()); } - // return the results - return result.map(group => { - /** @type {GroupedItems} */ - return { - key: group.key, - items: group.nodes.map(node => node.item), - size: group.size - }; - }); -}; + asPairArray() { + this._compress(); + return Array.from(this.map.entries(), extractPair); + } + + asMap() { + return new Map(this.asPairArray()); + } + + get size() { + this._compress(); + return this.map.size; + } + + createChild() { + return new StackedMap(this.stack); + } +} + +module.exports = StackedMap; /***/ }), -/***/ 31670: +/***/ 23877: /***/ (function(module) { "use strict"; /* MIT License http://www.opensource.org/licenses/mit-license.php - Author Sam Chen @chenxsan + Author Tobias Koppers @sokra */ -/** - * @param {string} urlAndGlobal the script request - * @returns {string[]} script url and its global variable - */ -module.exports = function extractUrlAndGlobal(urlAndGlobal) { - const index = urlAndGlobal.indexOf("@"); - return [urlAndGlobal.substring(index + 1), urlAndGlobal.substring(0, index)]; -}; +class StringXor { + constructor() { + this._value = undefined; + } + + /** + * @param {string} str string + * @returns {void} + */ + add(str) { + const len = str.length; + const value = this._value; + if (value === undefined) { + const newValue = (this._value = Buffer.allocUnsafe(len)); + for (let i = 0; i < len; i++) { + newValue[i] = str.charCodeAt(i); + } + return; + } + const valueLen = value.length; + if (valueLen < len) { + const newValue = (this._value = Buffer.allocUnsafe(len)); + let i; + for (i = 0; i < valueLen; i++) { + newValue[i] = value[i] ^ str.charCodeAt(i); + } + for (; i < len; i++) { + newValue[i] = str.charCodeAt(i); + } + } else { + for (let i = 0; i < len; i++) { + value[i] = value[i] ^ str.charCodeAt(i); + } + } + } + + toString() { + const value = this._value; + return value === undefined ? "" : value.toString("latin1"); + } + + updateHash(hash) { + const value = this._value; + if (value !== undefined) hash.update(value); + } +} + +module.exports = StringXor; /***/ }), -/***/ 38670: -/***/ (function(module) { +/***/ 54345: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; /* @@ -127079,673 +126049,592 @@ module.exports = function extractUrlAndGlobal(urlAndGlobal) { -const NO_MARKER = 0; -const IN_PROGRESS_MARKER = 1; -const DONE_MARKER = 2; -const DONE_MAYBE_ROOT_CYCLE_MARKER = 3; -const DONE_AND_ROOT_MARKER = 4; +const TupleSet = __webpack_require__(39322); /** - * @template T + * @template {any[]} T */ -class Node { +class TupleQueue { /** - * @param {T} item the value of the node + * @param {Iterable=} items The initial elements. */ - constructor(item) { - this.item = item; - /** @type {Set>} */ - this.dependencies = new Set(); - this.marker = NO_MARKER; - /** @type {Cycle | undefined} */ - this.cycle = undefined; - this.incoming = 0; + constructor(items) { + /** @private @type {TupleSet} */ + this._set = new TupleSet(items); + /** @private @type {Iterator} */ + this._iterator = this._set[Symbol.iterator](); } -} -/** - * @template T - */ -class Cycle { - constructor() { - /** @type {Set>} */ - this.nodes = new Set(); + /** + * Returns the number of elements in this queue. + * @returns {number} The number of elements in this queue. + */ + get length() { + return this._set.size; + } + + /** + * Appends the specified element to this queue. + * @param {T} item The element to add. + * @returns {void} + */ + enqueue(...item) { + this._set.add(...item); + } + + /** + * Retrieves and removes the head of this queue. + * @returns {T | undefined} The head of the queue of `undefined` if this queue is empty. + */ + dequeue() { + const result = this._iterator.next(); + if (result.done) { + if (this._set.size > 0) { + this._iterator = this._set[Symbol.iterator](); + const value = this._iterator.next().value; + this._set.delete(...value); + return value; + } + return undefined; + } + this._set.delete(...result.value); + return result.value; } } -/** - * @template T - * @typedef {Object} StackEntry - * @property {Node} node - * @property {Node[]} openEdges - */ +module.exports = TupleQueue; + + +/***/ }), + +/***/ 39322: +/***/ (function(module) { + +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ + + /** - * @template T - * @param {Iterable} items list of items - * @param {function(T): Iterable} getDependencies function to get dependencies of an item (items that are not in list are ignored) - * @returns {Iterable} graph roots of the items + * @template {any[]} T */ -module.exports = (items, getDependencies) => { - /** @type {Map>} */ - const itemToNode = new Map(); - for (const item of items) { - const node = new Node(item); - itemToNode.set(item, node); +class TupleSet { + constructor(init) { + this._map = new Map(); + this.size = 0; + if (init) { + for (const tuple of init) { + this.add(...tuple); + } + } } - // early exit when there is only a single item - if (itemToNode.size <= 1) return items; - - // grab all the dependencies - for (const node of itemToNode.values()) { - for (const dep of getDependencies(node.item)) { - const depNode = itemToNode.get(dep); - if (depNode !== undefined) { - node.dependencies.add(depNode); + /** + * @param {T} args tuple + * @returns {void} + */ + add(...args) { + let map = this._map; + for (let i = 0; i < args.length - 2; i++) { + const arg = args[i]; + const innerMap = map.get(arg); + if (innerMap === undefined) { + map.set(arg, (map = new Map())); + } else { + map = innerMap; } } + + const beforeLast = args[args.length - 2]; + let set = map.get(beforeLast); + if (set === undefined) { + map.set(beforeLast, (set = new Set())); + } + + const last = args[args.length - 1]; + this.size -= set.size; + set.add(last); + this.size += set.size; } - // Set of current root modules - // items will be removed if a new reference to it has been found - /** @type {Set>} */ - const roots = new Set(); + /** + * @param {T} args tuple + * @returns {boolean} true, if the tuple is in the Set + */ + has(...args) { + let map = this._map; + for (let i = 0; i < args.length - 2; i++) { + const arg = args[i]; + map = map.get(arg); + if (map === undefined) { + return false; + } + } - // Set of current cycles without references to it - // cycles will be removed if a new reference to it has been found - // that is not part of the cycle - /** @type {Set>} */ - const rootCycles = new Set(); + const beforeLast = args[args.length - 2]; + let set = map.get(beforeLast); + if (set === undefined) { + return false; + } - // For all non-marked nodes - for (const selectedNode of itemToNode.values()) { - if (selectedNode.marker === NO_MARKER) { - // deep-walk all referenced modules - // in a non-recursive way + const last = args[args.length - 1]; + return set.has(last); + } - // start by entering the selected node - selectedNode.marker = IN_PROGRESS_MARKER; + /** + * @param {T} args tuple + * @returns {void} + */ + delete(...args) { + let map = this._map; + for (let i = 0; i < args.length - 2; i++) { + const arg = args[i]; + map = map.get(arg); + if (map === undefined) { + return; + } + } - // keep a stack to avoid recursive walk - /** @type {StackEntry[]} */ - const stack = [ - { - node: selectedNode, - openEdges: Array.from(selectedNode.dependencies) - } - ]; + const beforeLast = args[args.length - 2]; + let set = map.get(beforeLast); + if (set === undefined) { + return; + } - // process the top item until stack is empty - while (stack.length > 0) { - const topOfStack = stack[stack.length - 1]; + const last = args[args.length - 1]; + this.size -= set.size; + set.delete(last); + this.size += set.size; + } - // Are there still edges unprocessed in the current node? - if (topOfStack.openEdges.length > 0) { - // Process one dependency - const dependency = topOfStack.openEdges.pop(); - switch (dependency.marker) { - case NO_MARKER: - // dependency has not be visited yet - // mark it as in-progress and recurse - stack.push({ - node: dependency, - openEdges: Array.from(dependency.dependencies) - }); - dependency.marker = IN_PROGRESS_MARKER; - break; - case IN_PROGRESS_MARKER: { - // It's a in-progress cycle - let cycle = dependency.cycle; - if (!cycle) { - cycle = new Cycle(); - cycle.nodes.add(dependency); - dependency.cycle = cycle; - } - // set cycle property for each node in the cycle - // if nodes are already part of a cycle - // we merge the cycles to a shared cycle - for ( - let i = stack.length - 1; - stack[i].node !== dependency; - i-- - ) { - const node = stack[i].node; - if (node.cycle) { - if (node.cycle !== cycle) { - // merge cycles - for (const cycleNode of node.cycle.nodes) { - cycleNode.cycle = cycle; - cycle.nodes.add(cycleNode); - } - } - } else { - node.cycle = cycle; - cycle.nodes.add(node); - } - } - // don't recurse into dependencies - // these are already on the stack - break; - } - case DONE_AND_ROOT_MARKER: - // This node has be visited yet and is currently a root node - // But as this is a new reference to the node - // it's not really a root - // so we have to convert it to a normal node - dependency.marker = DONE_MARKER; - roots.delete(dependency); - break; - case DONE_MAYBE_ROOT_CYCLE_MARKER: - // This node has be visited yet and - // is maybe currently part of a completed root cycle - // we found a new reference to the cycle - // so it's not really a root cycle - // remove the cycle from the root cycles - // and convert it to a normal node - rootCycles.delete(dependency.cycle); - dependency.marker = DONE_MARKER; - break; - // DONE_MARKER: nothing to do, don't recurse into dependencies - } - } else { - // All dependencies of the current node has been visited - // we leave the node - stack.pop(); - topOfStack.node.marker = DONE_MARKER; - } - } - const cycle = selectedNode.cycle; - if (cycle) { - for (const node of cycle.nodes) { - node.marker = DONE_MAYBE_ROOT_CYCLE_MARKER; - } - rootCycles.add(cycle); + /** + * @returns {Iterator} iterator + */ + [Symbol.iterator]() { + const iteratorStack = []; + const tuple = []; + let currentSetIterator = undefined; + + const next = it => { + const result = it.next(); + if (result.done) { + if (iteratorStack.length === 0) return false; + tuple.pop(); + return next(iteratorStack.pop()); + } + const [key, value] = result.value; + iteratorStack.push(it); + tuple.push(key); + if (value instanceof Set) { + currentSetIterator = value[Symbol.iterator](); + return true; } else { - selectedNode.marker = DONE_AND_ROOT_MARKER; - roots.add(selectedNode); + return next(value[Symbol.iterator]()); } - } - } + }; - // Extract roots from root cycles - // We take the nodes with most incoming edges - // inside of the cycle - for (const cycle of rootCycles) { - let max = 0; - /** @type {Set>} */ - const cycleRoots = new Set(); - const nodes = cycle.nodes; - for (const node of nodes) { - for (const dep of node.dependencies) { - if (nodes.has(dep)) { - dep.incoming++; - if (dep.incoming < max) continue; - if (dep.incoming > max) { - cycleRoots.clear(); - max = dep.incoming; + next(this._map[Symbol.iterator]()); + + return { + next() { + while (currentSetIterator) { + const result = currentSetIterator.next(); + if (result.done) { + tuple.pop(); + if (!next(iteratorStack.pop())) { + currentSetIterator = undefined; + } + } else { + return { + done: false, + value: /** @type {T} */ (tuple.concat(result.value)) + }; } - cycleRoots.add(dep); } + return { done: true, value: undefined }; } - } - for (const cycleRoot of cycleRoots) { - roots.add(cycleRoot); - } + }; } +} - // When roots were found, return them - if (roots.size > 0) { - return Array.from(roots, r => r.item); - } else { - throw new Error("Implementation of findGraphRoots is broken"); - } -}; +module.exports = TupleSet; /***/ }), -/***/ 93204: -/***/ (function(__unused_webpack_module, exports, __webpack_require__) { +/***/ 49606: +/***/ (function(__unused_webpack_module, exports) { "use strict"; /* MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra + Author Ivan Kopeykin @vankop */ -const path = __webpack_require__(85622); - -/** @typedef {import("../../declarations/WebpackOptions").WatchOptions} WatchOptions */ -/** @typedef {import("../FileSystemInfo").FileSystemInfoEntry} FileSystemInfoEntry */ +/** @typedef {import("./fs").InputFileSystem} InputFileSystem */ +/** @typedef {(error: Error|null, result?: Buffer) => void} ErrorFirstCallback */ +const backSlashCharCode = "\\".charCodeAt(0); +const slashCharCode = "/".charCodeAt(0); +const aLowerCaseCharCode = "a".charCodeAt(0); +const zLowerCaseCharCode = "z".charCodeAt(0); +const aUpperCaseCharCode = "A".charCodeAt(0); +const zUpperCaseCharCode = "Z".charCodeAt(0); +const _0CharCode = "0".charCodeAt(0); +const _9CharCode = "9".charCodeAt(0); +const plusCharCode = "+".charCodeAt(0); +const hyphenCharCode = "-".charCodeAt(0); +const colonCharCode = ":".charCodeAt(0); +const hashCharCode = "#".charCodeAt(0); +const queryCharCode = "?".charCodeAt(0); /** - * @typedef {Object} IStats - * @property {() => boolean} isFile - * @property {() => boolean} isDirectory - * @property {() => boolean} isBlockDevice - * @property {() => boolean} isCharacterDevice - * @property {() => boolean} isSymbolicLink - * @property {() => boolean} isFIFO - * @property {() => boolean} isSocket - * @property {number | bigint} dev - * @property {number | bigint} ino - * @property {number | bigint} mode - * @property {number | bigint} nlink - * @property {number | bigint} uid - * @property {number | bigint} gid - * @property {number | bigint} rdev - * @property {number | bigint} size - * @property {number | bigint} blksize - * @property {number | bigint} blocks - * @property {number | bigint} atimeMs - * @property {number | bigint} mtimeMs - * @property {number | bigint} ctimeMs - * @property {number | bigint} birthtimeMs - * @property {Date} atime - * @property {Date} mtime - * @property {Date} ctime - * @property {Date} birthtime + * Get scheme if specifier is an absolute URL specifier + * e.g. Absolute specifiers like 'file:///user/webpack/index.js' + * https://tools.ietf.org/html/rfc3986#section-3.1 + * @param {string} specifier specifier + * @returns {string|undefined} scheme if absolute URL specifier provided */ +function getScheme(specifier) { + const start = specifier.charCodeAt(0); -/** - * @typedef {Object} IDirent - * @property {() => boolean} isFile - * @property {() => boolean} isDirectory - * @property {() => boolean} isBlockDevice - * @property {() => boolean} isCharacterDevice - * @property {() => boolean} isSymbolicLink - * @property {() => boolean} isFIFO - * @property {() => boolean} isSocket - * @property {string | Buffer} name - */ + // First char maybe only a letter + if ( + (start < aLowerCaseCharCode || start > zLowerCaseCharCode) && + (start < aUpperCaseCharCode || start > zUpperCaseCharCode) + ) { + return undefined; + } -/** @typedef {function((NodeJS.ErrnoException | null)=): void} Callback */ -/** @typedef {function((NodeJS.ErrnoException | null)=, Buffer=): void} BufferCallback */ -/** @typedef {function((NodeJS.ErrnoException | null)=, Buffer|string=): void} BufferOrStringCallback */ -/** @typedef {function((NodeJS.ErrnoException | null)=, (string | Buffer)[] | IDirent[]=): void} DirentArrayCallback */ -/** @typedef {function((NodeJS.ErrnoException | null)=, string=): void} StringCallback */ -/** @typedef {function((NodeJS.ErrnoException | null)=, number=): void} NumberCallback */ -/** @typedef {function((NodeJS.ErrnoException | null)=, IStats=): void} StatsCallback */ -/** @typedef {function((NodeJS.ErrnoException | Error | null)=, any=): void} ReadJsonCallback */ -/** @typedef {function((NodeJS.ErrnoException | Error | null)=, IStats|string=): void} LstatReadlinkAbsoluteCallback */ + let i = 1; + let ch = specifier.charCodeAt(i); -/** - * @typedef {Object} Watcher - * @property {function(): void} close closes the watcher and all underlying file watchers - * @property {function(): void} pause closes the watcher, but keeps underlying file watchers alive until the next watch call - * @property {function(): Set=} getAggregatedChanges get current aggregated changes that have not yet send to callback - * @property {function(): Set=} getAggregatedRemovals get current aggregated removals that have not yet send to callback - * @property {function(): Map} getFileTimeInfoEntries get info about files - * @property {function(): Map} getContextTimeInfoEntries get info about directories - */ + while ( + (ch >= aLowerCaseCharCode && ch <= zLowerCaseCharCode) || + (ch >= aUpperCaseCharCode && ch <= zUpperCaseCharCode) || + (ch >= _0CharCode && ch <= _9CharCode) || + ch === plusCharCode || + ch === hyphenCharCode + ) { + if (++i === specifier.length) return undefined; + ch = specifier.charCodeAt(i); + } -/** - * @callback WatchMethod - * @param {Iterable} files watched files - * @param {Iterable} directories watched directories - * @param {Iterable} missing watched exitance entries - * @param {number} startTime timestamp of start time - * @param {WatchOptions} options options object - * @param {function(Error=, Map, Map, Set, Set): void} callback aggregated callback - * @param {function(string, number): void} callbackUndelayed callback when the first change was detected - * @returns {Watcher} a watcher - */ + // Scheme must end with colon + if (ch !== colonCharCode) return undefined; -// TODO webpack 6 make optional methods required + // Check for Windows absolute path + // https://url.spec.whatwg.org/#url-miscellaneous + if (i === 1) { + const nextChar = i + 1 < specifier.length ? specifier.charCodeAt(i + 1) : 0; + if ( + nextChar === 0 || + nextChar === backSlashCharCode || + nextChar === slashCharCode || + nextChar === hashCharCode || + nextChar === queryCharCode + ) { + return undefined; + } + } -/** - * @typedef {Object} OutputFileSystem - * @property {function(string, Buffer|string, Callback): void} writeFile - * @property {function(string, Callback): void} mkdir - * @property {function(string, DirentArrayCallback): void=} readdir - * @property {function(string, Callback): void=} rmdir - * @property {function(string, Callback): void=} unlink - * @property {function(string, StatsCallback): void} stat - * @property {function(string, StatsCallback): void=} lstat - * @property {function(string, BufferOrStringCallback): void} readFile - * @property {(function(string, string): string)=} join - * @property {(function(string, string): string)=} relative - * @property {(function(string): string)=} dirname - */ + return specifier.slice(0, i).toLowerCase(); +} /** - * @typedef {Object} InputFileSystem - * @property {function(string, BufferOrStringCallback): void} readFile - * @property {(function(string, ReadJsonCallback): void)=} readJson - * @property {function(string, BufferOrStringCallback): void} readlink - * @property {function(string, DirentArrayCallback): void} readdir - * @property {function(string, StatsCallback): void} stat - * @property {function(string, StatsCallback): void=} lstat - * @property {(function(string, BufferOrStringCallback): void)=} realpath - * @property {(function(string=): void)=} purge - * @property {(function(string, string): string)=} join - * @property {(function(string, string): string)=} relative - * @property {(function(string): string)=} dirname + * @param {string} specifier specifier + * @returns {string|null} protocol if absolute URL specifier provided */ +function getProtocol(specifier) { + const scheme = getScheme(specifier); + return scheme === undefined ? undefined : scheme + ":"; +} -/** - * @typedef {Object} WatchFileSystem - * @property {WatchMethod} watch - */ +exports.getScheme = getScheme; +exports.getProtocol = getProtocol; -/** - * @typedef {Object} IntermediateFileSystemExtras - * @property {function(string): void} mkdirSync - * @property {function(string): NodeJS.WritableStream} createWriteStream - * @property {function(string, string, NumberCallback): void} open - * @property {function(number, Buffer, number, number, number, NumberCallback): void} read - * @property {function(number, Callback): void} close - * @property {function(string, string, Callback): void} rename - */ -/** @typedef {InputFileSystem & OutputFileSystem & IntermediateFileSystemExtras} IntermediateFileSystem */ +/***/ }), -/** - * - * @param {InputFileSystem|OutputFileSystem|undefined} fs a file system - * @param {string} rootPath the root path - * @param {string} targetPath the target path - * @returns {string} location of targetPath relative to rootPath - */ -const relative = (fs, rootPath, targetPath) => { - if (fs && fs.relative) { - return fs.relative(rootPath, targetPath); - } else if (path.posix.isAbsolute(rootPath)) { - return path.posix.relative(rootPath, targetPath); - } else if (path.win32.isAbsolute(rootPath)) { - return path.win32.relative(rootPath, targetPath); - } else { - throw new Error( - `${rootPath} is neither a posix nor a windows path, and there is no 'relative' method defined in the file system` - ); - } -}; -exports.relative = relative; +/***/ 73963: +/***/ (function(module) { + +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ -/** - * @param {InputFileSystem|OutputFileSystem|undefined} fs a file system - * @param {string} rootPath a path - * @param {string} filename a filename - * @returns {string} the joined path - */ -const join = (fs, rootPath, filename) => { - if (fs && fs.join) { - return fs.join(rootPath, filename); - } else if (path.posix.isAbsolute(rootPath)) { - return path.posix.join(rootPath, filename); - } else if (path.win32.isAbsolute(rootPath)) { - return path.win32.join(rootPath, filename); - } else { - throw new Error( - `${rootPath} is neither a posix nor a windows path, and there is no 'join' method defined in the file system` - ); - } -}; -exports.join = join; + + +const isWeakKey = thing => typeof thing === "object" && thing !== null; /** - * @param {InputFileSystem|OutputFileSystem|undefined} fs a file system - * @param {string} absPath an absolute path - * @returns {string} the parent directory of the absolute path + * @template {any[]} T + * @template V */ -const dirname = (fs, absPath) => { - if (fs && fs.dirname) { - return fs.dirname(absPath); - } else if (path.posix.isAbsolute(absPath)) { - return path.posix.dirname(absPath); - } else if (path.win32.isAbsolute(absPath)) { - return path.win32.dirname(absPath); - } else { - throw new Error( - `${absPath} is neither a posix nor a windows path, and there is no 'dirname' method defined in the file system` - ); +class WeakTupleMap { + constructor() { + /** @private */ + this.f = 0; + /** @private @type {any} */ + this.v = undefined; + /** @private @type {Map> | undefined} */ + this.m = undefined; + /** @private @type {WeakMap> | undefined} */ + this.w = undefined; } -}; -exports.dirname = dirname; -/** - * @param {OutputFileSystem} fs a file system - * @param {string} p an absolute path - * @param {function(Error=): void} callback callback function for the error - * @returns {void} - */ -const mkdirp = (fs, p, callback) => { - fs.mkdir(p, err => { - if (err) { - if (err.code === "ENOENT") { - const dir = dirname(fs, p); - if (dir === p) { - callback(err); - return; - } - mkdirp(fs, dir, err => { - if (err) { - callback(err); - return; - } - fs.mkdir(p, err => { - if (err) { - if (err.code === "EEXIST") { - callback(); - return; - } - callback(err); - return; - } - callback(); - }); - }); - return; - } else if (err.code === "EEXIST") { - callback(); - return; - } - callback(err); - return; + /** + * @param {[...T, V]} args tuple + * @returns {void} + */ + set(...args) { + /** @type {WeakTupleMap} */ + let node = this; + for (let i = 0; i < args.length - 1; i++) { + node = node._get(args[i]); } - callback(); - }); -}; -exports.mkdirp = mkdirp; + node._setValue(args[args.length - 1]); + } -/** - * @param {IntermediateFileSystem} fs a file system - * @param {string} p an absolute path - * @returns {void} - */ -const mkdirpSync = (fs, p) => { - try { - fs.mkdirSync(p); - } catch (err) { - if (err) { - if (err.code === "ENOENT") { - const dir = dirname(fs, p); - if (dir === p) { - throw err; - } - mkdirpSync(fs, dir); - fs.mkdirSync(p); - return; - } else if (err.code === "EEXIST") { - return; - } - throw err; + /** + * @param {T} args tuple + * @returns {boolean} true, if the tuple is in the Set + */ + has(...args) { + /** @type {WeakTupleMap} */ + let node = this; + for (let i = 0; i < args.length; i++) { + node = node._peek(args[i]); + if (node === undefined) return false; } + return node._hasValue(); } -}; -exports.mkdirpSync = mkdirpSync; -/** - * @param {InputFileSystem} fs a file system - * @param {string} p an absolute path - * @param {ReadJsonCallback} callback callback - * @returns {void} - */ -const readJson = (fs, p, callback) => { - if ("readJson" in fs) return fs.readJson(p, callback); - fs.readFile(p, (err, buf) => { - if (err) return callback(err); - let data; - try { - data = JSON.parse(buf.toString("utf-8")); - } catch (e) { - return callback(e); + /** + * @param {T} args tuple + * @returns {V} the value + */ + get(...args) { + /** @type {WeakTupleMap} */ + let node = this; + for (let i = 0; i < args.length; i++) { + node = node._peek(args[i]); + if (node === undefined) return undefined; } - return callback(null, data); - }); -}; -exports.readJson = readJson; + return node._getValue(); + } -/** - * @param {InputFileSystem} fs a file system - * @param {string} p an absolute path - * @param {ReadJsonCallback} callback callback - * @returns {void} - */ -const lstatReadlinkAbsolute = (fs, p, callback) => { - let i = 3; - const doReadLink = () => { - fs.readlink(p, (err, target) => { - if (err && --i > 0) { - // It might was just changed from symlink to file - // we retry 2 times to catch this case before throwing the error - return doStat(); - } - if (err || !target) return doStat(); - const value = target.toString(); - callback(null, join(fs, dirname(fs, p), value)); - }); - }; - const doStat = () => { - if ("lstat" in fs) { - return fs.lstat(p, (err, stats) => { - if (err) return callback(err); - if (stats.isSymbolicLink()) { - return doReadLink(); - } - callback(null, stats); - }); - } else { - return fs.stat(p, callback); + /** + * @param {[...T, function(): V]} args tuple + * @returns {V} the value + */ + provide(...args) { + /** @type {WeakTupleMap} */ + let node = this; + for (let i = 0; i < args.length - 1; i++) { + node = node._get(args[i]); } - }; - if ("lstat" in fs) return doStat(); - doReadLink(); -}; -exports.lstatReadlinkAbsolute = lstatReadlinkAbsolute; - - -/***/ }), + if (node._hasValue()) return node._getValue(); + const fn = args[args.length - 1]; + const newValue = fn(...args.slice(0, -1)); + node._setValue(newValue); + return newValue; + } -/***/ 32928: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + /** + * @param {T} args tuple + * @returns {void} + */ + delete(...args) { + /** @type {WeakTupleMap} */ + let node = this; + for (let i = 0; i < args.length; i++) { + node = node._peek(args[i]); + if (node === undefined) return; + } + node._deleteValue(); + } -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ + /** + * @returns {void} + */ + clear() { + this.f = 0; + this.v = undefined; + this.w = undefined; + this.m = undefined; + } + _getValue() { + return this.v; + } + _hasValue() { + return (this.f & 1) === 1; + } -const Hash = __webpack_require__(21301); -const MAX_SHORT_STRING = __webpack_require__(21941).MAX_SHORT_STRING; + _setValue(v) { + this.f |= 1; + this.v = v; + } -class BatchedHash extends Hash { - constructor(hash) { - super(); - this.string = undefined; - this.encoding = undefined; - this.hash = hash; + _deleteValue() { + this.f &= 6; + this.v = undefined; } - /** - * Update hash {@link https://nodejs.org/api/crypto.html#crypto_hash_update_data_inputencoding} - * @param {string|Buffer} data data - * @param {string=} inputEncoding data encoding - * @returns {this} updated hash - */ - update(data, inputEncoding) { - if (this.string !== undefined) { - if ( - typeof data === "string" && - inputEncoding === this.encoding && - this.string.length + data.length < MAX_SHORT_STRING - ) { - this.string += data; - return this; - } - this.hash.update(this.string, this.encoding); - this.string = undefined; - } - if (typeof data === "string") { - if ( - data.length < MAX_SHORT_STRING && - // base64 encoding is not valid since it may contain padding chars - (!inputEncoding || !inputEncoding.startsWith("ba")) - ) { - this.string = data; - this.encoding = inputEncoding; - } else { - this.hash.update(data, inputEncoding); - } + _peek(thing) { + if (isWeakKey(thing)) { + if ((this.f & 4) !== 4) return undefined; + return this.w.get(thing); } else { - this.hash.update(data); + if ((this.f & 2) !== 2) return undefined; + return this.m.get(thing); } - return this; } - /** - * Calculates the digest {@link https://nodejs.org/api/crypto.html#crypto_hash_digest_encoding} - * @param {string=} encoding encoding of the return value - * @returns {string|Buffer} digest - */ - digest(encoding) { - if (this.string !== undefined) { - this.hash.update(this.string, this.encoding); + _get(thing) { + if (isWeakKey(thing)) { + if ((this.f & 4) !== 4) { + const newMap = new WeakMap(); + this.f |= 4; + const newNode = new WeakTupleMap(); + (this.w = newMap).set(thing, newNode); + return newNode; + } + const entry = this.w.get(thing); + if (entry !== undefined) { + return entry; + } + const newNode = new WeakTupleMap(); + this.w.set(thing, newNode); + return newNode; + } else { + if ((this.f & 2) !== 2) { + const newMap = new Map(); + this.f |= 2; + const newNode = new WeakTupleMap(); + (this.m = newMap).set(thing, newNode); + return newNode; + } + const entry = this.m.get(thing); + if (entry !== undefined) { + return entry; + } + const newNode = new WeakTupleMap(); + this.m.set(thing, newNode); + return newNode; } - return this.hash.digest(encoding); } } -module.exports = BatchedHash; +module.exports = WeakTupleMap; /***/ }), -/***/ 20487: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { +/***/ 44795: +/***/ (function(module) { "use strict"; /* MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra + Author Mikola Lysenko @mikolalysenko */ -const create = __webpack_require__(21941); +/* cspell:disable-next-line */ +// Refactor: Peter Somogyvari @petermetz -//#region wasm code: md4 (../../../assembly/hash/md4.asm.ts) --initialMemory 1 -const md4 = new WebAssembly.Module( - Buffer.from( - // 2156 bytes - "AGFzbQEAAAABCAJgAX8AYAAAAwUEAQAAAAUDAQABBhoFfwFBAAt/AUEAC38BQQALfwFBAAt/AUEACwciBARpbml0AAAGdXBkYXRlAAIFZmluYWwAAwZtZW1vcnkCAAqLEAQmAEGBxpS6BiQBQYnXtv5+JAJB/rnrxXkkA0H2qMmBASQEQQAkAAvSCgEZfyMBIQUjAiECIwMhAyMEIQQDQCAAIAFLBEAgASgCJCISIAEoAiAiEyABKAIcIgkgASgCGCIIIAEoAhQiByABKAIQIg4gASgCDCIGIAEoAggiDyABKAIEIhAgASgCACIRIAMgBHMgAnEgBHMgBWpqQQN3IgogAiADc3EgA3MgBGpqQQd3IgsgAiAKc3EgAnMgA2pqQQt3IgwgCiALc3EgCnMgAmpqQRN3Ig0gCyAMc3EgC3MgCmpqQQN3IgogDCANc3EgDHMgC2pqQQd3IgsgCiANc3EgDXMgDGpqQQt3IgwgCiALc3EgCnMgDWpqQRN3Ig0gCyAMc3EgC3MgCmpqQQN3IhQgDCANc3EgDHMgC2pqQQd3IRUgASgCLCILIAEoAigiCiAMIA0gDSAUcyAVcXNqakELdyIWIBQgFXNxIBRzIA1qakETdyEXIAEoAjQiGCABKAIwIhkgFSAWcyAXcSAVcyAUampBA3ciFCAWIBdzcSAWcyAVampBB3chFSABKAI8Ig0gASgCOCIMIBQgF3MgFXEgF3MgFmpqQQt3IhYgFCAVc3EgFHMgF2pqQRN3IRcgEyAOIBEgFCAVIBZyIBdxIBUgFnFyampBmfOJ1AVqQQN3IhQgFiAXcnEgFiAXcXIgFWpqQZnzidQFakEFdyIVIBQgF3JxIBQgF3FyIBZqakGZ84nUBWpBCXchFiAPIBggEiAWIAcgFSAQIBQgGSAUIBVyIBZxIBQgFXFyIBdqakGZ84nUBWpBDXciFCAVIBZycSAVIBZxcmpqQZnzidQFakEDdyIVIBQgFnJxIBQgFnFyampBmfOJ1AVqQQV3IhcgFCAVcnEgFCAVcXJqakGZ84nUBWpBCXciFiAVIBdycSAVIBdxciAUampBmfOJ1AVqQQ13IhQgFiAXcnEgFiAXcXIgFWpqQZnzidQFakEDdyEVIBEgBiAVIAwgFCAKIBYgCCAUIBZyIBVxIBQgFnFyIBdqakGZ84nUBWpBBXciFyAUIBVycSAUIBVxcmpqQZnzidQFakEJdyIWIBUgF3JxIBUgF3FyampBmfOJ1AVqQQ13IhQgFiAXcnEgFiAXcXJqakGZ84nUBWpBA3ciFSALIBYgCSAUIBZyIBVxIBQgFnFyIBdqakGZ84nUBWpBBXciFiAUIBVycSAUIBVxcmpqQZnzidQFakEJdyIXIA0gFSAWciAXcSAVIBZxciAUampBmfOJ1AVqQQ13IhRzIBZzampBodfn9gZqQQN3IREgByAIIA4gFCARIBcgESAUc3MgFmogE2pBodfn9gZqQQl3IhNzcyAXampBodfn9gZqQQt3Ig4gDyARIBMgDiARIA4gE3NzIBRqIBlqQaHX5/YGakEPdyIRc3NqakGh1+f2BmpBA3ciDyAOIA8gEXNzIBNqIApqQaHX5/YGakEJdyIKcyARc2pqQaHX5/YGakELdyIIIBAgDyAKIAggDCAPIAggCnNzIBFqakGh1+f2BmpBD3ciDHNzampBodfn9gZqQQN3Ig4gEiAIIAwgDnNzIApqakGh1+f2BmpBCXciCHMgDHNqakGh1+f2BmpBC3chByAFIAYgCCAHIBggDiAHIAhzcyAMampBodfn9gZqQQ93IgpzcyAOampBodfn9gZqQQN3IgZqIQUgDSAGIAkgByAGIAsgByAGIApzcyAIampBodfn9gZqQQl3IgdzIApzampBodfn9gZqQQt3IgYgB3NzIApqakGh1+f2BmpBD3cgAmohAiADIAZqIQMgBCAHaiEEIAFBQGshAQwBCwsgBSQBIAIkAiADJAMgBCQECw0AIAAQASAAIwBqJAAL/wQCA38BfiAAIwBqrUIDhiEEIABByABqQUBxIgJBCGshAyAAIgFBAWohACABQYABOgAAA0AgACACSUEAIABBB3EbBEAgAEEAOgAAIABBAWohAAwBCwsDQCAAIAJJBEAgAEIANwMAIABBCGohAAwBCwsgAyAENwMAIAIQAUEAIwGtIgRC//8DgyAEQoCA/P8Pg0IQhoQiBEL/gYCA8B+DIARCgP6DgIDgP4NCCIaEIgRCj4C8gPCBwAeDQgiGIARC8IHAh4CegPgAg0IEiIQiBEKGjJiw4MCBgwZ8QgSIQoGChIiQoMCAAYNCJ34gBEKw4MCBg4aMmDCEfDcDAEEIIwKtIgRC//8DgyAEQoCA/P8Pg0IQhoQiBEL/gYCA8B+DIARCgP6DgIDgP4NCCIaEIgRCj4C8gPCBwAeDQgiGIARC8IHAh4CegPgAg0IEiIQiBEKGjJiw4MCBgwZ8QgSIQoGChIiQoMCAAYNCJ34gBEKw4MCBg4aMmDCEfDcDAEEQIwOtIgRC//8DgyAEQoCA/P8Pg0IQhoQiBEL/gYCA8B+DIARCgP6DgIDgP4NCCIaEIgRCj4C8gPCBwAeDQgiGIARC8IHAh4CegPgAg0IEiIQiBEKGjJiw4MCBgwZ8QgSIQoGChIiQoMCAAYNCJ34gBEKw4MCBg4aMmDCEfDcDAEEYIwStIgRC//8DgyAEQoCA/P8Pg0IQhoQiBEL/gYCA8B+DIARCgP6DgIDgP4NCCIaEIgRCj4C8gPCBwAeDQgiGIARC8IHAh4CegPgAg0IEiIQiBEKGjJiw4MCBgwZ8QgSIQoGChIiQoMCAAYNCJ34gBEKw4MCBg4aMmDCEfDcDAAs=", - "base64" - ) -); -//#endregion +const compileSearch = (funcName, predicate, reversed, extraArgs, earlyOut) => { + const code = [ + "function ", + funcName, + "(a,l,h,", + extraArgs.join(","), + "){", + earlyOut ? "" : "var i=", + reversed ? "l-1" : "h+1", + ";while(l<=h){var m=(l+h)>>>1,x=a[m]" + ]; -module.exports = create.bind(null, md4, [], 64, 32); + if (earlyOut) { + if (predicate.indexOf("c") < 0) { + code.push(";if(x===y){return m}else if(x<=y){"); + } else { + code.push(";var p=c(x,y);if(p===0){return m}else if(p<=0){"); + } + } else { + code.push(";if(", predicate, "){i=m;"); + } + if (reversed) { + code.push("l=m+1}else{h=m-1}"); + } else { + code.push("h=m-1}else{l=m+1}"); + } + code.push("}"); + if (earlyOut) { + code.push("return -1};"); + } else { + code.push("return i};"); + } + return code.join(""); +}; + +const compileBoundsSearch = (predicate, reversed, suffix, earlyOut) => { + const arg1 = compileSearch( + "A", + "x" + predicate + "y", + reversed, + ["y"], + earlyOut + ); + + const arg2 = compileSearch( + "P", + "c(x,y)" + predicate + "0", + reversed, + ["y", "c"], + earlyOut + ); + + const fnHeader = "function dispatchBinarySearch"; + + const fnBody = + "(a,y,c,l,h){\ +if(typeof(c)==='function'){\ +return P(a,(l===void 0)?0:l|0,(h===void 0)?a.length-1:h|0,y,c)\ +}else{\ +return A(a,(c===void 0)?0:c|0,(l===void 0)?a.length-1:l|0,y)\ +}}\ +return dispatchBinarySearch"; + + const fnArgList = [arg1, arg2, fnHeader, suffix, fnBody, suffix]; + const fnSource = fnArgList.join(""); + const result = new Function(fnSource); + return result(); +}; + +module.exports = { + ge: compileBoundsSearch(">=", false, "GE"), + gt: compileBoundsSearch(">", false, "GT"), + lt: compileBoundsSearch("<", true, "LT"), + le: compileBoundsSearch("<=", true, "LE"), + eq: compileBoundsSearch("-", true, "EQ", true) +}; /***/ }), -/***/ 21941: -/***/ (function(module) { +/***/ 11217: +/***/ (function(__unused_webpack_module, exports) { "use strict"; /* @@ -127755,843 +126644,1039 @@ module.exports = create.bind(null, md4, [], 64, 32); -// 65536 is the size of a wasm memory page -// 64 is the maximum chunk size for every possible wasm hash implementation -// 4 is the maximum number of bytes per char for string encoding (max is utf-8) -// ~3 makes sure that it's always a block of 4 chars, so avoid partially encoded bytes for base64 -const MAX_SHORT_STRING = Math.floor((65536 - 64) / 4) & ~3; +/** @type {WeakMap>} */ +const mergeCache = new WeakMap(); +/** @type {WeakMap>>} */ +const setPropertyCache = new WeakMap(); +const DELETE = Symbol("DELETE"); +const DYNAMIC_INFO = Symbol("cleverMerge dynamic info"); -class WasmHash { - /** - * @param {WebAssembly.Instance} instance wasm instance - * @param {WebAssembly.Instance[]} instancesPool pool of instances - * @param {number} chunkSize size of data chunks passed to wasm - * @param {number} digestSize size of digest returned by wasm - */ - constructor(instance, instancesPool, chunkSize, digestSize) { - const exports = /** @type {any} */ (instance.exports); - exports.init(); - this.exports = exports; - this.mem = Buffer.from(exports.memory.buffer, 0, 65536); - this.buffered = 0; - this.instancesPool = instancesPool; - this.chunkSize = chunkSize; - this.digestSize = digestSize; +/** + * Merges two given objects and caches the result to avoid computation if same objects passed as arguments again. + * @template T + * @template O + * @example + * // performs cleverMerge(first, second), stores the result in WeakMap and returns result + * cachedCleverMerge({a: 1}, {a: 2}) + * {a: 2} + * // when same arguments passed, gets the result from WeakMap and returns it. + * cachedCleverMerge({a: 1}, {a: 2}) + * {a: 2} + * @param {T} first first object + * @param {O} second second object + * @returns {T & O | T | O} merged object of first and second object + */ +const cachedCleverMerge = (first, second) => { + if (second === undefined) return first; + if (first === undefined) return second; + if (typeof second !== "object" || second === null) return second; + if (typeof first !== "object" || first === null) return first; + + let innerCache = mergeCache.get(first); + if (innerCache === undefined) { + innerCache = new WeakMap(); + mergeCache.set(first, innerCache); } + const prevMerge = innerCache.get(second); + if (prevMerge !== undefined) return prevMerge; + const newMerge = _cleverMerge(first, second, true); + innerCache.set(second, newMerge); + return newMerge; +}; - reset() { - this.buffered = 0; - this.exports.init(); +/** + * @template T + * @param {Partial} obj object + * @param {string} property property + * @param {string|number|boolean} value assignment value + * @returns {T} new object + */ +const cachedSetProperty = (obj, property, value) => { + let mapByProperty = setPropertyCache.get(obj); + + if (mapByProperty === undefined) { + mapByProperty = new Map(); + setPropertyCache.set(obj, mapByProperty); } - /** - * @param {Buffer | string} data data - * @param {BufferEncoding=} encoding encoding - * @returns {this} itself - */ - update(data, encoding) { - if (typeof data === "string") { - while (data.length > MAX_SHORT_STRING) { - this._updateWithShortString(data.slice(0, MAX_SHORT_STRING), encoding); - data = data.slice(MAX_SHORT_STRING); - } - this._updateWithShortString(data, encoding); - return this; - } - this._updateWithBuffer(data); - return this; + let mapByValue = mapByProperty.get(property); + + if (mapByValue === undefined) { + mapByValue = new Map(); + mapByProperty.set(property, mapByValue); } - /** - * @param {string} data data - * @param {BufferEncoding=} encoding encoding - * @returns {void} - */ - _updateWithShortString(data, encoding) { - const { exports, buffered, mem, chunkSize } = this; - let endPos; - if (data.length < 70) { - if (!encoding || encoding === "utf-8" || encoding === "utf8") { - endPos = buffered; - for (let i = 0; i < data.length; i++) { - const cc = data.charCodeAt(i); - if (cc < 0x80) mem[endPos++] = cc; - else if (cc < 0x800) { - mem[endPos] = (cc >> 6) | 0xc0; - mem[endPos + 1] = (cc & 0x3f) | 0x80; - endPos += 2; - } else { - // bail-out for weird chars - endPos += mem.write(data.slice(i), endPos, encoding); - break; + let result = mapByValue.get(value); + + if (result) return result; + + result = { + ...obj, + [property]: value + }; + mapByValue.set(value, result); + + return result; +}; + +/** + * @typedef {Object} ObjectParsedPropertyEntry + * @property {any | undefined} base base value + * @property {string | undefined} byProperty the name of the selector property + * @property {Map} byValues value depending on selector property, merged with base + */ + +/** + * @typedef {Object} ParsedObject + * @property {Map} static static properties (key is property name) + * @property {{ byProperty: string, fn: Function } | undefined} dynamic dynamic part + */ + +/** @type {WeakMap} */ +const parseCache = new WeakMap(); + +/** + * @param {object} obj the object + * @returns {ParsedObject} parsed object + */ +const cachedParseObject = obj => { + const entry = parseCache.get(obj); + if (entry !== undefined) return entry; + const result = parseObject(obj); + parseCache.set(obj, result); + return result; +}; + +/** + * @param {object} obj the object + * @returns {ParsedObject} parsed object + */ +const parseObject = obj => { + const info = new Map(); + let dynamicInfo; + const getInfo = p => { + const entry = info.get(p); + if (entry !== undefined) return entry; + const newEntry = { + base: undefined, + byProperty: undefined, + byValues: undefined + }; + info.set(p, newEntry); + return newEntry; + }; + for (const key of Object.keys(obj)) { + if (key.startsWith("by")) { + const byProperty = key; + const byObj = obj[byProperty]; + if (typeof byObj === "object") { + for (const byValue of Object.keys(byObj)) { + const obj = byObj[byValue]; + for (const key of Object.keys(obj)) { + const entry = getInfo(key); + if (entry.byProperty === undefined) { + entry.byProperty = byProperty; + entry.byValues = new Map(); + } else if (entry.byProperty !== byProperty) { + throw new Error( + `${byProperty} and ${entry.byProperty} for a single property is not supported` + ); + } + entry.byValues.set(byValue, obj[key]); + if (byValue === "default") { + for (const otherByValue of Object.keys(byObj)) { + if (!entry.byValues.has(otherByValue)) + entry.byValues.set(otherByValue, undefined); + } + } } } - } else if (encoding === "latin1") { - endPos = buffered; - for (let i = 0; i < data.length; i++) { - const cc = data.charCodeAt(i); - mem[endPos++] = cc; + } else if (typeof byObj === "function") { + if (dynamicInfo === undefined) { + dynamicInfo = { + byProperty: key, + fn: byObj + }; + } else { + throw new Error( + `${key} and ${dynamicInfo.byProperty} when both are functions is not supported` + ); } } else { - endPos = buffered + mem.write(data, buffered, encoding); + const entry = getInfo(key); + entry.base = obj[key]; } } else { - endPos = buffered + mem.write(data, buffered, encoding); - } - if (endPos < chunkSize) { - this.buffered = endPos; - } else { - const l = endPos & ~(this.chunkSize - 1); - exports.update(l); - const newBuffered = endPos - l; - this.buffered = newBuffered; - if (newBuffered > 0) mem.copyWithin(0, l, endPos); + const entry = getInfo(key); + entry.base = obj[key]; } } + return { + static: info, + dynamic: dynamicInfo + }; +}; - /** - * @param {Buffer} data data - * @returns {void} - */ - _updateWithBuffer(data) { - const { exports, buffered, mem } = this; - const length = data.length; - if (buffered + length < this.chunkSize) { - data.copy(mem, buffered, 0, length); - this.buffered += length; - } else { - const l = (buffered + length) & ~(this.chunkSize - 1); - if (l > 65536) { - let i = 65536 - buffered; - data.copy(mem, buffered, 0, i); - exports.update(65536); - const stop = l - buffered - 65536; - while (i < stop) { - data.copy(mem, 0, i, i + 65536); - exports.update(65536); - i += 65536; - } - data.copy(mem, 0, i, l - buffered); - exports.update(l - buffered - i); - } else { - data.copy(mem, buffered, 0, l - buffered); - exports.update(l); +/** + * @param {Map} info static properties (key is property name) + * @param {{ byProperty: string, fn: Function } | undefined} dynamicInfo dynamic part + * @returns {object} the object + */ +const serializeObject = (info, dynamicInfo) => { + const obj = {}; + // Setup byProperty structure + for (const entry of info.values()) { + if (entry.byProperty !== undefined) { + const byObj = (obj[entry.byProperty] = obj[entry.byProperty] || {}); + for (const byValue of entry.byValues.keys()) { + byObj[byValue] = byObj[byValue] || {}; } - const newBuffered = length + buffered - l; - this.buffered = newBuffered; - if (newBuffered > 0) data.copy(mem, 0, length - newBuffered, length); } } - - digest(type) { - const { exports, buffered, mem, digestSize } = this; - exports.final(buffered); - this.instancesPool.push(this); - const hex = mem.toString("latin1", 0, digestSize); - if (type === "hex") return hex; - if (type === "binary" || !type) return Buffer.from(hex, "hex"); - return Buffer.from(hex, "hex").toString(type); + for (const [key, entry] of info) { + if (entry.base !== undefined) { + obj[key] = entry.base; + } + // Fill byProperty structure + if (entry.byProperty !== undefined) { + const byObj = (obj[entry.byProperty] = obj[entry.byProperty] || {}); + for (const byValue of Object.keys(byObj)) { + const value = getFromByValues(entry.byValues, byValue); + if (value !== undefined) byObj[byValue][key] = value; + } + } } -} - -const create = (wasmModule, instancesPool, chunkSize, digestSize) => { - if (instancesPool.length > 0) { - const old = instancesPool.pop(); - old.reset(); - return old; - } else { - return new WasmHash( - new WebAssembly.Instance(wasmModule), - instancesPool, - chunkSize, - digestSize - ); + if (dynamicInfo !== undefined) { + obj[dynamicInfo.byProperty] = dynamicInfo.fn; } + return obj; }; -module.exports = create; -module.exports.MAX_SHORT_STRING = MAX_SHORT_STRING; - - -/***/ }), - -/***/ 37364: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ - - - -const create = __webpack_require__(21941); - -//#region wasm code: xxhash64 (../../../assembly/hash/xxhash64.asm.ts) --initialMemory 1 -const xxhash64 = new WebAssembly.Module( - Buffer.from( - // 1173 bytes - "AGFzbQEAAAABCAJgAX8AYAAAAwQDAQAABQMBAAEGGgV+AUIAC34BQgALfgFCAAt+AUIAC34BQgALByIEBGluaXQAAAZ1cGRhdGUAAQVmaW5hbAACBm1lbW9yeQIACrUIAzAAQtbrgu7q/Yn14AAkAELP1tO+0ser2UIkAUIAJAJC+erQ0OfJoeThACQDQgAkBAvUAQIBfwR+IABFBEAPCyMEIACtfCQEIwAhAiMBIQMjAiEEIwMhBQNAIAIgASkDAELP1tO+0ser2UJ+fEIfiUKHla+vmLbem55/fiECIAMgASkDCELP1tO+0ser2UJ+fEIfiUKHla+vmLbem55/fiEDIAQgASkDEELP1tO+0ser2UJ+fEIfiUKHla+vmLbem55/fiEEIAUgASkDGELP1tO+0ser2UJ+fEIfiUKHla+vmLbem55/fiEFIAAgAUEgaiIBSw0ACyACJAAgAyQBIAQkAiAFJAMLqwYCAX8EfiMEQgBSBH4jACICQgGJIwEiA0IHiXwjAiIEQgyJfCMDIgVCEol8IAJCz9bTvtLHq9lCfkIfiUKHla+vmLbem55/foVCh5Wvr5i23puef35CnaO16oOxjYr6AH0gA0LP1tO+0ser2UJ+Qh+JQoeVr6+Ytt6bnn9+hUKHla+vmLbem55/fkKdo7Xqg7GNivoAfSAEQs/W077Sx6vZQn5CH4lCh5Wvr5i23puef36FQoeVr6+Ytt6bnn9+Qp2jteqDsY2K+gB9IAVCz9bTvtLHq9lCfkIfiUKHla+vmLbem55/foVCh5Wvr5i23puef35CnaO16oOxjYr6AH0FQsXP2bLx5brqJwsjBCAArXx8IQIDQCABQQhqIABNBEAgAiABKQMAQs/W077Sx6vZQn5CH4lCh5Wvr5i23puef36FQhuJQoeVr6+Ytt6bnn9+Qp2jteqDsY2K+gB9IQIgAUEIaiEBDAELCyABQQRqIABNBEACfyACIAE1AgBCh5Wvr5i23puef36FQheJQs/W077Sx6vZQn5C+fPd8Zn2masWfCECIAFBBGoLIQELA0AgACABRwRAIAIgATEAAELFz9my8eW66id+hUILiUKHla+vmLbem55/fiECIAFBAWohAQwBCwtBACACIAJCIYiFQs/W077Sx6vZQn4iAkIdiCAChUL5893xmfaZqxZ+IgJCIIggAoUiAkIgiCIDQv//A4NCIIYgA0KAgPz/D4NCEIiEIgNC/4GAgPAfg0IQhiADQoD+g4CA4D+DQgiIhCIDQo+AvIDwgcAHg0IIhiADQvCBwIeAnoD4AINCBIiEIgNChoyYsODAgYMGfEIEiEKBgoSIkKDAgAGDQid+IANCsODAgYOGjJgwhHw3AwBBCCACQv////8PgyICQv//A4NCIIYgAkKAgPz/D4NCEIiEIgJC/4GAgPAfg0IQhiACQoD+g4CA4D+DQgiIhCICQo+AvIDwgcAHg0IIhiACQvCBwIeAnoD4AINCBIiEIgJChoyYsODAgYMGfEIEiEKBgoSIkKDAgAGDQid+IAJCsODAgYOGjJgwhHw3AwAL", - "base64" - ) -); -//#endregion - -module.exports = create.bind(null, xxhash64, [], 32, 16); - - -/***/ }), - -/***/ 96236: -/***/ (function(__unused_webpack_module, exports, __webpack_require__) { - -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php -*/ - - - -const path = __webpack_require__(85622); +const VALUE_TYPE_UNDEFINED = 0; +const VALUE_TYPE_ATOM = 1; +const VALUE_TYPE_ARRAY_EXTEND = 2; +const VALUE_TYPE_OBJECT = 3; +const VALUE_TYPE_DELETE = 4; -const WINDOWS_ABS_PATH_REGEXP = /^[a-zA-Z]:[\\/]/; -const SEGMENTS_SPLIT_REGEXP = /([|!])/; -const WINDOWS_PATH_SEPARATOR_REGEXP = /\\/g; +/** + * @param {any} value a single value + * @returns {VALUE_TYPE_UNDEFINED | VALUE_TYPE_ATOM | VALUE_TYPE_ARRAY_EXTEND | VALUE_TYPE_OBJECT | VALUE_TYPE_DELETE} value type + */ +const getValueType = value => { + if (value === undefined) { + return VALUE_TYPE_UNDEFINED; + } else if (value === DELETE) { + return VALUE_TYPE_DELETE; + } else if (Array.isArray(value)) { + if (value.lastIndexOf("...") !== -1) return VALUE_TYPE_ARRAY_EXTEND; + return VALUE_TYPE_ATOM; + } else if ( + typeof value === "object" && + value !== null && + (!value.constructor || value.constructor === Object) + ) { + return VALUE_TYPE_OBJECT; + } + return VALUE_TYPE_ATOM; +}; /** - * @typedef {Object} MakeRelativePathsCache - * @property {Map>=} relativePaths + * Merges two objects. Objects are deeply clever merged. + * Arrays might reference the old value with "...". + * Non-object values take preference over object values. + * @template T + * @template O + * @param {T} first first object + * @param {O} second second object + * @returns {T & O | T | O} merged object of first and second object */ +const cleverMerge = (first, second) => { + if (second === undefined) return first; + if (first === undefined) return second; + if (typeof second !== "object" || second === null) return second; + if (typeof first !== "object" || first === null) return first; -const relativePathToRequest = relativePath => { - if (relativePath === "") return "./."; - if (relativePath === "..") return "../."; - if (relativePath.startsWith("../")) return relativePath; - return `./${relativePath}`; + return _cleverMerge(first, second, false); }; /** - * @param {string} context context for relative path - * @param {string} maybeAbsolutePath path to make relative - * @returns {string} relative path in request style + * Merges two objects. Objects are deeply clever merged. + * @param {object} first first object + * @param {object} second second object + * @param {boolean} internalCaching should parsing of objects and nested merges be cached + * @returns {object} merged object of first and second object */ -const absoluteToRequest = (context, maybeAbsolutePath) => { - if (maybeAbsolutePath[0] === "/") { - if ( - maybeAbsolutePath.length > 1 && - maybeAbsolutePath[maybeAbsolutePath.length - 1] === "/" - ) { - // this 'path' is actually a regexp generated by dynamic requires. - // Don't treat it as an absolute path. - return maybeAbsolutePath; - } +const _cleverMerge = (first, second, internalCaching = false) => { + const firstObject = internalCaching + ? cachedParseObject(first) + : parseObject(first); + const { static: firstInfo, dynamic: firstDynamicInfo } = firstObject; - const querySplitPos = maybeAbsolutePath.indexOf("?"); - let resource = - querySplitPos === -1 - ? maybeAbsolutePath - : maybeAbsolutePath.slice(0, querySplitPos); - resource = relativePathToRequest(path.posix.relative(context, resource)); - return querySplitPos === -1 - ? resource - : resource + maybeAbsolutePath.slice(querySplitPos); + // If the first argument has a dynamic part we modify the dynamic part to merge the second argument + if (firstDynamicInfo !== undefined) { + let { byProperty, fn } = firstDynamicInfo; + const fnInfo = fn[DYNAMIC_INFO]; + if (fnInfo) { + second = internalCaching + ? cachedCleverMerge(fnInfo[1], second) + : cleverMerge(fnInfo[1], second); + fn = fnInfo[0]; + } + const newFn = (...args) => { + const fnResult = fn(...args); + return internalCaching + ? cachedCleverMerge(fnResult, second) + : cleverMerge(fnResult, second); + }; + newFn[DYNAMIC_INFO] = [fn, second]; + return serializeObject(firstObject.static, { byProperty, fn: newFn }); } - if (WINDOWS_ABS_PATH_REGEXP.test(maybeAbsolutePath)) { - const querySplitPos = maybeAbsolutePath.indexOf("?"); - let resource = - querySplitPos === -1 - ? maybeAbsolutePath - : maybeAbsolutePath.slice(0, querySplitPos); - resource = path.win32.relative(context, resource); - if (!WINDOWS_ABS_PATH_REGEXP.test(resource)) { - resource = relativePathToRequest( - resource.replace(WINDOWS_PATH_SEPARATOR_REGEXP, "/") - ); + // If the first part is static only, we merge the static parts and keep the dynamic part of the second argument + const secondObject = internalCaching + ? cachedParseObject(second) + : parseObject(second); + const { static: secondInfo, dynamic: secondDynamicInfo } = secondObject; + /** @type {Map} */ + const resultInfo = new Map(); + for (const [key, firstEntry] of firstInfo) { + const secondEntry = secondInfo.get(key); + const entry = + secondEntry !== undefined + ? mergeEntries(firstEntry, secondEntry, internalCaching) + : firstEntry; + resultInfo.set(key, entry); + } + for (const [key, secondEntry] of secondInfo) { + if (!firstInfo.has(key)) { + resultInfo.set(key, secondEntry); } - return querySplitPos === -1 - ? resource - : resource + maybeAbsolutePath.slice(querySplitPos); } - - // not an absolute path - return maybeAbsolutePath; + return serializeObject(resultInfo, secondDynamicInfo); }; /** - * @param {string} context context for relative path - * @param {string} relativePath path - * @returns {string} absolute path + * @param {ObjectParsedPropertyEntry} firstEntry a + * @param {ObjectParsedPropertyEntry} secondEntry b + * @param {boolean} internalCaching should parsing of objects and nested merges be cached + * @returns {ObjectParsedPropertyEntry} new entry */ -const requestToAbsolute = (context, relativePath) => { - if (relativePath.startsWith("./") || relativePath.startsWith("../")) - return path.join(context, relativePath); - return relativePath; +const mergeEntries = (firstEntry, secondEntry, internalCaching) => { + switch (getValueType(secondEntry.base)) { + case VALUE_TYPE_ATOM: + case VALUE_TYPE_DELETE: + // No need to consider firstEntry at all + // second value override everything + // = second.base + second.byProperty + return secondEntry; + case VALUE_TYPE_UNDEFINED: + if (!firstEntry.byProperty) { + // = first.base + second.byProperty + return { + base: firstEntry.base, + byProperty: secondEntry.byProperty, + byValues: secondEntry.byValues + }; + } else if (firstEntry.byProperty !== secondEntry.byProperty) { + throw new Error( + `${firstEntry.byProperty} and ${secondEntry.byProperty} for a single property is not supported` + ); + } else { + // = first.base + (first.byProperty + second.byProperty) + // need to merge first and second byValues + const newByValues = new Map(firstEntry.byValues); + for (const [key, value] of secondEntry.byValues) { + const firstValue = getFromByValues(firstEntry.byValues, key); + newByValues.set( + key, + mergeSingleValue(firstValue, value, internalCaching) + ); + } + return { + base: firstEntry.base, + byProperty: firstEntry.byProperty, + byValues: newByValues + }; + } + default: { + if (!firstEntry.byProperty) { + // The simple case + // = (first.base + second.base) + second.byProperty + return { + base: mergeSingleValue( + firstEntry.base, + secondEntry.base, + internalCaching + ), + byProperty: secondEntry.byProperty, + byValues: secondEntry.byValues + }; + } + let newBase; + const intermediateByValues = new Map(firstEntry.byValues); + for (const [key, value] of intermediateByValues) { + intermediateByValues.set( + key, + mergeSingleValue(value, secondEntry.base, internalCaching) + ); + } + if ( + Array.from(firstEntry.byValues.values()).every(value => { + const type = getValueType(value); + return type === VALUE_TYPE_ATOM || type === VALUE_TYPE_DELETE; + }) + ) { + // = (first.base + second.base) + ((first.byProperty + second.base) + second.byProperty) + newBase = mergeSingleValue( + firstEntry.base, + secondEntry.base, + internalCaching + ); + } else { + // = first.base + ((first.byProperty (+default) + second.base) + second.byProperty) + newBase = firstEntry.base; + if (!intermediateByValues.has("default")) + intermediateByValues.set("default", secondEntry.base); + } + if (!secondEntry.byProperty) { + // = first.base + (first.byProperty + second.base) + return { + base: newBase, + byProperty: firstEntry.byProperty, + byValues: intermediateByValues + }; + } else if (firstEntry.byProperty !== secondEntry.byProperty) { + throw new Error( + `${firstEntry.byProperty} and ${secondEntry.byProperty} for a single property is not supported` + ); + } + const newByValues = new Map(intermediateByValues); + for (const [key, value] of secondEntry.byValues) { + const firstValue = getFromByValues(intermediateByValues, key); + newByValues.set( + key, + mergeSingleValue(firstValue, value, internalCaching) + ); + } + return { + base: newBase, + byProperty: firstEntry.byProperty, + byValues: newByValues + }; + } + } }; -const makeCacheable = fn => { - /** @type {WeakMap>>} */ - const cache = new WeakMap(); - - /** - * @param {string} context context used to create relative path - * @param {string} identifier identifier used to create relative path - * @param {Object=} associatedObjectForCache an object to which the cache will be attached - * @returns {string} the returned relative path - */ - const cachedFn = (context, identifier, associatedObjectForCache) => { - if (!associatedObjectForCache) return fn(context, identifier); - - let innerCache = cache.get(associatedObjectForCache); - if (innerCache === undefined) { - innerCache = new Map(); - cache.set(associatedObjectForCache, innerCache); - } +/** + * @param {Map} byValues all values + * @param {string} key value of the selector + * @returns {any | undefined} value + */ +const getFromByValues = (byValues, key) => { + if (key !== "default" && byValues.has(key)) { + return byValues.get(key); + } + return byValues.get("default"); +}; - let cachedResult; - let innerSubCache = innerCache.get(context); - if (innerSubCache === undefined) { - innerCache.set(context, (innerSubCache = new Map())); - } else { - cachedResult = innerSubCache.get(identifier); +/** + * @param {any} a value + * @param {any} b value + * @param {boolean} internalCaching should parsing of objects and nested merges be cached + * @returns {any} value + */ +const mergeSingleValue = (a, b, internalCaching) => { + const bType = getValueType(b); + const aType = getValueType(a); + switch (bType) { + case VALUE_TYPE_DELETE: + case VALUE_TYPE_ATOM: + return b; + case VALUE_TYPE_OBJECT: { + return aType !== VALUE_TYPE_OBJECT + ? b + : internalCaching + ? cachedCleverMerge(a, b) + : cleverMerge(a, b); } + case VALUE_TYPE_UNDEFINED: + return a; + case VALUE_TYPE_ARRAY_EXTEND: + switch ( + aType !== VALUE_TYPE_ATOM + ? aType + : Array.isArray(a) + ? VALUE_TYPE_ARRAY_EXTEND + : VALUE_TYPE_OBJECT + ) { + case VALUE_TYPE_UNDEFINED: + return b; + case VALUE_TYPE_DELETE: + return b.filter(item => item !== "..."); + case VALUE_TYPE_ARRAY_EXTEND: { + const newArray = []; + for (const item of b) { + if (item === "...") { + for (const item of a) { + newArray.push(item); + } + } else { + newArray.push(item); + } + } + return newArray; + } + case VALUE_TYPE_OBJECT: + return b.map(item => (item === "..." ? a : item)); + default: + throw new Error("Not implemented"); + } + default: + throw new Error("Not implemented"); + } +}; - if (cachedResult !== undefined) { - return cachedResult; - } else { - const result = fn(context, identifier); - innerSubCache.set(identifier, result); - return result; +/** + * @template T + * @param {T} obj the object + * @returns {T} the object without operations like "..." or DELETE + */ +const removeOperations = obj => { + const newObj = /** @type {T} */ ({}); + for (const key of Object.keys(obj)) { + const value = obj[key]; + const type = getValueType(value); + switch (type) { + case VALUE_TYPE_UNDEFINED: + case VALUE_TYPE_DELETE: + break; + case VALUE_TYPE_OBJECT: + newObj[key] = removeOperations(value); + break; + case VALUE_TYPE_ARRAY_EXTEND: + newObj[key] = value.filter(i => i !== "..."); + break; + default: + newObj[key] = value; + break; } - }; + } + return newObj; +}; - /** - * @param {Object=} associatedObjectForCache an object to which the cache will be attached - * @returns {function(string, string): string} cached function - */ - cachedFn.bindCache = associatedObjectForCache => { - let innerCache; - if (associatedObjectForCache) { - innerCache = cache.get(associatedObjectForCache); - if (innerCache === undefined) { - innerCache = new Map(); - cache.set(associatedObjectForCache, innerCache); - } +/** + * @template T + * @template {string} P + * @param {T} obj the object + * @param {P} byProperty the by description + * @param {...any} values values + * @returns {Omit} object with merged byProperty + */ +const resolveByProperty = (obj, byProperty, ...values) => { + if (typeof obj !== "object" || obj === null || !(byProperty in obj)) { + return obj; + } + const { [byProperty]: _byValue, ..._remaining } = /** @type {object} */ (obj); + const remaining = /** @type {T} */ (_remaining); + const byValue = /** @type {Record | function(...any[]): T} */ ( + _byValue + ); + if (typeof byValue === "object") { + const key = values[0]; + if (key in byValue) { + return cachedCleverMerge(remaining, byValue[key]); + } else if ("default" in byValue) { + return cachedCleverMerge(remaining, byValue.default); } else { - innerCache = new Map(); + return /** @type {T} */ (remaining); } + } else if (typeof byValue === "function") { + const result = byValue.apply(null, values); + return cachedCleverMerge( + remaining, + resolveByProperty(result, byProperty, ...values) + ); + } +}; - /** - * @param {string} context context used to create relative path - * @param {string} identifier identifier used to create relative path - * @returns {string} the returned relative path - */ - const boundFn = (context, identifier) => { - let cachedResult; - let innerSubCache = innerCache.get(context); - if (innerSubCache === undefined) { - innerCache.set(context, (innerSubCache = new Map())); - } else { - cachedResult = innerSubCache.get(identifier); - } +exports.cachedSetProperty = cachedSetProperty; +exports.cachedCleverMerge = cachedCleverMerge; +exports.cleverMerge = cleverMerge; +exports.resolveByProperty = resolveByProperty; +exports.removeOperations = removeOperations; +exports.DELETE = DELETE; - if (cachedResult !== undefined) { - return cachedResult; - } else { - const result = fn(context, identifier); - innerSubCache.set(identifier, result); - return result; - } - }; - return boundFn; - }; +/***/ }), - /** - * @param {string} context context used to create relative path - * @param {Object=} associatedObjectForCache an object to which the cache will be attached - * @returns {function(string): string} cached function - */ - cachedFn.bindContextCache = (context, associatedObjectForCache) => { - let innerSubCache; - if (associatedObjectForCache) { - let innerCache = cache.get(associatedObjectForCache); - if (innerCache === undefined) { - innerCache = new Map(); - cache.set(associatedObjectForCache, innerCache); - } +/***/ 26296: +/***/ (function(__unused_webpack_module, exports, __webpack_require__) { - innerSubCache = innerCache.get(context); - if (innerSubCache === undefined) { - innerCache.set(context, (innerSubCache = new Map())); - } - } else { - innerSubCache = new Map(); - } +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ - /** - * @param {string} identifier identifier used to create relative path - * @returns {string} the returned relative path - */ - const boundFn = identifier => { - const cachedResult = innerSubCache.get(identifier); - if (cachedResult !== undefined) { - return cachedResult; - } else { - const result = fn(context, identifier); - innerSubCache.set(identifier, result); - return result; - } - }; - return boundFn; - }; - return cachedFn; -}; +const { compareRuntime } = __webpack_require__(19655); + +/** @typedef {import("../Chunk")} Chunk */ +/** @typedef {import("../ChunkGraph")} ChunkGraph */ +/** @typedef {import("../ChunkGroup")} ChunkGroup */ +/** @typedef {import("../Dependency").DependencyLocation} DependencyLocation */ +/** @typedef {import("../Module")} Module */ +/** @typedef {import("../ModuleGraph")} ModuleGraph */ + +/** @template T @typedef {function(T, T): -1|0|1} Comparator */ +/** @template TArg @template T @typedef {function(TArg, T, T): -1|0|1} RawParameterizedComparator */ +/** @template TArg @template T @typedef {function(TArg): Comparator} ParameterizedComparator */ /** - * - * @param {string} context context for relative path - * @param {string} identifier identifier for path - * @returns {string} a converted relative path + * @template T + * @param {RawParameterizedComparator} fn comparator with argument + * @returns {ParameterizedComparator} comparator */ -const _makePathsRelative = (context, identifier) => { - return identifier - .split(SEGMENTS_SPLIT_REGEXP) - .map(str => absoluteToRequest(context, str)) - .join(""); +const createCachedParameterizedComparator = fn => { + /** @type {WeakMap>} */ + const map = new WeakMap(); + return arg => { + const cachedResult = map.get(arg); + if (cachedResult !== undefined) return cachedResult; + /** + * @param {T} a first item + * @param {T} b second item + * @returns {-1|0|1} compare result + */ + const result = fn.bind(null, arg); + map.set(arg, result); + return result; + }; }; -exports.makePathsRelative = makeCacheable(_makePathsRelative); - /** - * - * @param {string} context context for relative path - * @param {string} identifier identifier for path - * @returns {string} a converted relative path + * @param {Chunk} a chunk + * @param {Chunk} b chunk + * @returns {-1|0|1} compare result */ -const _makePathsAbsolute = (context, identifier) => { - return identifier - .split(SEGMENTS_SPLIT_REGEXP) - .map(str => requestToAbsolute(context, str)) - .join(""); +exports.compareChunksById = (a, b) => { + return compareIds(a.id, b.id); }; -exports.makePathsAbsolute = makeCacheable(_makePathsAbsolute); - /** - * @param {string} context absolute context path - * @param {string} request any request string may containing absolute paths, query string, etc. - * @returns {string} a new request string avoiding absolute paths when possible + * @param {Module} a module + * @param {Module} b module + * @returns {-1|0|1} compare result */ -const _contextify = (context, request) => { - return request - .split("!") - .map(r => absoluteToRequest(context, r)) - .join("!"); +exports.compareModulesByIdentifier = (a, b) => { + return compareIds(a.identifier(), b.identifier()); }; -const contextify = makeCacheable(_contextify); -exports.contextify = contextify; - /** - * @param {string} context absolute context path - * @param {string} request any request string - * @returns {string} a new request string using absolute paths when possible + * @param {ChunkGraph} chunkGraph the chunk graph + * @param {Module} a module + * @param {Module} b module + * @returns {-1|0|1} compare result */ -const _absolutify = (context, request) => { - return request - .split("!") - .map(r => requestToAbsolute(context, r)) - .join("!"); +const compareModulesById = (chunkGraph, a, b) => { + return compareIds(chunkGraph.getModuleId(a), chunkGraph.getModuleId(b)); }; - -const absolutify = makeCacheable(_absolutify); -exports.absolutify = absolutify; - -const PATH_QUERY_FRAGMENT_REGEXP = - /^((?:\0.|[^?#\0])*)(\?(?:\0.|[^#\0])*)?(#.*)?$/; - -/** @typedef {{ resource: string, path: string, query: string, fragment: string }} ParsedResource */ +/** @type {ParameterizedComparator} */ +exports.compareModulesById = + createCachedParameterizedComparator(compareModulesById); /** - * @param {string} str the path with query and fragment - * @returns {ParsedResource} parsed parts + * @param {number} a number + * @param {number} b number + * @returns {-1|0|1} compare result */ -const _parseResource = str => { - const match = PATH_QUERY_FRAGMENT_REGEXP.exec(str); - return { - resource: str, - path: match[1].replace(/\0(.)/g, "$1"), - query: match[2] ? match[2].replace(/\0(.)/g, "$1") : "", - fragment: match[3] || "" - }; +const compareNumbers = (a, b) => { + if (typeof a !== typeof b) { + return typeof a < typeof b ? -1 : 1; + } + if (a < b) return -1; + if (a > b) return 1; + return 0; }; -exports.parseResource = (realFn => { - /** @type {WeakMap>} */ - const cache = new WeakMap(); - - const getCache = associatedObjectForCache => { - const entry = cache.get(associatedObjectForCache); - if (entry !== undefined) return entry; - /** @type {Map} */ - const map = new Map(); - cache.set(associatedObjectForCache, map); - return map; - }; - - /** - * @param {string} str the path with query and fragment - * @param {Object=} associatedObjectForCache an object to which the cache will be attached - * @returns {ParsedResource} parsed parts - */ - const fn = (str, associatedObjectForCache) => { - if (!associatedObjectForCache) return realFn(str); - const cache = getCache(associatedObjectForCache); - const entry = cache.get(str); - if (entry !== undefined) return entry; - const result = realFn(str); - cache.set(str, result); - return result; - }; - - fn.bindCache = associatedObjectForCache => { - const cache = getCache(associatedObjectForCache); - return str => { - const entry = cache.get(str); - if (entry !== undefined) return entry; - const result = realFn(str); - cache.set(str, result); - return result; - }; - }; - - return fn; -})(_parseResource); +exports.compareNumbers = compareNumbers; /** - * @param {string} filename the filename which should be undone - * @param {string} outputPath the output path that is restored (only relevant when filename contains "..") - * @param {boolean} enforceRelative true returns ./ for empty paths - * @returns {string} repeated ../ to leave the directory of the provided filename to be back on output dir + * @param {string} a string + * @param {string} b string + * @returns {-1|0|1} compare result */ -exports.getUndoPath = (filename, outputPath, enforceRelative) => { - let depth = -1; - let append = ""; - outputPath = outputPath.replace(/[\\/]$/, ""); - for (const part of filename.split(/[/\\]+/)) { - if (part === "..") { - if (depth > -1) { - depth--; +const compareStringsNumeric = (a, b) => { + const partsA = a.split(/(\d+)/); + const partsB = b.split(/(\d+)/); + const len = Math.min(partsA.length, partsB.length); + for (let i = 0; i < len; i++) { + const pA = partsA[i]; + const pB = partsB[i]; + if (i % 2 === 0) { + if (pA.length > pB.length) { + if (pA.slice(0, pB.length) > pB) return 1; + return -1; + } else if (pB.length > pA.length) { + if (pB.slice(0, pA.length) > pA) return -1; + return 1; } else { - const i = outputPath.lastIndexOf("/"); - const j = outputPath.lastIndexOf("\\"); - const pos = i < 0 ? j : j < 0 ? i : Math.max(i, j); - if (pos < 0) return outputPath + "/"; - append = outputPath.slice(pos + 1) + "/" + append; - outputPath = outputPath.slice(0, pos); + if (pA < pB) return -1; + if (pA > pB) return 1; } - } else if (part !== ".") { - depth++; + } else { + const nA = +pA; + const nB = +pB; + if (nA < nB) return -1; + if (nA > nB) return 1; } } - return depth > 0 - ? `${"../".repeat(depth)}${append}` - : enforceRelative - ? `./${append}` - : append; + if (partsB.length < partsA.length) return 1; + if (partsB.length > partsA.length) return -1; + return 0; }; +exports.compareStringsNumeric = compareStringsNumeric; +/** + * @param {ModuleGraph} moduleGraph the module graph + * @param {Module} a module + * @param {Module} b module + * @returns {-1|0|1} compare result + */ +const compareModulesByPostOrderIndexOrIdentifier = (moduleGraph, a, b) => { + const cmp = compareNumbers( + moduleGraph.getPostOrderIndex(a), + moduleGraph.getPostOrderIndex(b) + ); + if (cmp !== 0) return cmp; + return compareIds(a.identifier(), b.identifier()); +}; +/** @type {ParameterizedComparator} */ +exports.compareModulesByPostOrderIndexOrIdentifier = + createCachedParameterizedComparator( + compareModulesByPostOrderIndexOrIdentifier + ); -/***/ }), - -/***/ 7679: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ - - +/** + * @param {ModuleGraph} moduleGraph the module graph + * @param {Module} a module + * @param {Module} b module + * @returns {-1|0|1} compare result + */ +const compareModulesByPreOrderIndexOrIdentifier = (moduleGraph, a, b) => { + const cmp = compareNumbers( + moduleGraph.getPreOrderIndex(a), + moduleGraph.getPreOrderIndex(b) + ); + if (cmp !== 0) return cmp; + return compareIds(a.identifier(), b.identifier()); +}; +/** @type {ParameterizedComparator} */ +exports.compareModulesByPreOrderIndexOrIdentifier = + createCachedParameterizedComparator( + compareModulesByPreOrderIndexOrIdentifier + ); -// We need to include a list of requires here -// to allow webpack to be bundled with only static requires -// We could use a dynamic require(`../${request}`) but this -// would include too many modules and not every tool is able -// to process this -module.exports = { - AsyncDependenciesBlock: () => __webpack_require__(11315), - CommentCompilationWarning: () => __webpack_require__(28151), - ContextModule: () => __webpack_require__(80207), - "cache/PackFileCacheStrategy": () => - __webpack_require__(46810), - "cache/ResolverCachePlugin": () => __webpack_require__(11740), - "container/ContainerEntryDependency": () => - __webpack_require__(44055), - "container/ContainerEntryModule": () => - __webpack_require__(3234), - "container/ContainerExposedDependency": () => - __webpack_require__(50), - "container/FallbackDependency": () => - __webpack_require__(41061), - "container/FallbackItemDependency": () => - __webpack_require__(33393), - "container/FallbackModule": () => __webpack_require__(95193), - "container/RemoteModule": () => __webpack_require__(581), - "container/RemoteToExternalDependency": () => - __webpack_require__(44637), - "dependencies/AMDDefineDependency": () => - __webpack_require__(76309), - "dependencies/AMDRequireArrayDependency": () => - __webpack_require__(98233), - "dependencies/AMDRequireContextDependency": () => - __webpack_require__(60958), - "dependencies/AMDRequireDependenciesBlock": () => - __webpack_require__(69675), - "dependencies/AMDRequireDependency": () => - __webpack_require__(11311), - "dependencies/AMDRequireItemDependency": () => - __webpack_require__(90377), - "dependencies/CachedConstDependency": () => - __webpack_require__(64177), - "dependencies/CreateScriptUrlDependency": () => - __webpack_require__(29829), - "dependencies/CommonJsRequireContextDependency": () => - __webpack_require__(84175), - "dependencies/CommonJsExportRequireDependency": () => - __webpack_require__(76922), - "dependencies/CommonJsExportsDependency": () => - __webpack_require__(9585), - "dependencies/CommonJsFullRequireDependency": () => - __webpack_require__(29496), - "dependencies/CommonJsRequireDependency": () => - __webpack_require__(38604), - "dependencies/CommonJsSelfReferenceDependency": () => - __webpack_require__(69217), - "dependencies/ConstDependency": () => - __webpack_require__(60864), - "dependencies/ContextDependency": () => - __webpack_require__(67840), - "dependencies/ContextElementDependency": () => - __webpack_require__(83853), - "dependencies/CriticalDependencyWarning": () => - __webpack_require__(14190), - "dependencies/DelegatedSourceDependency": () => - __webpack_require__(82766), - "dependencies/DllEntryDependency": () => - __webpack_require__(57839), - "dependencies/EntryDependency": () => - __webpack_require__(41075), - "dependencies/ExportsInfoDependency": () => - __webpack_require__(30474), - "dependencies/HarmonyAcceptDependency": () => - __webpack_require__(38421), - "dependencies/HarmonyAcceptImportDependency": () => - __webpack_require__(35316), - "dependencies/HarmonyCompatibilityDependency": () => - __webpack_require__(56164), - "dependencies/HarmonyExportExpressionDependency": () => - __webpack_require__(22705), - "dependencies/HarmonyExportHeaderDependency": () => - __webpack_require__(67159), - "dependencies/HarmonyExportImportedSpecifierDependency": () => - __webpack_require__(77952), - "dependencies/HarmonyExportSpecifierDependency": () => - __webpack_require__(59042), - "dependencies/HarmonyImportSideEffectDependency": () => - __webpack_require__(76853), - "dependencies/HarmonyImportSpecifierDependency": () => - __webpack_require__(61994), - "dependencies/ImportContextDependency": () => - __webpack_require__(75785), - "dependencies/ImportDependency": () => - __webpack_require__(16727), - "dependencies/ImportEagerDependency": () => - __webpack_require__(91941), - "dependencies/ImportWeakDependency": () => - __webpack_require__(58426), - "dependencies/JsonExportsDependency": () => - __webpack_require__(36986), - "dependencies/LocalModule": () => __webpack_require__(930), - "dependencies/LocalModuleDependency": () => - __webpack_require__(67494), - "dependencies/ModuleDecoratorDependency": () => - __webpack_require__(58969), - "dependencies/ModuleHotAcceptDependency": () => - __webpack_require__(90200), - "dependencies/ModuleHotDeclineDependency": () => - __webpack_require__(72986), - "dependencies/ImportMetaHotAcceptDependency": () => - __webpack_require__(58287), - "dependencies/ImportMetaHotDeclineDependency": () => - __webpack_require__(89911), - "dependencies/ProvidedDependency": () => - __webpack_require__(88915), - "dependencies/PureExpressionDependency": () => - __webpack_require__(24746), - "dependencies/RequireContextDependency": () => - __webpack_require__(98854), - "dependencies/RequireEnsureDependenciesBlock": () => - __webpack_require__(91421), - "dependencies/RequireEnsureDependency": () => - __webpack_require__(975), - "dependencies/RequireEnsureItemDependency": () => - __webpack_require__(56867), - "dependencies/RequireHeaderDependency": () => - __webpack_require__(57010), - "dependencies/RequireIncludeDependency": () => - __webpack_require__(17046), - "dependencies/RequireIncludeDependencyParserPlugin": () => - __webpack_require__(29984), - "dependencies/RequireResolveContextDependency": () => - __webpack_require__(48789), - "dependencies/RequireResolveDependency": () => - __webpack_require__(93172), - "dependencies/RequireResolveHeaderDependency": () => - __webpack_require__(24128), - "dependencies/RuntimeRequirementsDependency": () => - __webpack_require__(75941), - "dependencies/StaticExportsDependency": () => - __webpack_require__(67967), - "dependencies/SystemPlugin": () => __webpack_require__(88768), - "dependencies/UnsupportedDependency": () => - __webpack_require__(41381), - "dependencies/URLDependency": () => __webpack_require__(30990), - "dependencies/WebAssemblyExportImportedDependency": () => - __webpack_require__(18248), - "dependencies/WebAssemblyImportDependency": () => - __webpack_require__(97093), - "dependencies/WebpackIsIncludedDependency": () => - __webpack_require__(41744), - "dependencies/WorkerDependency": () => - __webpack_require__(73016), - "json/JsonData": () => __webpack_require__(97637), - "optimize/ConcatenatedModule": () => - __webpack_require__(1881), - DelegatedModule: () => __webpack_require__(68719), - DependenciesBlock: () => __webpack_require__(21484), - DllModule: () => __webpack_require__(52692), - ExternalModule: () => __webpack_require__(89805), - FileSystemInfo: () => __webpack_require__(13679), - InitFragment: () => __webpack_require__(51739), - InvalidDependenciesModuleWarning: () => - __webpack_require__(2822), - Module: () => __webpack_require__(85887), - ModuleBuildError: () => __webpack_require__(37991), - ModuleDependencyWarning: () => __webpack_require__(61528), - ModuleError: () => __webpack_require__(11686), - ModuleGraph: () => __webpack_require__(20258), - ModuleParseError: () => __webpack_require__(13110), - ModuleWarning: () => __webpack_require__(92085), - NormalModule: () => __webpack_require__(11026), - RawModule: () => __webpack_require__(82329), - "sharing/ConsumeSharedModule": () => - __webpack_require__(61474), - "sharing/ConsumeSharedFallbackDependency": () => - __webpack_require__(90489), - "sharing/ProvideSharedModule": () => - __webpack_require__(65945), - "sharing/ProvideSharedDependency": () => - __webpack_require__(99355), - "sharing/ProvideForSharedDependency": () => - __webpack_require__(40235), - UnsupportedFeatureWarning: () => __webpack_require__(9532), - "util/LazySet": () => __webpack_require__(59534), - UnhandledSchemeError: () => __webpack_require__(63859), - NodeStuffInWebError: () => __webpack_require__(5771), - WebpackError: () => __webpack_require__(68422), +/** + * @param {ChunkGraph} chunkGraph the chunk graph + * @param {Module} a module + * @param {Module} b module + * @returns {-1|0|1} compare result + */ +const compareModulesByIdOrIdentifier = (chunkGraph, a, b) => { + const cmp = compareIds(chunkGraph.getModuleId(a), chunkGraph.getModuleId(b)); + if (cmp !== 0) return cmp; + return compareIds(a.identifier(), b.identifier()); +}; +/** @type {ParameterizedComparator} */ +exports.compareModulesByIdOrIdentifier = createCachedParameterizedComparator( + compareModulesByIdOrIdentifier +); - "util/registerExternalSerializer": () => { - // already registered - } +/** + * @param {ChunkGraph} chunkGraph the chunk graph + * @param {Chunk} a chunk + * @param {Chunk} b chunk + * @returns {-1|0|1} compare result + */ +const compareChunks = (chunkGraph, a, b) => { + return chunkGraph.compareChunks(a, b); }; +/** @type {ParameterizedComparator} */ +exports.compareChunks = createCachedParameterizedComparator(compareChunks); +/** + * @param {string|number} a first id + * @param {string|number} b second id + * @returns {-1|0|1} compare result + */ +const compareIds = (a, b) => { + if (typeof a !== typeof b) { + return typeof a < typeof b ? -1 : 1; + } + if (a < b) return -1; + if (a > b) return 1; + return 0; +}; -/***/ }), - -/***/ 26522: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { +exports.compareIds = compareIds; -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php -*/ +/** + * @param {string} a first string + * @param {string} b second string + * @returns {-1|0|1} compare result + */ +const compareStrings = (a, b) => { + if (a < b) return -1; + if (a > b) return 1; + return 0; +}; +exports.compareStrings = compareStrings; +/** + * @param {ChunkGroup} a first chunk group + * @param {ChunkGroup} b second chunk group + * @returns {-1|0|1} compare result + */ +const compareChunkGroupsByIndex = (a, b) => { + return a.index < b.index ? -1 : 1; +}; -const { register } = __webpack_require__(99551); +exports.compareChunkGroupsByIndex = compareChunkGroupsByIndex; -class ClassSerializer { - constructor(Constructor) { - this.Constructor = Constructor; +/** + * @template K1 {Object} + * @template K2 + * @template T + */ +class TwoKeyWeakMap { + constructor() { + /** @private @type {WeakMap>} */ + this._map = new WeakMap(); } - serialize(obj, context) { - obj.serialize(context); + /** + * @param {K1} key1 first key + * @param {K2} key2 second key + * @returns {T | undefined} value + */ + get(key1, key2) { + const childMap = this._map.get(key1); + if (childMap === undefined) { + return undefined; + } + return childMap.get(key2); } - deserialize(context) { - if (typeof this.Constructor.deserialize === "function") { - return this.Constructor.deserialize(context); + /** + * @param {K1} key1 first key + * @param {K2} key2 second key + * @param {T | undefined} value new value + * @returns {void} + */ + set(key1, key2, value) { + let childMap = this._map.get(key1); + if (childMap === undefined) { + childMap = new WeakMap(); + this._map.set(key1, childMap); } - const obj = new this.Constructor(); - obj.deserialize(context); - return obj; + childMap.set(key2, value); } } -module.exports = (Constructor, request, name = null) => { - register(Constructor, request, name, new ClassSerializer(Constructor)); -}; - - -/***/ }), +/** @type {TwoKeyWeakMap, Comparator, Comparator>}} */ +const concatComparatorsCache = new TwoKeyWeakMap(); -/***/ 84297: -/***/ (function(module) { +/** + * @template T + * @param {Comparator} c1 comparator + * @param {Comparator} c2 comparator + * @param {Comparator[]} cRest comparators + * @returns {Comparator} comparator + */ +const concatComparators = (c1, c2, ...cRest) => { + if (cRest.length > 0) { + const [c3, ...cRest2] = cRest; + return concatComparators(c1, concatComparators(c2, c3, ...cRest2)); + } + const cacheEntry = /** @type {Comparator} */ ( + concatComparatorsCache.get(c1, c2) + ); + if (cacheEntry !== undefined) return cacheEntry; + /** + * @param {T} a first value + * @param {T} b second value + * @returns {-1|0|1} compare result + */ + const result = (a, b) => { + const res = c1(a, b); + if (res !== 0) return res; + return c2(a, b); + }; + concatComparatorsCache.set(c1, c2, result); + return result; +}; +exports.concatComparators = concatComparators; -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php -*/ +/** @template A, B @typedef {(input: A) => B} Selector */ +/** @type {TwoKeyWeakMap, Comparator, Comparator>}} */ +const compareSelectCache = new TwoKeyWeakMap(); +/** + * @template T + * @template R + * @param {Selector} getter getter for value + * @param {Comparator} comparator comparator + * @returns {Comparator} comparator + */ +const compareSelect = (getter, comparator) => { + const cacheEntry = compareSelectCache.get(getter, comparator); + if (cacheEntry !== undefined) return cacheEntry; + /** + * @param {T} a first value + * @param {T} b second value + * @returns {-1|0|1} compare result + */ + const result = (a, b) => { + const aValue = getter(a); + const bValue = getter(b); + if (aValue !== undefined && aValue !== null) { + if (bValue !== undefined && bValue !== null) { + return comparator(aValue, bValue); + } + return -1; + } else { + if (bValue !== undefined && bValue !== null) { + return 1; + } + return 0; + } + }; + compareSelectCache.set(getter, comparator, result); + return result; +}; +exports.compareSelect = compareSelect; -/** @template T @typedef {function(): T} FunctionReturning */ +/** @type {WeakMap, Comparator>>} */ +const compareIteratorsCache = new WeakMap(); /** * @template T - * @param {FunctionReturning} fn memorized function - * @returns {FunctionReturning} new function + * @param {Comparator} elementComparator comparator for elements + * @returns {Comparator>} comparator for iterables of elements */ -const memoize = fn => { - let cache = false; - /** @type {T} */ - let result = undefined; - return () => { - if (cache) { - return result; - } else { - result = fn(); - cache = true; - // Allow to clean up memory for fn - // and all dependent resources - fn = undefined; - return result; +const compareIterables = elementComparator => { + const cacheEntry = compareIteratorsCache.get(elementComparator); + if (cacheEntry !== undefined) return cacheEntry; + /** + * @param {Iterable} a first value + * @param {Iterable} b second value + * @returns {-1|0|1} compare result + */ + const result = (a, b) => { + const aI = a[Symbol.iterator](); + const bI = b[Symbol.iterator](); + // eslint-disable-next-line no-constant-condition + while (true) { + const aItem = aI.next(); + const bItem = bI.next(); + if (aItem.done) { + return bItem.done ? 0 : -1; + } else if (bItem.done) { + return 1; + } + const res = elementComparator(aItem.value, bItem.value); + if (res !== 0) return res; } }; + compareIteratorsCache.set(elementComparator, result); + return result; }; +exports.compareIterables = compareIterables; -module.exports = memoize; +// TODO this is no longer needed when minimum node.js version is >= 12 +// since these versions ship with a stable sort function +/** + * @template T + * @param {Iterable} iterable original ordered list + * @returns {Comparator} comparator + */ +exports.keepOriginalOrder = iterable => { + /** @type {Map} */ + const map = new Map(); + let i = 0; + for (const item of iterable) { + map.set(item, i++); + } + return (a, b) => compareNumbers(map.get(a), map.get(b)); +}; + +/** + * @param {ChunkGraph} chunkGraph the chunk graph + * @returns {Comparator} comparator + */ +exports.compareChunksNatural = chunkGraph => { + const cmpFn = exports.compareModulesById(chunkGraph); + const cmpIterableFn = compareIterables(cmpFn); + return concatComparators( + compareSelect(chunk => chunk.name, compareIds), + compareSelect(chunk => chunk.runtime, compareRuntime), + compareSelect( + /** + * @param {Chunk} chunk a chunk + * @returns {Iterable} modules + */ + chunk => chunkGraph.getOrderedChunkModulesIterable(chunk, cmpFn), + cmpIterableFn + ) + ); +}; + +/** + * Compare two locations + * @param {DependencyLocation} a A location node + * @param {DependencyLocation} b A location node + * @returns {-1|0|1} sorting comparator value + */ +exports.compareLocations = (a, b) => { + let isObjectA = typeof a === "object" && a !== null; + let isObjectB = typeof b === "object" && b !== null; + if (!isObjectA || !isObjectB) { + if (isObjectA) return 1; + if (isObjectB) return -1; + return 0; + } + if ("start" in a) { + if ("start" in b) { + const ap = a.start; + const bp = b.start; + if (ap.line < bp.line) return -1; + if (ap.line > bp.line) return 1; + if (ap.column < bp.column) return -1; + if (ap.column > bp.column) return 1; + } else return -1; + } else if ("start" in b) return 1; + if ("name" in a) { + if ("name" in b) { + if (a.name < b.name) return -1; + if (a.name > b.name) return 1; + } else return -1; + } else if ("name" in b) return 1; + if ("index" in a) { + if ("index" in b) { + if (a.index < b.index) return -1; + if (a.index > b.index) return 1; + } else return -1; + } else if ("index" in b) return 1; + return 0; +}; /***/ }), -/***/ 91679: +/***/ 356: /***/ (function(module) { "use strict"; @@ -128602,120 +127687,211 @@ module.exports = memoize; -const SAFE_LIMIT = 0x80000000; -const SAFE_PART = SAFE_LIMIT - 1; -const COUNT = 4; -const arr = [0, 0, 0, 0, 0]; -const primes = [3, 7, 17, 19]; +const quoteMeta = str => { + return str.replace(/[-[\]\\/{}()*+?.^$|]/g, "\\$&"); +}; -module.exports = (str, range) => { - arr.fill(0); - for (let i = 0; i < str.length; i++) { - const c = str.charCodeAt(i); - for (let j = 0; j < COUNT; j++) { - const p = (j + COUNT - 1) % COUNT; - arr[j] = (arr[j] + c * primes[j] + arr[p]) & SAFE_PART; - } - for (let j = 0; j < COUNT; j++) { - const q = arr[j] % COUNT; - arr[j] = arr[j] ^ (arr[q] >> 1); - } +const toSimpleString = str => { + if (`${+str}` === str) { + return str; } - if (range <= SAFE_PART) { - let sum = 0; - for (let j = 0; j < COUNT; j++) { - sum = (sum + arr[j]) % range; - } - return sum; + return JSON.stringify(str); +}; + +/** + * @param {Record} map value map + * @returns {true|false|function(string): string} true/false, when unconditionally true/false, or a template function to determine the value at runtime + */ +const compileBooleanMatcher = map => { + const positiveItems = Object.keys(map).filter(i => map[i]); + const negativeItems = Object.keys(map).filter(i => !map[i]); + if (positiveItems.length === 0) return false; + if (negativeItems.length === 0) return true; + return compileBooleanMatcherFromLists(positiveItems, negativeItems); +}; + +/** + * @param {string[]} positiveItems positive items + * @param {string[]} negativeItems negative items + * @returns {function(string): string} a template function to determine the value at runtime + */ +const compileBooleanMatcherFromLists = (positiveItems, negativeItems) => { + if (positiveItems.length === 0) return () => "false"; + if (negativeItems.length === 0) return () => "true"; + if (positiveItems.length === 1) + return value => `${toSimpleString(positiveItems[0])} == ${value}`; + if (negativeItems.length === 1) + return value => `${toSimpleString(negativeItems[0])} != ${value}`; + const positiveRegexp = itemsToRegexp(positiveItems); + const negativeRegexp = itemsToRegexp(negativeItems); + if (positiveRegexp.length <= negativeRegexp.length) { + return value => `/^${positiveRegexp}$/.test(${value})`; } else { - let sum1 = 0; - let sum2 = 0; - const rangeExt = Math.floor(range / SAFE_LIMIT); - for (let j = 0; j < COUNT; j += 2) { - sum1 = (sum1 + arr[j]) & SAFE_PART; + return value => `!/^${negativeRegexp}$/.test(${value})`; + } +}; + +const popCommonItems = (itemsSet, getKey, condition) => { + const map = new Map(); + for (const item of itemsSet) { + const key = getKey(item); + if (key) { + let list = map.get(key); + if (list === undefined) { + list = []; + map.set(key, list); + } + list.push(item); } - for (let j = 1; j < COUNT; j += 2) { - sum2 = (sum2 + arr[j]) % rangeExt; + } + const result = []; + for (const list of map.values()) { + if (condition(list)) { + for (const item of list) { + itemsSet.delete(item); + } + result.push(list); } - return (sum2 * SAFE_LIMIT + sum1) % range; } + return result; }; +const getCommonPrefix = items => { + let prefix = items[0]; + for (let i = 1; i < items.length; i++) { + const item = items[i]; + for (let p = 0; p < prefix.length; p++) { + if (item[p] !== prefix[p]) { + prefix = prefix.slice(0, p); + break; + } + } + } + return prefix; +}; -/***/ }), - -/***/ 76815: -/***/ (function(module) { - -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ - - +const getCommonSuffix = items => { + let suffix = items[0]; + for (let i = 1; i < items.length; i++) { + const item = items[i]; + for (let p = item.length - 1, s = suffix.length - 1; s >= 0; p--, s--) { + if (item[p] !== suffix[s]) { + suffix = suffix.slice(s + 1); + break; + } + } + } + return suffix; +}; -/** - * @template T - * @template {Error} E - * @param {Iterable} items initial items - * @param {number} concurrency number of items running in parallel - * @param {function(T, function(T): void, function(E=): void): void} processor worker which pushes more items - * @param {function(E=): void} callback all items processed - * @returns {void} - */ -const processAsyncTree = (items, concurrency, processor, callback) => { - const queue = Array.from(items); - if (queue.length === 0) return callback(); - let processing = 0; - let finished = false; - let processScheduled = true; +const itemsToRegexp = itemsArr => { + if (itemsArr.length === 1) { + return quoteMeta(itemsArr[0]); + } + const finishedItems = []; - const push = item => { - queue.push(item); - if (!processScheduled && processing < concurrency) { - processScheduled = true; - process.nextTick(processQueue); + // merge single char items: (a|b|c|d|ef) => ([abcd]|ef) + let countOfSingleCharItems = 0; + for (const item of itemsArr) { + if (item.length === 1) { + countOfSingleCharItems++; } - }; + } + // special case for only single char items + if (countOfSingleCharItems === itemsArr.length) { + return `[${quoteMeta(itemsArr.sort().join(""))}]`; + } + const items = new Set(itemsArr.sort()); + if (countOfSingleCharItems > 2) { + let singleCharItems = ""; + for (const item of items) { + if (item.length === 1) { + singleCharItems += item; + items.delete(item); + } + } + finishedItems.push(`[${quoteMeta(singleCharItems)}]`); + } - const processorCallback = err => { - processing--; - if (err && !finished) { - finished = true; - callback(err); - return; + // special case for 2 items with common prefix/suffix + if (finishedItems.length === 0 && items.size === 2) { + const prefix = getCommonPrefix(itemsArr); + const suffix = getCommonSuffix( + itemsArr.map(item => item.slice(prefix.length)) + ); + if (prefix.length > 0 || suffix.length > 0) { + return `${quoteMeta(prefix)}${itemsToRegexp( + itemsArr.map(i => i.slice(prefix.length, -suffix.length || undefined)) + )}${quoteMeta(suffix)}`; } - if (!processScheduled) { - processScheduled = true; - process.nextTick(processQueue); + } + + // special case for 2 items with common suffix + if (finishedItems.length === 0 && items.size === 2) { + const it = items[Symbol.iterator](); + const a = it.next().value; + const b = it.next().value; + if (a.length > 0 && b.length > 0 && a.slice(-1) === b.slice(-1)) { + return `${itemsToRegexp([a.slice(0, -1), b.slice(0, -1)])}${quoteMeta( + a.slice(-1) + )}`; } - }; + } - const processQueue = () => { - if (finished) return; - while (processing < concurrency && queue.length > 0) { - processing++; - const item = queue.pop(); - processor(item, push, processorCallback); + // find common prefix: (a1|a2|a3|a4|b5) => (a(1|2|3|4)|b5) + const prefixed = popCommonItems( + items, + item => (item.length >= 1 ? item[0] : false), + list => { + if (list.length >= 3) return true; + if (list.length <= 1) return false; + return list[0][1] === list[1][1]; } - processScheduled = false; - if (queue.length === 0 && processing === 0 && !finished) { - finished = true; - callback(); + ); + for (const prefixedItems of prefixed) { + const prefix = getCommonPrefix(prefixedItems); + finishedItems.push( + `${quoteMeta(prefix)}${itemsToRegexp( + prefixedItems.map(i => i.slice(prefix.length)) + )}` + ); + } + + // find common suffix: (a1|b1|c1|d1|e2) => ((a|b|c|d)1|e2) + const suffixed = popCommonItems( + items, + item => (item.length >= 1 ? item.slice(-1) : false), + list => { + if (list.length >= 3) return true; + if (list.length <= 1) return false; + return list[0].slice(-2) === list[1].slice(-2); } - }; + ); + for (const suffixedItems of suffixed) { + const suffix = getCommonSuffix(suffixedItems); + finishedItems.push( + `${itemsToRegexp( + suffixedItems.map(i => i.slice(0, -suffix.length)) + )}${quoteMeta(suffix)}` + ); + } - processQueue(); + // TODO further optimize regexp, i. e. + // use ranges: (1|2|3|4|a) => [1-4a] + const conditional = finishedItems.concat(Array.from(items, quoteMeta)); + if (conditional.length === 1) return conditional[0]; + return `(${conditional.join("|")})`; }; -module.exports = processAsyncTree; +compileBooleanMatcher.fromLists = compileBooleanMatcherFromLists; +compileBooleanMatcher.itemsToRegexp = itemsToRegexp; +module.exports = compileBooleanMatcher; /***/ }), -/***/ 86709: -/***/ (function(module) { +/***/ 77695: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; /* @@ -128725,83 +127901,33 @@ module.exports = processAsyncTree; -const SAFE_IDENTIFIER = /^[_a-zA-Z$][_a-zA-Z$0-9]*$/; -const RESERVED_IDENTIFIER = new Set([ - "break", - "case", - "catch", - "class", - "const", - "continue", - "debugger", - "default", - "delete", - "do", - "else", - "export", - "extends", - "finally", - "for", - "function", - "if", - "import", - "in", - "instanceof", - "new", - "return", - "super", - "switch", - "this", - "throw", - "try", - "typeof", - "var", - "void", - "while", - "with", - "enum", - // strict mode - "implements", - "interface", - "let", - "package", - "private", - "protected", - "public", - "static", - "yield", - "yield", - // module code - "await", - // skip future reserved keywords defined under ES1 till ES3 - // additional - "null", - "true", - "false" -]); +const memoize = __webpack_require__(84297); -const propertyAccess = (properties, start = 0) => { - let str = ""; - for (let i = start; i < properties.length; i++) { - const p = properties[i]; - if (`${+p}` === p) { - str += `[${p}]`; - } else if (SAFE_IDENTIFIER.test(p) && !RESERVED_IDENTIFIER.has(p)) { - str += `.${p}`; - } else { - str += `[${JSON.stringify(p)}]`; +const getValidate = memoize(() => __webpack_require__(79286).validate); + +const createSchemaValidation = (check, getSchema, options) => { + getSchema = memoize(getSchema); + return value => { + if (check && !check(value)) { + getValidate()(getSchema(), value, options); + if (check) { + __webpack_require__(31669).deprecate( + () => {}, + "webpack bug: Pre-compiled schema reports error while real schema is happy. This has performance drawbacks.", + "DEP_WEBPACK_PRE_COMPILED_SCHEMA_INVALID" + )(); + } } - } - return str; + }; }; -module.exports = propertyAccess; +module.exports = createSchemaValidation; /***/ }), -/***/ 31107: -/***/ (function(__unused_webpack_module, __unused_webpack_exports, __webpack_require__) { +/***/ 24123: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; /* @@ -128811,1594 +127937,1224 @@ module.exports = propertyAccess; -const { register } = __webpack_require__(99551); - -const Position = /** @type {TODO} */ __webpack_require__(29089).Position; -const SourceLocation = __webpack_require__(29089).SourceLocation; -const ValidationError = __webpack_require__(40321)/* .default */ .Z; -const { - CachedSource, - ConcatSource, - OriginalSource, - PrefixSource, - RawSource, - ReplaceSource, - SourceMapSource -} = __webpack_require__(96192); - -/** @typedef {import("acorn").Position} Position */ -/** @typedef {import("../Dependency").RealDependencyLocation} RealDependencyLocation */ -/** @typedef {import("../Dependency").SourcePosition} SourcePosition */ -/** @typedef {import("./serialization").ObjectDeserializerContext} ObjectDeserializerContext */ -/** @typedef {import("./serialization").ObjectSerializerContext} ObjectSerializerContext */ - -/** @typedef {ObjectSerializerContext & { writeLazy?: (any) => void }} WebpackObjectSerializerContext */ - -const CURRENT_MODULE = "webpack/lib/util/registerExternalSerializer"; - -register( - CachedSource, - CURRENT_MODULE, - "webpack-sources/CachedSource", - new (class CachedSourceSerializer { - /** - * @param {CachedSource} source the cached source to be serialized - * @param {WebpackObjectSerializerContext} context context - * @returns {void} - */ - serialize(source, { write, writeLazy }) { - if (writeLazy) { - writeLazy(source.originalLazy()); - } else { - write(source.original()); - } - write(source.getCachedData()); - } - - /** - * @param {ObjectDeserializerContext} context context - * @returns {CachedSource} cached source - */ - deserialize({ read }) { - const source = read(); - const cachedData = read(); - return new CachedSource(source, cachedData); - } - })() -); - -register( - RawSource, - CURRENT_MODULE, - "webpack-sources/RawSource", - new (class RawSourceSerializer { - /** - * @param {RawSource} source the raw source to be serialized - * @param {WebpackObjectSerializerContext} context context - * @returns {void} - */ - serialize(source, { write }) { - write(source.buffer()); - write(!source.isBuffer()); - } - - /** - * @param {ObjectDeserializerContext} context context - * @returns {RawSource} raw source - */ - deserialize({ read }) { - const source = read(); - const convertToString = read(); - return new RawSource(source, convertToString); - } - })() -); - -register( - ConcatSource, - CURRENT_MODULE, - "webpack-sources/ConcatSource", - new (class ConcatSourceSerializer { - /** - * @param {ConcatSource} source the concat source to be serialized - * @param {WebpackObjectSerializerContext} context context - * @returns {void} - */ - serialize(source, { write }) { - write(source.getChildren()); - } - - /** - * @param {ObjectDeserializerContext} context context - * @returns {ConcatSource} concat source - */ - deserialize({ read }) { - const source = new ConcatSource(); - source.addAllSkipOptimizing(read()); - return source; - } - })() -); +const Hash = __webpack_require__(21301); -register( - PrefixSource, - CURRENT_MODULE, - "webpack-sources/PrefixSource", - new (class PrefixSourceSerializer { - /** - * @param {PrefixSource} source the prefix source to be serialized - * @param {WebpackObjectSerializerContext} context context - * @returns {void} - */ - serialize(source, { write }) { - write(source.getPrefix()); - write(source.original()); - } +const BULK_SIZE = 2000; - /** - * @param {ObjectDeserializerContext} context context - * @returns {PrefixSource} prefix source - */ - deserialize({ read }) { - return new PrefixSource(read(), read()); - } - })() -); +// We are using an object instead of a Map as this will stay static during the runtime +// so access to it can be optimized by v8 +const digestCaches = {}; -register( - ReplaceSource, - CURRENT_MODULE, - "webpack-sources/ReplaceSource", - new (class ReplaceSourceSerializer { - /** - * @param {ReplaceSource} source the replace source to be serialized - * @param {WebpackObjectSerializerContext} context context - * @returns {void} - */ - serialize(source, { write }) { - write(source.original()); - write(source.getName()); - const replacements = source.getReplacements(); - write(replacements.length); - for (const repl of replacements) { - write(repl.start); - write(repl.end); - } - for (const repl of replacements) { - write(repl.content); - write(repl.name); - } +class BulkUpdateDecorator extends Hash { + /** + * @param {Hash | function(): Hash} hashOrFactory function to create a hash + * @param {string=} hashKey key for caching + */ + constructor(hashOrFactory, hashKey) { + super(); + this.hashKey = hashKey; + if (typeof hashOrFactory === "function") { + this.hashFactory = hashOrFactory; + this.hash = undefined; + } else { + this.hashFactory = undefined; + this.hash = hashOrFactory; } + this.buffer = ""; + } - /** - * @param {ObjectDeserializerContext} context context - * @returns {ReplaceSource} replace source - */ - deserialize({ read }) { - const source = new ReplaceSource(read(), read()); - const len = read(); - const startEndBuffer = []; - for (let i = 0; i < len; i++) { - startEndBuffer.push(read(), read()); + /** + * Update hash {@link https://nodejs.org/api/crypto.html#crypto_hash_update_data_inputencoding} + * @param {string|Buffer} data data + * @param {string=} inputEncoding data encoding + * @returns {this} updated hash + */ + update(data, inputEncoding) { + if ( + inputEncoding !== undefined || + typeof data !== "string" || + data.length > BULK_SIZE + ) { + if (this.hash === undefined) this.hash = this.hashFactory(); + if (this.buffer.length > 0) { + this.hash.update(this.buffer); + this.buffer = ""; } - let j = 0; - for (let i = 0; i < len; i++) { - source.replace( - startEndBuffer[j++], - startEndBuffer[j++], - read(), - read() - ); + this.hash.update(data, inputEncoding); + } else { + this.buffer += data; + if (this.buffer.length > BULK_SIZE) { + if (this.hash === undefined) this.hash = this.hashFactory(); + this.hash.update(this.buffer); + this.buffer = ""; } - return source; - } - })() -); - -register( - OriginalSource, - CURRENT_MODULE, - "webpack-sources/OriginalSource", - new (class OriginalSourceSerializer { - /** - * @param {OriginalSource} source the original source to be serialized - * @param {WebpackObjectSerializerContext} context context - * @returns {void} - */ - serialize(source, { write }) { - write(source.buffer()); - write(source.getName()); } + return this; + } - /** - * @param {ObjectDeserializerContext} context context - * @returns {OriginalSource} original source - */ - deserialize({ read }) { - const buffer = read(); - const name = read(); - return new OriginalSource(buffer, name); - } - })() -); - -register( - SourceLocation, - CURRENT_MODULE, - "acorn/SourceLocation", - new (class SourceLocationSerializer { - /** - * @param {SourceLocation} loc the location to be serialized - * @param {WebpackObjectSerializerContext} context context - * @returns {void} - */ - serialize(loc, { write }) { - write(loc.start.line); - write(loc.start.column); - write(loc.end.line); - write(loc.end.column); - } - - /** - * @param {ObjectDeserializerContext} context context - * @returns {RealDependencyLocation} location - */ - deserialize({ read }) { - return { - start: { - line: read(), - column: read() - }, - end: { - line: read(), - column: read() - } - }; - } - })() -); - -register( - Position, - CURRENT_MODULE, - "acorn/Position", - new (class PositionSerializer { - /** - * @param {Position} pos the position to be serialized - * @param {WebpackObjectSerializerContext} context context - * @returns {void} - */ - serialize(pos, { write }) { - write(pos.line); - write(pos.column); - } - - /** - * @param {ObjectDeserializerContext} context context - * @returns {SourcePosition} position - */ - deserialize({ read }) { - return { - line: read(), - column: read() - }; - } - })() -); - -register( - SourceMapSource, - CURRENT_MODULE, - "webpack-sources/SourceMapSource", - new (class SourceMapSourceSerializer { - /** - * @param {SourceMapSource} source the source map source to be serialized - * @param {WebpackObjectSerializerContext} context context - * @returns {void} - */ - serialize(source, { write }) { - write(source.getArgsAsBuffers()); - } - - /** - * @param {ObjectDeserializerContext} context context - * @returns {SourceMapSource} source source map source - */ - deserialize({ read }) { - // @ts-expect-error - return new SourceMapSource(...read()); - } - })() -); - -register( - ValidationError, - CURRENT_MODULE, - "schema-utils/ValidationError", - new (class ValidationErrorSerializer { - // TODO error should be ValidationError, but this fails the type checks - /** - * @param {TODO} error the source map source to be serialized - * @param {WebpackObjectSerializerContext} context context - * @returns {void} - */ - serialize(error, { write }) { - write(error.errors); - write(error.schema); - write({ - name: error.headerName, - baseDataPath: error.baseDataPath, - postFormatter: error.postFormatter - }); + /** + * Calculates the digest {@link https://nodejs.org/api/crypto.html#crypto_hash_digest_encoding} + * @param {string=} encoding encoding of the return value + * @returns {string|Buffer} digest + */ + digest(encoding) { + let digestCache; + const buffer = this.buffer; + if (this.hash === undefined) { + // short data for hash, we can use caching + const cacheKey = `${this.hashKey}-${encoding}`; + digestCache = digestCaches[cacheKey]; + if (digestCache === undefined) { + digestCache = digestCaches[cacheKey] = new Map(); + } + const cacheEntry = digestCache.get(buffer); + if (cacheEntry !== undefined) return cacheEntry; + this.hash = this.hashFactory(); } - - /** - * @param {ObjectDeserializerContext} context context - * @returns {TODO} error - */ - deserialize({ read }) { - return new ValidationError(read(), read(), read()); + if (buffer.length > 0) { + this.hash.update(buffer); } - })() -); - - -/***/ }), - -/***/ 19655: -/***/ (function(__unused_webpack_module, exports, __webpack_require__) { - -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ - + const digestResult = this.hash.digest(encoding); + const result = + typeof digestResult === "string" ? digestResult : digestResult.toString(); + if (digestCache !== undefined) { + digestCache.set(buffer, result); + } + return result; + } +} +/* istanbul ignore next */ +class DebugHash extends Hash { + constructor() { + super(); + this.string = ""; + } -const SortableSet = __webpack_require__(67563); + /** + * Update hash {@link https://nodejs.org/api/crypto.html#crypto_hash_update_data_inputencoding} + * @param {string|Buffer} data data + * @param {string=} inputEncoding data encoding + * @returns {this} updated hash + */ + update(data, inputEncoding) { + if (typeof data !== "string") data = data.toString("utf-8"); + if (data.startsWith("debug-digest-")) { + data = Buffer.from(data.slice("debug-digest-".length), "hex").toString(); + } + this.string += `[${data}](${new Error().stack.split("\n", 3)[2]})\n`; + return this; + } -/** @typedef {import("../Compilation")} Compilation */ -/** @typedef {import("../Entrypoint").EntryOptions} EntryOptions */ + /** + * Calculates the digest {@link https://nodejs.org/api/crypto.html#crypto_hash_digest_encoding} + * @param {string=} encoding encoding of the return value + * @returns {string|Buffer} digest + */ + digest(encoding) { + return "debug-digest-" + Buffer.from(this.string).toString("hex"); + } +} -/** @typedef {string | SortableSet | undefined} RuntimeSpec */ -/** @typedef {RuntimeSpec | boolean} RuntimeCondition */ +let crypto = undefined; +let createXXHash64 = undefined; +let createMd4 = undefined; +let BatchedHash = undefined; /** - * @param {Compilation} compilation the compilation - * @param {string} name name of the entry - * @param {EntryOptions=} options optionally already received entry options - * @returns {RuntimeSpec} runtime + * Creates a hash by name or function + * @param {string | typeof Hash} algorithm the algorithm name or a constructor creating a hash + * @returns {Hash} the hash */ -exports.getEntryRuntime = (compilation, name, options) => { - let dependOn; - let runtime; - if (options) { - ({ dependOn, runtime } = options); - } else { - const entry = compilation.entries.get(name); - if (!entry) return name; - ({ dependOn, runtime } = entry.options); +module.exports = algorithm => { + if (typeof algorithm === "function") { + return new BulkUpdateDecorator(() => new algorithm()); } - if (dependOn) { - /** @type {RuntimeSpec} */ - let result = undefined; - const queue = new Set(dependOn); - for (const name of queue) { - const dep = compilation.entries.get(name); - if (!dep) continue; - const { dependOn, runtime } = dep.options; - if (dependOn) { - for (const name of dependOn) { - queue.add(name); + switch (algorithm) { + // TODO add non-cryptographic algorithm here + case "debug": + return new DebugHash(); + case "xxhash64": + if (createXXHash64 === undefined) { + createXXHash64 = __webpack_require__(37364); + if (BatchedHash === undefined) { + BatchedHash = __webpack_require__(32928); } - } else { - result = mergeRuntimeOwned(result, runtime || name); } - } - return result || name; - } else { - return runtime || name; + return new BatchedHash(createXXHash64()); + case "md4": + if (createMd4 === undefined) { + createMd4 = __webpack_require__(20487); + if (BatchedHash === undefined) { + BatchedHash = __webpack_require__(32928); + } + } + return new BatchedHash(createMd4()); + case "native-md4": + if (crypto === undefined) crypto = __webpack_require__(76417); + return new BulkUpdateDecorator(() => crypto.createHash("md4"), "md4"); + default: + if (crypto === undefined) crypto = __webpack_require__(76417); + return new BulkUpdateDecorator( + () => crypto.createHash(algorithm), + algorithm + ); } }; -/** - * @param {RuntimeSpec} runtime runtime - * @param {function(string): void} fn functor - * @param {boolean} deterministicOrder enforce a deterministic order - * @returns {void} - */ -exports.forEachRuntime = (runtime, fn, deterministicOrder = false) => { - if (runtime === undefined) { - fn(undefined); - } else if (typeof runtime === "string") { - fn(runtime); - } else { - if (deterministicOrder) runtime.sort(); - for (const r of runtime) { - fn(r); - } - } -}; -const getRuntimesKey = set => { - set.sort(); - return Array.from(set).join("\n"); -}; +/***/ }), -/** - * @param {RuntimeSpec} runtime runtime(s) - * @returns {string} key of runtimes - */ -const getRuntimeKey = runtime => { - if (runtime === undefined) return "*"; - if (typeof runtime === "string") return runtime; - return runtime.getFromUnorderedCache(getRuntimesKey); -}; -exports.getRuntimeKey = getRuntimeKey; +/***/ 2594: +/***/ (function(__unused_webpack_module, exports, __webpack_require__) { -/** - * @param {string} key key of runtimes - * @returns {RuntimeSpec} runtime(s) - */ -const keyToRuntime = key => { - if (key === "*") return undefined; - const items = key.split("\n"); - if (items.length === 1) return items[0]; - return new SortableSet(items); -}; -exports.keyToRuntime = keyToRuntime; +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ -const getRuntimesString = set => { - set.sort(); - return Array.from(set).join("+"); -}; -/** - * @param {RuntimeSpec} runtime runtime(s) - * @returns {string} readable version - */ -const runtimeToString = runtime => { - if (runtime === undefined) return "*"; - if (typeof runtime === "string") return runtime; - return runtime.getFromUnorderedCache(getRuntimesString); -}; -exports.runtimeToString = runtimeToString; -/** - * @param {RuntimeCondition} runtimeCondition runtime condition - * @returns {string} readable version - */ -exports.runtimeConditionToString = runtimeCondition => { - if (runtimeCondition === true) return "true"; - if (runtimeCondition === false) return "false"; - return runtimeToString(runtimeCondition); -}; +const util = __webpack_require__(31669); -/** - * @param {RuntimeSpec} a first - * @param {RuntimeSpec} b second - * @returns {boolean} true, when they are equal - */ -const runtimeEqual = (a, b) => { - if (a === b) { - return true; - } else if ( - a === undefined || - b === undefined || - typeof a === "string" || - typeof b === "string" - ) { - return false; - } else if (a.size !== b.size) { - return false; - } else { - a.sort(); - b.sort(); - const aIt = a[Symbol.iterator](); - const bIt = b[Symbol.iterator](); - for (;;) { - const aV = aIt.next(); - if (aV.done) return true; - const bV = bIt.next(); - if (aV.value !== bV.value) return false; - } - } -}; -exports.runtimeEqual = runtimeEqual; +/** @type {Map} */ +const deprecationCache = new Map(); /** - * @param {RuntimeSpec} a first - * @param {RuntimeSpec} b second - * @returns {-1|0|1} compare + * @typedef {Object} FakeHookMarker + * @property {true} _fakeHook it's a fake hook */ -exports.compareRuntime = (a, b) => { - if (a === b) { - return 0; - } else if (a === undefined) { - return -1; - } else if (b === undefined) { - return 1; - } else { - const aKey = getRuntimeKey(a); - const bKey = getRuntimeKey(b); - if (aKey < bKey) return -1; - if (aKey > bKey) return 1; - return 0; - } -}; -/** - * @param {RuntimeSpec} a first - * @param {RuntimeSpec} b second - * @returns {RuntimeSpec} merged - */ -const mergeRuntime = (a, b) => { - if (a === undefined) { - return b; - } else if (b === undefined) { - return a; - } else if (a === b) { - return a; - } else if (typeof a === "string") { - if (typeof b === "string") { - const set = new SortableSet(); - set.add(a); - set.add(b); - return set; - } else if (b.has(a)) { - return b; - } else { - const set = new SortableSet(b); - set.add(a); - return set; - } - } else { - if (typeof b === "string") { - if (a.has(b)) return a; - const set = new SortableSet(a); - set.add(b); - return set; - } else { - const set = new SortableSet(a); - for (const item of b) set.add(item); - if (set.size === a.size) return a; - return set; - } - } -}; -exports.mergeRuntime = mergeRuntime; +/** @template T @typedef {T & FakeHookMarker} FakeHook */ /** - * @param {RuntimeCondition} a first - * @param {RuntimeCondition} b second - * @param {RuntimeSpec} runtime full runtime - * @returns {RuntimeCondition} result + * @param {string} message deprecation message + * @param {string} code deprecation code + * @returns {Function} function to trigger deprecation */ -exports.mergeRuntimeCondition = (a, b, runtime) => { - if (a === false) return b; - if (b === false) return a; - if (a === true || b === true) return true; - const merged = mergeRuntime(a, b); - if (merged === undefined) return undefined; - if (typeof merged === "string") { - if (typeof runtime === "string" && merged === runtime) return true; - return merged; - } - if (typeof runtime === "string" || runtime === undefined) return merged; - if (merged.size === runtime.size) return true; - return merged; +const createDeprecation = (message, code) => { + const cached = deprecationCache.get(message); + if (cached !== undefined) return cached; + const fn = util.deprecate( + () => {}, + message, + "DEP_WEBPACK_DEPRECATION_" + code + ); + deprecationCache.set(message, fn); + return fn; }; -/** - * @param {RuntimeSpec | true} a first - * @param {RuntimeSpec | true} b second - * @param {RuntimeSpec} runtime full runtime - * @returns {RuntimeSpec | true} result - */ -exports.mergeRuntimeConditionNonFalse = (a, b, runtime) => { - if (a === true || b === true) return true; - const merged = mergeRuntime(a, b); - if (merged === undefined) return undefined; - if (typeof merged === "string") { - if (typeof runtime === "string" && merged === runtime) return true; - return merged; - } - if (typeof runtime === "string" || runtime === undefined) return merged; - if (merged.size === runtime.size) return true; - return merged; -}; +const COPY_METHODS = [ + "concat", + "entry", + "filter", + "find", + "findIndex", + "includes", + "indexOf", + "join", + "lastIndexOf", + "map", + "reduce", + "reduceRight", + "slice", + "some" +]; + +const DISABLED_METHODS = [ + "copyWithin", + "entries", + "fill", + "keys", + "pop", + "reverse", + "shift", + "splice", + "sort", + "unshift" +]; /** - * @param {RuntimeSpec} a first (may be modified) - * @param {RuntimeSpec} b second - * @returns {RuntimeSpec} merged + * @param {any} set new set + * @param {string} name property name + * @returns {void} */ -const mergeRuntimeOwned = (a, b) => { - if (b === undefined) { - return a; - } else if (a === b) { - return a; - } else if (a === undefined) { - if (typeof b === "string") { - return b; - } else { - return new SortableSet(b); - } - } else if (typeof a === "string") { - if (typeof b === "string") { - const set = new SortableSet(); - set.add(a); - set.add(b); - return set; - } else { - const set = new SortableSet(b); - set.add(a); - return set; +exports.arrayToSetDeprecation = (set, name) => { + for (const method of COPY_METHODS) { + if (set[method]) continue; + const d = createDeprecation( + `${name} was changed from Array to Set (using Array method '${method}' is deprecated)`, + "ARRAY_TO_SET" + ); + /** + * @deprecated + * @this {Set} + * @returns {number} count + */ + set[method] = function () { + d(); + const array = Array.from(this); + return Array.prototype[method].apply(array, arguments); + }; + } + const dPush = createDeprecation( + `${name} was changed from Array to Set (using Array method 'push' is deprecated)`, + "ARRAY_TO_SET_PUSH" + ); + const dLength = createDeprecation( + `${name} was changed from Array to Set (using Array property 'length' is deprecated)`, + "ARRAY_TO_SET_LENGTH" + ); + const dIndexer = createDeprecation( + `${name} was changed from Array to Set (indexing Array is deprecated)`, + "ARRAY_TO_SET_INDEXER" + ); + /** + * @deprecated + * @this {Set} + * @returns {number} count + */ + set.push = function () { + dPush(); + for (const item of Array.from(arguments)) { + this.add(item); } - } else { - if (typeof b === "string") { - a.add(b); - return a; - } else { - for (const item of b) a.add(item); - return a; + return this.size; + }; + for (const method of DISABLED_METHODS) { + if (set[method]) continue; + set[method] = () => { + throw new Error( + `${name} was changed from Array to Set (using Array method '${method}' is not possible)` + ); + }; + } + const createIndexGetter = index => { + /** + * @this {Set} a Set + * @returns {any} the value at this location + */ + const fn = function () { + dIndexer(); + let i = 0; + for (const item of this) { + if (i++ === index) return item; + } + return undefined; + }; + return fn; + }; + const defineIndexGetter = index => { + Object.defineProperty(set, index, { + get: createIndexGetter(index), + set(value) { + throw new Error( + `${name} was changed from Array to Set (indexing Array with write is not possible)` + ); + } + }); + }; + defineIndexGetter(0); + let indexerDefined = 1; + Object.defineProperty(set, "length", { + get() { + dLength(); + const length = this.size; + for (indexerDefined; indexerDefined < length + 1; indexerDefined++) { + defineIndexGetter(indexerDefined); + } + return length; + }, + set(value) { + throw new Error( + `${name} was changed from Array to Set (writing to Array property 'length' is not possible)` + ); } - } + }); + set[Symbol.isConcatSpreadable] = true; }; -exports.mergeRuntimeOwned = mergeRuntimeOwned; -/** - * @param {RuntimeSpec} a first - * @param {RuntimeSpec} b second - * @returns {RuntimeSpec} merged - */ -exports.intersectRuntime = (a, b) => { - if (a === undefined) { - return b; - } else if (b === undefined) { - return a; - } else if (a === b) { - return a; - } else if (typeof a === "string") { - if (typeof b === "string") { - return undefined; - } else if (b.has(a)) { - return a; - } else { - return undefined; - } - } else { - if (typeof b === "string") { - if (a.has(b)) return b; - return undefined; - } else { - const set = new SortableSet(); - for (const item of b) { - if (a.has(item)) set.add(item); +exports.createArrayToSetDeprecationSet = name => { + let initialized = false; + class SetDeprecatedArray extends Set { + constructor(items) { + super(items); + if (!initialized) { + initialized = true; + exports.arrayToSetDeprecation(SetDeprecatedArray.prototype, name); } - if (set.size === 0) return undefined; - if (set.size === 1) for (const item of set) return item; - return set; } } + return SetDeprecatedArray; +}; + +exports.soonFrozenObjectDeprecation = (obj, name, code, note = "") => { + const message = `${name} will be frozen in future, all modifications are deprecated.${ + note && `\n${note}` + }`; + return new Proxy(obj, { + set: util.deprecate( + (target, property, value, receiver) => + Reflect.set(target, property, value, receiver), + message, + code + ), + defineProperty: util.deprecate( + (target, property, descriptor) => + Reflect.defineProperty(target, property, descriptor), + message, + code + ), + deleteProperty: util.deprecate( + (target, property) => Reflect.deleteProperty(target, property), + message, + code + ), + setPrototypeOf: util.deprecate( + (target, proto) => Reflect.setPrototypeOf(target, proto), + message, + code + ) + }); }; /** - * @param {RuntimeSpec} a first - * @param {RuntimeSpec} b second - * @returns {RuntimeSpec} result + * @template T + * @param {T} obj object + * @param {string} message deprecation message + * @param {string} code deprecation code + * @returns {T} object with property access deprecated */ -const subtractRuntime = (a, b) => { - if (a === undefined) { - return undefined; - } else if (b === undefined) { - return a; - } else if (a === b) { - return undefined; - } else if (typeof a === "string") { - if (typeof b === "string") { - return a; - } else if (b.has(a)) { - return undefined; - } else { - return a; - } - } else { - if (typeof b === "string") { - if (!a.has(b)) return a; - if (a.size === 2) { - for (const item of a) { - if (item !== b) return item; - } - } - const set = new SortableSet(a); - set.delete(b); +const deprecateAllProperties = (obj, message, code) => { + const newObj = {}; + const descriptors = Object.getOwnPropertyDescriptors(obj); + for (const name of Object.keys(descriptors)) { + const descriptor = descriptors[name]; + if (typeof descriptor.value === "function") { + Object.defineProperty(newObj, name, { + ...descriptor, + value: util.deprecate(descriptor.value, message, code) + }); + } else if (descriptor.get || descriptor.set) { + Object.defineProperty(newObj, name, { + ...descriptor, + get: descriptor.get && util.deprecate(descriptor.get, message, code), + set: descriptor.set && util.deprecate(descriptor.set, message, code) + }); } else { - const set = new SortableSet(); - for (const item of a) { - if (!b.has(item)) set.add(item); - } - if (set.size === 0) return undefined; - if (set.size === 1) for (const item of set) return item; - return set; + let value = descriptor.value; + Object.defineProperty(newObj, name, { + configurable: descriptor.configurable, + enumerable: descriptor.enumerable, + get: util.deprecate(() => value, message, code), + set: descriptor.writable + ? util.deprecate(v => (value = v), message, code) + : undefined + }); } } + return /** @type {T} */ (newObj); }; -exports.subtractRuntime = subtractRuntime; +exports.deprecateAllProperties = deprecateAllProperties; /** - * @param {RuntimeCondition} a first - * @param {RuntimeCondition} b second - * @param {RuntimeSpec} runtime runtime - * @returns {RuntimeCondition} result + * @template T + * @param {T} fakeHook fake hook implementation + * @param {string=} message deprecation message (not deprecated when unset) + * @param {string=} code deprecation code (not deprecated when unset) + * @returns {FakeHook} fake hook which redirects */ -exports.subtractRuntimeCondition = (a, b, runtime) => { - if (b === true) return false; - if (b === false) return a; - if (a === false) return false; - const result = subtractRuntime(a === true ? runtime : a, b); - return result === undefined ? false : result; +exports.createFakeHook = (fakeHook, message, code) => { + if (message && code) { + fakeHook = deprecateAllProperties(fakeHook, message, code); + } + return Object.freeze( + Object.assign(fakeHook, { _fakeHook: /** @type {true} */ (true) }) + ); }; + +/***/ }), + +/***/ 37906: +/***/ (function(module) { + +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ + + + +// Simulations show these probabilities for a single change +// 93.1% that one group is invalidated +// 4.8% that two groups are invalidated +// 1.1% that 3 groups are invalidated +// 0.1% that 4 or more groups are invalidated +// +// And these for removing/adding 10 lexically adjacent files +// 64.5% that one group is invalidated +// 24.8% that two groups are invalidated +// 7.8% that 3 groups are invalidated +// 2.7% that 4 or more groups are invalidated +// +// And these for removing/adding 3 random files +// 0% that one group is invalidated +// 3.7% that two groups are invalidated +// 80.8% that 3 groups are invalidated +// 12.3% that 4 groups are invalidated +// 3.2% that 5 or more groups are invalidated + /** - * @param {RuntimeSpec} runtime runtime - * @param {function(RuntimeSpec): boolean} filter filter function - * @returns {boolean | RuntimeSpec} true/false if filter is constant for all runtimes, otherwise runtimes that are active + * + * @param {string} a key + * @param {string} b key + * @returns {number} the similarity as number */ -exports.filterRuntime = (runtime, filter) => { - if (runtime === undefined) return filter(undefined); - if (typeof runtime === "string") return filter(runtime); - let some = false; - let every = true; - let result = undefined; - for (const r of runtime) { - const v = filter(r); - if (v) { - some = true; - result = mergeRuntimeOwned(result, r); - } else { - every = false; - } +const similarity = (a, b) => { + const l = Math.min(a.length, b.length); + let dist = 0; + for (let i = 0; i < l; i++) { + const ca = a.charCodeAt(i); + const cb = b.charCodeAt(i); + dist += Math.max(0, 10 - Math.abs(ca - cb)); } - if (!some) return false; - if (every) return true; - return result; + return dist; }; /** - * @template T + * @param {string} a key + * @param {string} b key + * @param {Set} usedNames set of already used names + * @returns {string} the common part and a single char for the difference */ -class RuntimeSpecMap { - /** - * @param {RuntimeSpecMap=} clone copy form this - */ - constructor(clone) { - this._mode = clone ? clone._mode : 0; // 0 = empty, 1 = single entry, 2 = map - /** @type {RuntimeSpec} */ - this._singleRuntime = clone ? clone._singleRuntime : undefined; - /** @type {T} */ - this._singleValue = clone ? clone._singleValue : undefined; - /** @type {Map | undefined} */ - this._map = clone && clone._map ? new Map(clone._map) : undefined; - } - - /** - * @param {RuntimeSpec} runtime the runtimes - * @returns {T} value - */ - get(runtime) { - switch (this._mode) { - case 0: - return undefined; - case 1: - return runtimeEqual(this._singleRuntime, runtime) - ? this._singleValue - : undefined; - default: - return this._map.get(getRuntimeKey(runtime)); +const getName = (a, b, usedNames) => { + const l = Math.min(a.length, b.length); + let i = 0; + while (i < l) { + if (a.charCodeAt(i) !== b.charCodeAt(i)) { + i++; + break; } + i++; } - - /** - * @param {RuntimeSpec} runtime the runtimes - * @returns {boolean} true, when the runtime is stored - */ - has(runtime) { - switch (this._mode) { - case 0: - return false; - case 1: - return runtimeEqual(this._singleRuntime, runtime); - default: - return this._map.has(getRuntimeKey(runtime)); + while (i < l) { + const name = a.slice(0, i); + const lowerName = name.toLowerCase(); + if (!usedNames.has(lowerName)) { + usedNames.add(lowerName); + return name; } + i++; } + // names always contain a hash, so this is always unique + // we don't need to check usedNames nor add it + return a; +}; - set(runtime, value) { - switch (this._mode) { - case 0: - this._mode = 1; - this._singleRuntime = runtime; - this._singleValue = value; - break; - case 1: - if (runtimeEqual(this._singleRuntime, runtime)) { - this._singleValue = value; - break; - } - this._mode = 2; - this._map = new Map(); - this._map.set(getRuntimeKey(this._singleRuntime), this._singleValue); - this._singleRuntime = undefined; - this._singleValue = undefined; - /* falls through */ - default: - this._map.set(getRuntimeKey(runtime), value); - } +/** + * @param {Record} total total size + * @param {Record} size single size + * @returns {void} + */ +const addSizeTo = (total, size) => { + for (const key of Object.keys(size)) { + total[key] = (total[key] || 0) + size[key]; } +}; - provide(runtime, computer) { - switch (this._mode) { - case 0: - this._mode = 1; - this._singleRuntime = runtime; - return (this._singleValue = computer()); - case 1: { - if (runtimeEqual(this._singleRuntime, runtime)) { - return this._singleValue; - } - this._mode = 2; - this._map = new Map(); - this._map.set(getRuntimeKey(this._singleRuntime), this._singleValue); - this._singleRuntime = undefined; - this._singleValue = undefined; - const newValue = computer(); - this._map.set(getRuntimeKey(runtime), newValue); - return newValue; - } - default: { - const key = getRuntimeKey(runtime); - const value = this._map.get(key); - if (value !== undefined) return value; - const newValue = computer(); - this._map.set(key, newValue); - return newValue; - } - } +/** + * @param {Record} total total size + * @param {Record} size single size + * @returns {void} + */ +const subtractSizeFrom = (total, size) => { + for (const key of Object.keys(size)) { + total[key] -= size[key]; } +}; - delete(runtime) { - switch (this._mode) { - case 0: - return; - case 1: - if (runtimeEqual(this._singleRuntime, runtime)) { - this._mode = 0; - this._singleRuntime = undefined; - this._singleValue = undefined; - } - return; - default: - this._map.delete(getRuntimeKey(runtime)); - } +/** + * @param {Iterable} nodes some nodes + * @returns {Record} total size + */ +const sumSize = nodes => { + const sum = Object.create(null); + for (const node of nodes) { + addSizeTo(sum, node.size); } + return sum; +}; - update(runtime, fn) { - switch (this._mode) { - case 0: - throw new Error("runtime passed to update must exist"); - case 1: { - if (runtimeEqual(this._singleRuntime, runtime)) { - this._singleValue = fn(this._singleValue); - break; - } - const newValue = fn(undefined); - if (newValue !== undefined) { - this._mode = 2; - this._map = new Map(); - this._map.set(getRuntimeKey(this._singleRuntime), this._singleValue); - this._singleRuntime = undefined; - this._singleValue = undefined; - this._map.set(getRuntimeKey(runtime), newValue); - } - break; - } - default: { - const key = getRuntimeKey(runtime); - const oldValue = this._map.get(key); - const newValue = fn(oldValue); - if (newValue !== oldValue) this._map.set(key, newValue); - } +const isTooBig = (size, maxSize) => { + for (const key of Object.keys(size)) { + const s = size[key]; + if (s === 0) continue; + const maxSizeValue = maxSize[key]; + if (typeof maxSizeValue === "number") { + if (s > maxSizeValue) return true; } } + return false; +}; - keys() { - switch (this._mode) { - case 0: - return []; - case 1: - return [this._singleRuntime]; - default: - return Array.from(this._map.keys(), keyToRuntime); +const isTooSmall = (size, minSize) => { + for (const key of Object.keys(size)) { + const s = size[key]; + if (s === 0) continue; + const minSizeValue = minSize[key]; + if (typeof minSizeValue === "number") { + if (s < minSizeValue) return true; } } + return false; +}; - values() { - switch (this._mode) { - case 0: - return [][Symbol.iterator](); - case 1: - return [this._singleValue][Symbol.iterator](); - default: - return this._map.values(); +const getTooSmallTypes = (size, minSize) => { + const types = new Set(); + for (const key of Object.keys(size)) { + const s = size[key]; + if (s === 0) continue; + const minSizeValue = minSize[key]; + if (typeof minSizeValue === "number") { + if (s < minSizeValue) types.add(key); } } + return types; +}; - get size() { - if (this._mode <= 1) return this._mode; - return this._map.size; - } -} - -exports.RuntimeSpecMap = RuntimeSpecMap; - -class RuntimeSpecSet { - constructor(iterable) { - /** @type {Map} */ - this._map = new Map(); - if (iterable) { - for (const item of iterable) { - this.add(item); - } - } +const getNumberOfMatchingSizeTypes = (size, types) => { + let i = 0; + for (const key of Object.keys(size)) { + if (size[key] !== 0 && types.has(key)) i++; } + return i; +}; - add(runtime) { - this._map.set(getRuntimeKey(runtime), runtime); +const selectiveSizeSum = (size, types) => { + let sum = 0; + for (const key of Object.keys(size)) { + if (size[key] !== 0 && types.has(key)) sum += size[key]; } + return sum; +}; - has(runtime) { - return this._map.has(getRuntimeKey(runtime)); +/** + * @template T + */ +class Node { + /** + * @param {T} item item + * @param {string} key key + * @param {Record} size size + */ + constructor(item, key, size) { + this.item = item; + this.key = key; + this.size = size; } +} - [Symbol.iterator]() { - return this._map.values(); +/** + * @template T + */ +class Group { + /** + * @param {Node[]} nodes nodes + * @param {number[]} similarities similarities between the nodes (length = nodes.length - 1) + * @param {Record=} size size of the group + */ + constructor(nodes, similarities, size) { + this.nodes = nodes; + this.similarities = similarities; + this.size = size || sumSize(nodes); + /** @type {string} */ + this.key = undefined; } - get size() { - return this._map.size; + /** + * @param {function(Node): boolean} filter filter function + * @returns {Node[]} removed nodes + */ + popNodes(filter) { + const newNodes = []; + const newSimilarities = []; + const resultNodes = []; + let lastNode; + for (let i = 0; i < this.nodes.length; i++) { + const node = this.nodes[i]; + if (filter(node)) { + resultNodes.push(node); + } else { + if (newNodes.length > 0) { + newSimilarities.push( + lastNode === this.nodes[i - 1] + ? this.similarities[i - 1] + : similarity(lastNode.key, node.key) + ); + } + newNodes.push(node); + lastNode = node; + } + } + if (resultNodes.length === this.nodes.length) return undefined; + this.nodes = newNodes; + this.similarities = newSimilarities; + this.size = sumSize(newNodes); + return resultNodes; } } -exports.RuntimeSpecSet = RuntimeSpecSet; - - -/***/ }), - -/***/ 60473: -/***/ (function(__unused_webpack_module, exports) { - -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ - - - -/** @typedef {(string|number|undefined|[])[]} SemVerRange */ - /** - * @param {string} str version string - * @returns {(string|number|undefined|[])[]} parsed version + * @param {Iterable} nodes nodes + * @returns {number[]} similarities */ -const parseVersion = str => { - var splitAndConvert = function (str) { - return str.split(".").map(function (item) { - // eslint-disable-next-line eqeqeq - return +item == item ? +item : item; - }); - }; - var match = /^([^-+]+)?(?:-([^+]+))?(?:\+(.+))?$/.exec(str); - /** @type {(string|number|undefined|[])[]} */ - var ver = match[1] ? splitAndConvert(match[1]) : []; - if (match[2]) { - ver.length++; - ver.push.apply(ver, splitAndConvert(match[2])); - } - if (match[3]) { - ver.push([]); - ver.push.apply(ver, splitAndConvert(match[3])); +const getSimilarities = nodes => { + // calculate similarities between lexically adjacent nodes + /** @type {number[]} */ + const similarities = []; + let last = undefined; + for (const node of nodes) { + if (last !== undefined) { + similarities.push(similarity(last.key, node.key)); + } + last = node; } - return ver; + return similarities; }; -exports.parseVersion = parseVersion; -/* eslint-disable eqeqeq */ /** - * @param {string} a version - * @param {string} b version - * @returns {boolean} true, iff a < b + * @template T + * @typedef {Object} GroupedItems + * @property {string} key + * @property {T[]} items + * @property {Record} size */ -const versionLt = (a, b) => { - // @ts-expect-error - a = parseVersion(a); - // @ts-expect-error - b = parseVersion(b); - var i = 0; - for (;;) { - // a b EOA object undefined number string - // EOA a == b a < b b < a a < b a < b - // object b < a (0) b < a a < b a < b - // undefined a < b a < b (0) a < b a < b - // number b < a b < a b < a (1) a < b - // string b < a b < a b < a b < a (1) - // EOA end of array - // (0) continue on - // (1) compare them via "<" - // Handles first row in table - if (i >= a.length) return i < b.length && (typeof b[i])[0] != "u"; +/** + * @template T + * @typedef {Object} Options + * @property {Record} maxSize maximum size of a group + * @property {Record} minSize minimum size of a group (preferred over maximum size) + * @property {Iterable} items a list of items + * @property {function(T): Record} getSize function to get size of an item + * @property {function(T): string} getKey function to get the key of an item + */ - var aValue = a[i]; - var aType = (typeof aValue)[0]; +/** + * @template T + * @param {Options} options options object + * @returns {GroupedItems[]} grouped items + */ +module.exports = ({ maxSize, minSize, items, getSize, getKey }) => { + /** @type {Group[]} */ + const result = []; - // Handles first column in table - if (i >= b.length) return aType == "u"; + const nodes = Array.from( + items, + item => new Node(item, getKey(item), getSize(item)) + ); - var bValue = b[i]; - var bType = (typeof bValue)[0]; + /** @type {Node[]} */ + const initialNodes = []; - if (aType == bType) { - if (aType != "o" && aType != "u" && aValue != bValue) { - return aValue < bValue; - } - i++; + // lexically ordering of keys + nodes.sort((a, b) => { + if (a.key < b.key) return -1; + if (a.key > b.key) return 1; + return 0; + }); + + // return nodes bigger than maxSize directly as group + // But make sure that minSize is not violated + for (const node of nodes) { + if (isTooBig(node.size, maxSize) && !isTooSmall(node.size, minSize)) { + result.push(new Group([node], [])); } else { - // Handles remaining cases - if (aType == "o" && bType == "n") return true; - return bType == "s" || aType == "u"; + initialNodes.push(node); } } -}; -/* eslint-enable eqeqeq */ -exports.versionLt = versionLt; - -/** - * @param {string} str range string - * @returns {SemVerRange} parsed range - */ -exports.parseRange = str => { - const splitAndConvert = str => { - return str.split(".").map(item => (`${+item}` === item ? +item : item)); - }; - // see https://docs.npmjs.com/misc/semver#range-grammar for grammar - const parsePartial = str => { - const match = /^([^-+]+)?(?:-([^+]+))?(?:\+(.+))?$/.exec(str); - /** @type {(string|number|undefined|[])[]} */ - const ver = match[1] ? [0, ...splitAndConvert(match[1])] : [0]; - if (match[2]) { - ver.length++; - ver.push.apply(ver, splitAndConvert(match[2])); - } - // remove trailing any matchers - let last = ver[ver.length - 1]; - while ( - ver.length && - (last === undefined || /^[*xX]$/.test(/** @type {string} */ (last))) - ) { - ver.pop(); - last = ver[ver.length - 1]; - } + if (initialNodes.length > 0) { + const initialGroup = new Group(initialNodes, getSimilarities(initialNodes)); - return ver; - }; - const toFixed = range => { - if (range.length === 1) { - // Special case for "*" is "x.x.x" instead of "=" - return [0]; - } else if (range.length === 2) { - // Special case for "1" is "1.x.x" instead of "=1" - return [1, ...range.slice(1)]; - } else if (range.length === 3) { - // Special case for "1.2" is "1.2.x" instead of "=1.2" - return [2, ...range.slice(1)]; - } else { - return [range.length, ...range.slice(1)]; - } - }; - const negate = range => { - return [-range[0] - 1, ...range.slice(1)]; - }; - const parseSimple = str => { - // simple ::= primitive | partial | tilde | caret - // primitive ::= ( '<' | '>' | '>=' | '<=' | '=' ) partial - // tilde ::= '~' partial - // caret ::= '^' partial - const match = /^(\^|~|<=|<|>=|>|=|v|!)/.exec(str); - const start = match ? match[0] : ""; - const remainder = parsePartial(str.slice(start.length)); - switch (start) { - case "^": - if (remainder.length > 1 && remainder[1] === 0) { - if (remainder.length > 2 && remainder[2] === 0) { - return [3, ...remainder.slice(1)]; - } - return [2, ...remainder.slice(1)]; + const removeProblematicNodes = (group, consideredSize = group.size) => { + const problemTypes = getTooSmallTypes(consideredSize, minSize); + if (problemTypes.size > 0) { + // We hit an edge case where the working set is already smaller than minSize + // We merge problematic nodes with the smallest result node to keep minSize intact + const problemNodes = group.popNodes( + n => getNumberOfMatchingSizeTypes(n.size, problemTypes) > 0 + ); + if (problemNodes === undefined) return false; + // Only merge it with result nodes that have the problematic size type + const possibleResultGroups = result.filter( + n => getNumberOfMatchingSizeTypes(n.size, problemTypes) > 0 + ); + if (possibleResultGroups.length > 0) { + const bestGroup = possibleResultGroups.reduce((min, group) => { + const minMatches = getNumberOfMatchingSizeTypes(min, problemTypes); + const groupMatches = getNumberOfMatchingSizeTypes( + group, + problemTypes + ); + if (minMatches !== groupMatches) + return minMatches < groupMatches ? group : min; + if ( + selectiveSizeSum(min.size, problemTypes) > + selectiveSizeSum(group.size, problemTypes) + ) + return group; + return min; + }); + for (const node of problemNodes) bestGroup.nodes.push(node); + bestGroup.nodes.sort((a, b) => { + if (a.key < b.key) return -1; + if (a.key > b.key) return 1; + return 0; + }); + } else { + // There are no other nodes with the same size types + // We create a new group and have to accept that it's smaller than minSize + result.push(new Group(problemNodes, null)); } - return [1, ...remainder.slice(1)]; - case "~": - return [2, ...remainder.slice(1)]; - case ">=": - return remainder; - case "=": - case "v": - case "": - return toFixed(remainder); - case "<": - return negate(remainder); - case ">": { - // and( >=, not( = ) ) => >=, =, not, and - const fixed = toFixed(remainder); - // eslint-disable-next-line no-sparse-arrays - return [, fixed, 0, remainder, 2]; - } - case "<=": - // or( <, = ) => <, =, or - // eslint-disable-next-line no-sparse-arrays - return [, toFixed(remainder), negate(remainder), 1]; - case "!": { - // not = - const fixed = toFixed(remainder); - // eslint-disable-next-line no-sparse-arrays - return [, fixed, 0]; - } - default: - throw new Error("Unexpected start value"); - } - }; - const combine = (items, fn) => { - if (items.length === 1) return items[0]; - const arr = []; - for (const item of items.slice().reverse()) { - if (0 in item) { - arr.push(item); + return true; } else { - arr.push(...item.slice(1)); + return false; } - } - // eslint-disable-next-line no-sparse-arrays - return [, ...arr, ...items.slice(1).map(() => fn)]; - }; - const parseRange = str => { - // range ::= hyphen | simple ( ' ' simple ) * | '' - // hyphen ::= partial ' - ' partial - const items = str.split(" - "); - if (items.length === 1) { - const items = str.trim().split(/\s+/g).map(parseSimple); - return combine(items, 2); - } - const a = parsePartial(items[0]); - const b = parsePartial(items[1]); - // >=a <=b => and( >=a, or( >=a, { - // range-set ::= range ( logical-or range ) * - // logical-or ::= ( ' ' ) * '||' ( ' ' ) * - const items = str.split(/\s*\|\|\s*/).map(parseRange); - return combine(items, 1); - }; - return parseLogicalOr(str); -}; - -/* eslint-disable eqeqeq */ -const rangeToString = range => { - var fixCount = range[0]; - var str = ""; - if (range.length === 1) { - return "*"; - } else if (fixCount + 0.5) { - str += - fixCount == 0 - ? ">=" - : fixCount == -1 - ? "<" - : fixCount == 1 - ? "^" - : fixCount == 2 - ? "~" - : fixCount > 0 - ? "=" - : "!="; - var needDot = 1; - // eslint-disable-next-line no-redeclare - for (var i = 1; i < range.length; i++) { - var item = range[i]; - var t = (typeof item)[0]; - needDot--; - str += - t == "u" - ? // undefined: prerelease marker, add an "-" - "-" - : // number or string: add the item, set flag to add an "." between two of them - (needDot > 0 ? "." : "") + ((needDot = 2), item); - } - return str; - } else { - var stack = []; - // eslint-disable-next-line no-redeclare - for (var i = 1; i < range.length; i++) { - // eslint-disable-next-line no-redeclare - var item = range[i]; - stack.push( - item === 0 - ? "not(" + pop() + ")" - : item === 1 - ? "(" + pop() + " || " + pop() + ")" - : item === 2 - ? stack.pop() + " " + stack.pop() - : rangeToString(item) - ); - } - return pop(); - } - function pop() { - return stack.pop().replace(/^\((.+)\)$/, "$1"); - } -}; -/* eslint-enable eqeqeq */ -exports.rangeToString = rangeToString; - -/* eslint-disable eqeqeq */ -/** - * @param {SemVerRange} range version range - * @param {string} version the version - * @returns {boolean} if version satisfy the range - */ -const satisfy = (range, version) => { - if (0 in range) { - // @ts-expect-error - version = parseVersion(version); - var fixCount = range[0]; - // when negated is set it swill set for < instead of >= - var negated = fixCount < 0; - if (negated) fixCount = -fixCount - 1; - for (var i = 0, j = 1, isEqual = true; ; j++, i++) { - // cspell:word nequal nequ - - // when isEqual = true: - // range version: EOA/object undefined number string - // EOA equal block big-ver big-ver - // undefined bigger next big-ver big-ver - // number smaller block cmp big-cmp - // fixed number smaller block cmp-fix differ - // string smaller block differ cmp - // fixed string smaller block small-cmp cmp-fix - - // when isEqual = false: - // range version: EOA/object undefined number string - // EOA nequal block next-ver next-ver - // undefined nequal block next-ver next-ver - // number nequal block next next - // fixed number nequal block next next (this never happens) - // string nequal block next next - // fixed string nequal block next next (this never happens) + }; - // EOA end of array - // equal (version is equal range): - // when !negated: return true, - // when negated: return false - // bigger (version is bigger as range): - // when fixed: return false, - // when !negated: return true, - // when negated: return false, - // smaller (version is smaller as range): - // when !negated: return false, - // when negated: return true - // nequal (version is not equal range (> resp <)): return true - // block (version is in different prerelease area): return false - // differ (version is different from fixed range (string vs. number)): return false - // next: continues to the next items - // next-ver: when fixed: return false, continues to the next item only for the version, sets isEqual=false - // big-ver: when fixed || negated: return false, continues to the next item only for the version, sets isEqual=false - // next-nequ: continues to the next items, sets isEqual=false - // cmp (negated === false): version < range => return false, version > range => next-nequ, else => next - // cmp (negated === true): version > range => return false, version < range => next-nequ, else => next - // cmp-fix: version == range => next, else => return false - // big-cmp: when negated => return false, else => next-nequ - // small-cmp: when negated => next-nequ, else => return false + if (initialGroup.nodes.length > 0) { + const queue = [initialGroup]; - var rangeType = j < range.length ? (typeof range[j])[0] : ""; + while (queue.length) { + const group = queue.pop(); + // only groups bigger than maxSize need to be splitted + if (!isTooBig(group.size, maxSize)) { + result.push(group); + continue; + } + // If the group is already too small + // we try to work only with the unproblematic nodes + if (removeProblematicNodes(group)) { + // This changed something, so we try this group again + queue.push(group); + continue; + } - var versionValue; - var versionType; + // find unsplittable area from left and right + // going minSize from left and right + // at least one node need to be included otherwise we get stuck + let left = 1; + let leftSize = Object.create(null); + addSizeTo(leftSize, group.nodes[0].size); + while (left < group.nodes.length && isTooSmall(leftSize, minSize)) { + addSizeTo(leftSize, group.nodes[left].size); + left++; + } + let right = group.nodes.length - 2; + let rightSize = Object.create(null); + addSizeTo(rightSize, group.nodes[group.nodes.length - 1].size); + while (right >= 0 && isTooSmall(rightSize, minSize)) { + addSizeTo(rightSize, group.nodes[right].size); + right--; + } - // Handles first column in both tables (end of version or object) - if ( - i >= version.length || - ((versionValue = version[i]), - (versionType = (typeof versionValue)[0]) == "o") - ) { - // Handles nequal - if (!isEqual) return true; - // Handles bigger - if (rangeType == "u") return j > fixCount && !negated; - // Handles equal and smaller: (range === EOA) XOR negated - return (rangeType == "") != negated; // equal + smaller - } + // left v v right + // [ O O O ] O O O [ O O O ] + // ^^^^^^^^^ leftSize + // rightSize ^^^^^^^^^ + // leftSize > minSize + // rightSize > minSize - // Handles second column in both tables (version = undefined) - if (versionType == "u") { - if (!isEqual || rangeType != "u") { - return false; - } - } + // Perfect split: [ O O O ] [ O O O ] + // right === left - 1 - // switch between first and second table - else if (isEqual) { - // Handle diagonal - if (rangeType == versionType) { - if (j <= fixCount) { - // Handles "cmp-fix" cases - if (versionValue != range[j]) { - return false; - } + if (left - 1 > right) { + // We try to remove some problematic nodes to "fix" that + let prevSize; + if (right < group.nodes.length - left) { + subtractSizeFrom(rightSize, group.nodes[right + 1].size); + prevSize = rightSize; } else { - // Handles "cmp" cases - if (negated ? versionValue > range[j] : versionValue < range[j]) { - return false; - } - if (versionValue != range[j]) isEqual = false; + subtractSizeFrom(leftSize, group.nodes[left - 1].size); + prevSize = leftSize; } + if (removeProblematicNodes(group, prevSize)) { + // This changed something, so we try this group again + queue.push(group); + continue; + } + // can't split group while holding minSize + // because minSize is preferred of maxSize we return + // the problematic nodes as result here even while it's too big + // To avoid this make sure maxSize > minSize * 3 + result.push(group); + continue; } + if (left <= right) { + // when there is a area between left and right + // we look for best split point + // we split at the minimum similarity + // here key space is separated the most + // But we also need to make sure to not create too small groups + let best = -1; + let bestSimilarity = Infinity; + let pos = left; + let rightSize = sumSize(group.nodes.slice(pos)); - // Handle big-ver - else if (rangeType != "s" && rangeType != "n") { - if (negated || j <= fixCount) return false; - isEqual = false; - j--; - } + // pos v v right + // [ O O O ] O O O [ O O O ] + // ^^^^^^^^^ leftSize + // rightSize ^^^^^^^^^^^^^^^ - // Handle differ, big-cmp and small-cmp - else if (j <= fixCount || versionType < rangeType != negated) { - return false; - } else { - isEqual = false; + while (pos <= right + 1) { + const similarity = group.similarities[pos - 1]; + if ( + similarity < bestSimilarity && + !isTooSmall(leftSize, minSize) && + !isTooSmall(rightSize, minSize) + ) { + best = pos; + bestSimilarity = similarity; + } + addSizeTo(leftSize, group.nodes[pos].size); + subtractSizeFrom(rightSize, group.nodes[pos].size); + pos++; + } + if (best < 0) { + // This can't happen + // but if that assumption is wrong + // fallback to a big group + result.push(group); + continue; + } + left = best; + right = best - 1; } - } else { - // Handles all "next-ver" cases in the second table - if (rangeType != "s" && rangeType != "n") { - isEqual = false; - j--; + + // create two new groups for left and right area + // and queue them up + const rightNodes = [group.nodes[right + 1]]; + /** @type {number[]} */ + const rightSimilarities = []; + for (let i = right + 2; i < group.nodes.length; i++) { + rightSimilarities.push(group.similarities[i - 1]); + rightNodes.push(group.nodes[i]); } + queue.push(new Group(rightNodes, rightSimilarities)); - // next is applied by default + const leftNodes = [group.nodes[0]]; + /** @type {number[]} */ + const leftSimilarities = []; + for (let i = 1; i < left; i++) { + leftSimilarities.push(group.similarities[i - 1]); + leftNodes.push(group.nodes[i]); + } + queue.push(new Group(leftNodes, leftSimilarities)); } } } - /** @type {(boolean | number)[]} */ - var stack = []; - var p = stack.pop.bind(stack); - // eslint-disable-next-line no-redeclare - for (var i = 1; i < range.length; i++) { - var item = /** @type {SemVerRange | 0 | 1 | 2} */ (range[i]); - stack.push( - item == 1 - ? p() | p() - : item == 2 - ? p() & p() - : item - ? satisfy(item, version) - : !p() - ); - } - return !!p(); -}; -/* eslint-enable eqeqeq */ -exports.satisfy = satisfy; -exports.stringifyHoley = json => { - switch (typeof json) { - case "undefined": - return ""; - case "object": - if (Array.isArray(json)) { - let str = "["; - for (let i = 0; i < json.length; i++) { - if (i !== 0) str += ","; - str += this.stringifyHoley(json[i]); - } - str += "]"; - return str; - } else { - return JSON.stringify(json); - } - default: - return JSON.stringify(json); + // lexically ordering + result.sort((a, b) => { + if (a.nodes[0].key < b.nodes[0].key) return -1; + if (a.nodes[0].key > b.nodes[0].key) return 1; + return 0; + }); + + // give every group a name + const usedNames = new Set(); + for (let i = 0; i < result.length; i++) { + const group = result[i]; + if (group.nodes.length === 1) { + group.key = group.nodes[0].key; + } else { + const first = group.nodes[0]; + const last = group.nodes[group.nodes.length - 1]; + const name = getName(first.key, last.key, usedNames); + group.key = name; + } } + + // return the results + return result.map(group => { + /** @type {GroupedItems} */ + return { + key: group.key, + items: group.nodes.map(node => node.item), + size: group.size + }; + }); }; -//#region runtime code: parseVersion -exports.parseVersionRuntimeCode = runtimeTemplate => - `var parseVersion = ${runtimeTemplate.basicFunction("str", [ - "// see webpack/lib/util/semver.js for original code", - `var p=${ - runtimeTemplate.supportsArrowFunction() ? "p=>" : "function(p)" - }{return p.split(".").map((${ - runtimeTemplate.supportsArrowFunction() ? "p=>" : "function(p)" - }{return+p==p?+p:p}))},n=/^([^-+]+)?(?:-([^+]+))?(?:\\+(.+))?$/.exec(str),r=n[1]?p(n[1]):[];return n[2]&&(r.length++,r.push.apply(r,p(n[2]))),n[3]&&(r.push([]),r.push.apply(r,p(n[3]))),r;` - ])}`; -//#endregion -//#region runtime code: versionLt -exports.versionLtRuntimeCode = runtimeTemplate => - `var versionLt = ${runtimeTemplate.basicFunction("a, b", [ - "// see webpack/lib/util/semver.js for original code", - 'a=parseVersion(a),b=parseVersion(b);for(var r=0;;){if(r>=a.length)return r=b.length)return"u"==n;var t=b[r],f=(typeof t)[0];if(n!=f)return"o"==n&&"n"==f||("s"==f||"u"==n);if("o"!=n&&"u"!=n&&e!=t)return e - `var rangeToString = ${runtimeTemplate.basicFunction("range", [ - "// see webpack/lib/util/semver.js for original code", - 'var r=range[0],n="";if(1===range.length)return"*";if(r+.5){n+=0==r?">=":-1==r?"<":1==r?"^":2==r?"~":r>0?"=":"!=";for(var e=1,a=1;a0?".":"")+(e=2,t)}return n}var g=[];for(a=1;a - `var satisfy = ${runtimeTemplate.basicFunction("range, version", [ - "// see webpack/lib/util/semver.js for original code", - 'if(0 in range){version=parseVersion(version);var e=range[0],r=e<0;r&&(e=-e-1);for(var n=0,i=1,a=!0;;i++,n++){var f,s,g=i=version.length||"o"==(s=(typeof(f=version[n]))[0]))return!a||("u"==g?i>e&&!r:""==g!=r);if("u"==s){if(!a||"u"!=g)return!1}else if(a)if(g==s)if(i<=e){if(f!=range[i])return!1}else{if(r?f>range[i]:f>} */ + this.dependencies = new Set(); + this.marker = NO_MARKER; + /** @type {Cycle | undefined} */ + this.cycle = undefined; + this.incoming = 0; + } +} -const getBinaryMiddleware = memoize(() => - __webpack_require__(7732) -); -const getObjectMiddleware = memoize(() => - __webpack_require__(77815) -); -const getSingleItemMiddleware = memoize(() => - __webpack_require__(63340) -); -const getSerializer = memoize(() => __webpack_require__(24754)); -const getSerializerMiddleware = memoize(() => - __webpack_require__(37063) -); +/** + * @template T + */ +class Cycle { + constructor() { + /** @type {Set>} */ + this.nodes = new Set(); + } +} -const getBinaryMiddlewareInstance = memoize( - () => new (getBinaryMiddleware())() -); +/** + * @template T + * @typedef {Object} StackEntry + * @property {Node} node + * @property {Node[]} openEdges + */ -const registerSerializers = memoize(() => { - __webpack_require__(31107); +/** + * @template T + * @param {Iterable} items list of items + * @param {function(T): Iterable} getDependencies function to get dependencies of an item (items that are not in list are ignored) + * @returns {Iterable} graph roots of the items + */ +module.exports = (items, getDependencies) => { + /** @type {Map>} */ + const itemToNode = new Map(); + for (const item of items) { + const node = new Node(item); + itemToNode.set(item, node); + } - // Load internal paths with a relative require - // This allows bundling all internal serializers - const internalSerializables = __webpack_require__(7679); - getObjectMiddleware().registerLoader(/^webpack\/lib\//, req => { - const loader = internalSerializables[req.slice("webpack/lib/".length)]; - if (loader) { - loader(); - } else { - console.warn(`${req} not found in internalSerializables`); + // early exit when there is only a single item + if (itemToNode.size <= 1) return items; + + // grab all the dependencies + for (const node of itemToNode.values()) { + for (const dep of getDependencies(node.item)) { + const depNode = itemToNode.get(dep); + if (depNode !== undefined) { + node.dependencies.add(depNode); + } } - return true; - }); -}); + } -/** @type {Serializer} */ -let buffersSerializer; + // Set of current root modules + // items will be removed if a new reference to it has been found + /** @type {Set>} */ + const roots = new Set(); -// Expose serialization API -module.exports = { - get register() { - return getObjectMiddleware().register; - }, - get registerLoader() { - return getObjectMiddleware().registerLoader; - }, - get registerNotSerializable() { - return getObjectMiddleware().registerNotSerializable; - }, - get NOT_SERIALIZABLE() { - return getObjectMiddleware().NOT_SERIALIZABLE; - }, - /** @type {MEASURE_START_OPERATION} */ - get MEASURE_START_OPERATION() { - return getBinaryMiddleware().MEASURE_START_OPERATION; - }, - /** @type {MEASURE_END_OPERATION} */ - get MEASURE_END_OPERATION() { - return getBinaryMiddleware().MEASURE_END_OPERATION; - }, - get buffersSerializer() { - if (buffersSerializer !== undefined) return buffersSerializer; - registerSerializers(); - const Serializer = getSerializer(); - const binaryMiddleware = getBinaryMiddlewareInstance(); - const SerializerMiddleware = getSerializerMiddleware(); - const SingleItemMiddleware = getSingleItemMiddleware(); - return (buffersSerializer = new Serializer([ - new SingleItemMiddleware(), - new (getObjectMiddleware())(context => { - if (context.write) { - context.writeLazy = value => { - context.write( - SerializerMiddleware.createLazy(value, binaryMiddleware) - ); - }; + // Set of current cycles without references to it + // cycles will be removed if a new reference to it has been found + // that is not part of the cycle + /** @type {Set>} */ + const rootCycles = new Set(); + + // For all non-marked nodes + for (const selectedNode of itemToNode.values()) { + if (selectedNode.marker === NO_MARKER) { + // deep-walk all referenced modules + // in a non-recursive way + + // start by entering the selected node + selectedNode.marker = IN_PROGRESS_MARKER; + + // keep a stack to avoid recursive walk + /** @type {StackEntry[]} */ + const stack = [ + { + node: selectedNode, + openEdges: Array.from(selectedNode.dependencies) } - }, "md4"), - binaryMiddleware - ])); - }, - createFileSerializer: (fs, hashFunction) => { - registerSerializers(); - const Serializer = getSerializer(); - const FileMiddleware = __webpack_require__(40572); - const fileMiddleware = new FileMiddleware(fs, hashFunction); - const binaryMiddleware = getBinaryMiddlewareInstance(); - const SerializerMiddleware = getSerializerMiddleware(); - const SingleItemMiddleware = getSingleItemMiddleware(); - return new Serializer([ - new SingleItemMiddleware(), - new (getObjectMiddleware())(context => { - if (context.write) { - context.writeLazy = value => { - context.write( - SerializerMiddleware.createLazy(value, binaryMiddleware) - ); - }; - context.writeSeparate = (value, options) => { - const lazy = SerializerMiddleware.createLazy( - value, - fileMiddleware, - options - ); - context.write(lazy); - return lazy; - }; + ]; + + // process the top item until stack is empty + while (stack.length > 0) { + const topOfStack = stack[stack.length - 1]; + + // Are there still edges unprocessed in the current node? + if (topOfStack.openEdges.length > 0) { + // Process one dependency + const dependency = topOfStack.openEdges.pop(); + switch (dependency.marker) { + case NO_MARKER: + // dependency has not be visited yet + // mark it as in-progress and recurse + stack.push({ + node: dependency, + openEdges: Array.from(dependency.dependencies) + }); + dependency.marker = IN_PROGRESS_MARKER; + break; + case IN_PROGRESS_MARKER: { + // It's a in-progress cycle + let cycle = dependency.cycle; + if (!cycle) { + cycle = new Cycle(); + cycle.nodes.add(dependency); + dependency.cycle = cycle; + } + // set cycle property for each node in the cycle + // if nodes are already part of a cycle + // we merge the cycles to a shared cycle + for ( + let i = stack.length - 1; + stack[i].node !== dependency; + i-- + ) { + const node = stack[i].node; + if (node.cycle) { + if (node.cycle !== cycle) { + // merge cycles + for (const cycleNode of node.cycle.nodes) { + cycleNode.cycle = cycle; + cycle.nodes.add(cycleNode); + } + } + } else { + node.cycle = cycle; + cycle.nodes.add(node); + } + } + // don't recurse into dependencies + // these are already on the stack + break; + } + case DONE_AND_ROOT_MARKER: + // This node has be visited yet and is currently a root node + // But as this is a new reference to the node + // it's not really a root + // so we have to convert it to a normal node + dependency.marker = DONE_MARKER; + roots.delete(dependency); + break; + case DONE_MAYBE_ROOT_CYCLE_MARKER: + // This node has be visited yet and + // is maybe currently part of a completed root cycle + // we found a new reference to the cycle + // so it's not really a root cycle + // remove the cycle from the root cycles + // and convert it to a normal node + rootCycles.delete(dependency.cycle); + dependency.marker = DONE_MARKER; + break; + // DONE_MARKER: nothing to do, don't recurse into dependencies + } + } else { + // All dependencies of the current node has been visited + // we leave the node + stack.pop(); + topOfStack.node.marker = DONE_MARKER; + } + } + const cycle = selectedNode.cycle; + if (cycle) { + for (const node of cycle.nodes) { + node.marker = DONE_MAYBE_ROOT_CYCLE_MARKER; } - }, hashFunction), - binaryMiddleware, - fileMiddleware - ]); + rootCycles.add(cycle); + } else { + selectedNode.marker = DONE_AND_ROOT_MARKER; + roots.add(selectedNode); + } + } + } + + // Extract roots from root cycles + // We take the nodes with most incoming edges + // inside of the cycle + for (const cycle of rootCycles) { + let max = 0; + /** @type {Set>} */ + const cycleRoots = new Set(); + const nodes = cycle.nodes; + for (const node of nodes) { + for (const dep of node.dependencies) { + if (nodes.has(dep)) { + dep.incoming++; + if (dep.incoming < max) continue; + if (dep.incoming > max) { + cycleRoots.clear(); + max = dep.incoming; + } + cycleRoots.add(dep); + } + } + } + for (const cycleRoot of cycleRoots) { + roots.add(cycleRoot); + } + } + + // When roots were found, return them + if (roots.size > 0) { + return Array.from(roots, r => r.item); + } else { + throw new Error("Implementation of findGraphRoots is broken"); } }; /***/ }), -/***/ 84820: -/***/ (function(module) { +/***/ 93204: +/***/ (function(__unused_webpack_module, exports, __webpack_require__) { "use strict"; /* @@ -130408,211 +129164,332 @@ module.exports = { +const path = __webpack_require__(85622); + +/** @typedef {import("../../declarations/WebpackOptions").WatchOptions} WatchOptions */ +/** @typedef {import("../FileSystemInfo").FileSystemInfoEntry} FileSystemInfoEntry */ + /** - * @typedef {Object} GroupOptions - * @property {boolean=} groupChildren - * @property {boolean=} force - * @property {number=} targetGroupCount + * @typedef {Object} IStats + * @property {() => boolean} isFile + * @property {() => boolean} isDirectory + * @property {() => boolean} isBlockDevice + * @property {() => boolean} isCharacterDevice + * @property {() => boolean} isSymbolicLink + * @property {() => boolean} isFIFO + * @property {() => boolean} isSocket + * @property {number | bigint} dev + * @property {number | bigint} ino + * @property {number | bigint} mode + * @property {number | bigint} nlink + * @property {number | bigint} uid + * @property {number | bigint} gid + * @property {number | bigint} rdev + * @property {number | bigint} size + * @property {number | bigint} blksize + * @property {number | bigint} blocks + * @property {number | bigint} atimeMs + * @property {number | bigint} mtimeMs + * @property {number | bigint} ctimeMs + * @property {number | bigint} birthtimeMs + * @property {Date} atime + * @property {Date} mtime + * @property {Date} ctime + * @property {Date} birthtime */ /** - * @template T - * @template R - * @typedef {Object} GroupConfig - * @property {function(T): string[]} getKeys - * @property {function(string, (R | T)[], T[]): R} createGroup - * @property {function(string, T[]): GroupOptions=} getOptions + * @typedef {Object} IDirent + * @property {() => boolean} isFile + * @property {() => boolean} isDirectory + * @property {() => boolean} isBlockDevice + * @property {() => boolean} isCharacterDevice + * @property {() => boolean} isSymbolicLink + * @property {() => boolean} isFIFO + * @property {() => boolean} isSocket + * @property {string | Buffer} name */ +/** @typedef {function((NodeJS.ErrnoException | null)=): void} Callback */ +/** @typedef {function((NodeJS.ErrnoException | null)=, Buffer=): void} BufferCallback */ +/** @typedef {function((NodeJS.ErrnoException | null)=, Buffer|string=): void} BufferOrStringCallback */ +/** @typedef {function((NodeJS.ErrnoException | null)=, (string | Buffer)[] | IDirent[]=): void} DirentArrayCallback */ +/** @typedef {function((NodeJS.ErrnoException | null)=, string=): void} StringCallback */ +/** @typedef {function((NodeJS.ErrnoException | null)=, number=): void} NumberCallback */ +/** @typedef {function((NodeJS.ErrnoException | null)=, IStats=): void} StatsCallback */ +/** @typedef {function((NodeJS.ErrnoException | Error | null)=, any=): void} ReadJsonCallback */ +/** @typedef {function((NodeJS.ErrnoException | Error | null)=, IStats|string=): void} LstatReadlinkAbsoluteCallback */ + /** - * @template T - * @template R - * @typedef {Object} ItemWithGroups - * @property {T} item - * @property {Set>} groups + * @typedef {Object} Watcher + * @property {function(): void} close closes the watcher and all underlying file watchers + * @property {function(): void} pause closes the watcher, but keeps underlying file watchers alive until the next watch call + * @property {function(): Set=} getAggregatedChanges get current aggregated changes that have not yet send to callback + * @property {function(): Set=} getAggregatedRemovals get current aggregated removals that have not yet send to callback + * @property {function(): Map} getFileTimeInfoEntries get info about files + * @property {function(): Map} getContextTimeInfoEntries get info about directories */ /** - * @template T - * @template R - * @typedef {{ config: GroupConfig, name: string, alreadyGrouped: boolean, items: Set> | undefined }} Group + * @callback WatchMethod + * @param {Iterable} files watched files + * @param {Iterable} directories watched directories + * @param {Iterable} missing watched exitance entries + * @param {number} startTime timestamp of start time + * @param {WatchOptions} options options object + * @param {function(Error=, Map, Map, Set, Set): void} callback aggregated callback + * @param {function(string, number): void} callbackUndelayed callback when the first change was detected + * @returns {Watcher} a watcher */ +// TODO webpack 6 make optional methods required + /** - * @template T - * @template R - * @param {T[]} items the list of items - * @param {GroupConfig[]} groupConfigs configuration - * @returns {(R | T)[]} grouped items + * @typedef {Object} OutputFileSystem + * @property {function(string, Buffer|string, Callback): void} writeFile + * @property {function(string, Callback): void} mkdir + * @property {function(string, DirentArrayCallback): void=} readdir + * @property {function(string, Callback): void=} rmdir + * @property {function(string, Callback): void=} unlink + * @property {function(string, StatsCallback): void} stat + * @property {function(string, StatsCallback): void=} lstat + * @property {function(string, BufferOrStringCallback): void} readFile + * @property {(function(string, string): string)=} join + * @property {(function(string, string): string)=} relative + * @property {(function(string): string)=} dirname */ -const smartGrouping = (items, groupConfigs) => { - /** @type {Set>} */ - const itemsWithGroups = new Set(); - /** @type {Map>} */ - const allGroups = new Map(); - for (const item of items) { - /** @type {Set>} */ - const groups = new Set(); - for (let i = 0; i < groupConfigs.length; i++) { - const groupConfig = groupConfigs[i]; - const keys = groupConfig.getKeys(item); - if (keys) { - for (const name of keys) { - const key = `${i}:${name}`; - let group = allGroups.get(key); - if (group === undefined) { - allGroups.set( - key, - (group = { - config: groupConfig, - name, - alreadyGrouped: false, - items: undefined - }) - ); - } - groups.add(group); - } - } - } - itemsWithGroups.add({ - item, - groups - }); + +/** + * @typedef {Object} InputFileSystem + * @property {function(string, BufferOrStringCallback): void} readFile + * @property {(function(string, ReadJsonCallback): void)=} readJson + * @property {function(string, BufferOrStringCallback): void} readlink + * @property {function(string, DirentArrayCallback): void} readdir + * @property {function(string, StatsCallback): void} stat + * @property {function(string, StatsCallback): void=} lstat + * @property {(function(string, BufferOrStringCallback): void)=} realpath + * @property {(function(string=): void)=} purge + * @property {(function(string, string): string)=} join + * @property {(function(string, string): string)=} relative + * @property {(function(string): string)=} dirname + */ + +/** + * @typedef {Object} WatchFileSystem + * @property {WatchMethod} watch + */ + +/** + * @typedef {Object} IntermediateFileSystemExtras + * @property {function(string): void} mkdirSync + * @property {function(string): NodeJS.WritableStream} createWriteStream + * @property {function(string, string, NumberCallback): void} open + * @property {function(number, Buffer, number, number, number, NumberCallback): void} read + * @property {function(number, Callback): void} close + * @property {function(string, string, Callback): void} rename + */ + +/** @typedef {InputFileSystem & OutputFileSystem & IntermediateFileSystemExtras} IntermediateFileSystem */ + +/** + * + * @param {InputFileSystem|OutputFileSystem|undefined} fs a file system + * @param {string} rootPath the root path + * @param {string} targetPath the target path + * @returns {string} location of targetPath relative to rootPath + */ +const relative = (fs, rootPath, targetPath) => { + if (fs && fs.relative) { + return fs.relative(rootPath, targetPath); + } else if (path.posix.isAbsolute(rootPath)) { + return path.posix.relative(rootPath, targetPath); + } else if (path.win32.isAbsolute(rootPath)) { + return path.win32.relative(rootPath, targetPath); + } else { + throw new Error( + `${rootPath} is neither a posix nor a windows path, and there is no 'relative' method defined in the file system` + ); } - /** - * @param {Set>} itemsWithGroups input items with groups - * @returns {(T | R)[]} groups items - */ - const runGrouping = itemsWithGroups => { - const totalSize = itemsWithGroups.size; - for (const entry of itemsWithGroups) { - for (const group of entry.groups) { - if (group.alreadyGrouped) continue; - const items = group.items; - if (items === undefined) { - group.items = new Set([entry]); - } else { - items.add(entry); +}; +exports.relative = relative; + +/** + * @param {InputFileSystem|OutputFileSystem|undefined} fs a file system + * @param {string} rootPath a path + * @param {string} filename a filename + * @returns {string} the joined path + */ +const join = (fs, rootPath, filename) => { + if (fs && fs.join) { + return fs.join(rootPath, filename); + } else if (path.posix.isAbsolute(rootPath)) { + return path.posix.join(rootPath, filename); + } else if (path.win32.isAbsolute(rootPath)) { + return path.win32.join(rootPath, filename); + } else { + throw new Error( + `${rootPath} is neither a posix nor a windows path, and there is no 'join' method defined in the file system` + ); + } +}; +exports.join = join; + +/** + * @param {InputFileSystem|OutputFileSystem|undefined} fs a file system + * @param {string} absPath an absolute path + * @returns {string} the parent directory of the absolute path + */ +const dirname = (fs, absPath) => { + if (fs && fs.dirname) { + return fs.dirname(absPath); + } else if (path.posix.isAbsolute(absPath)) { + return path.posix.dirname(absPath); + } else if (path.win32.isAbsolute(absPath)) { + return path.win32.dirname(absPath); + } else { + throw new Error( + `${absPath} is neither a posix nor a windows path, and there is no 'dirname' method defined in the file system` + ); + } +}; +exports.dirname = dirname; + +/** + * @param {OutputFileSystem} fs a file system + * @param {string} p an absolute path + * @param {function(Error=): void} callback callback function for the error + * @returns {void} + */ +const mkdirp = (fs, p, callback) => { + fs.mkdir(p, err => { + if (err) { + if (err.code === "ENOENT") { + const dir = dirname(fs, p); + if (dir === p) { + callback(err); + return; } - } - } - /** @type {Map, { items: Set>, options: GroupOptions | false | undefined, used: boolean }>} */ - const groupMap = new Map(); - for (const group of allGroups.values()) { - if (group.items) { - const items = group.items; - group.items = undefined; - groupMap.set(group, { - items, - options: undefined, - used: false + mkdirp(fs, dir, err => { + if (err) { + callback(err); + return; + } + fs.mkdir(p, err => { + if (err) { + if (err.code === "EEXIST") { + callback(); + return; + } + callback(err); + return; + } + callback(); + }); }); + return; + } else if (err.code === "EEXIST") { + callback(); + return; } + callback(err); + return; } - /** @type {(T | R)[]} */ - const results = []; - for (;;) { - /** @type {Group} */ - let bestGroup = undefined; - let bestGroupSize = -1; - let bestGroupItems = undefined; - let bestGroupOptions = undefined; - for (const [group, state] of groupMap) { - const { items, used } = state; - let options = state.options; - if (options === undefined) { - const groupConfig = group.config; - state.options = options = - (groupConfig.getOptions && - groupConfig.getOptions( - group.name, - Array.from(items, ({ item }) => item) - )) || - false; - } + callback(); + }); +}; +exports.mkdirp = mkdirp; - const force = options && options.force; - if (!force) { - if (bestGroupOptions && bestGroupOptions.force) continue; - if (used) continue; - if (items.size <= 1 || totalSize - items.size <= 1) { - continue; - } - } - const targetGroupCount = (options && options.targetGroupCount) || 4; - let sizeValue = force - ? items.size - : Math.min( - items.size, - (totalSize * 2) / targetGroupCount + - itemsWithGroups.size - - items.size - ); - if ( - sizeValue > bestGroupSize || - (force && (!bestGroupOptions || !bestGroupOptions.force)) - ) { - bestGroup = group; - bestGroupSize = sizeValue; - bestGroupItems = items; - bestGroupOptions = options; +/** + * @param {IntermediateFileSystem} fs a file system + * @param {string} p an absolute path + * @returns {void} + */ +const mkdirpSync = (fs, p) => { + try { + fs.mkdirSync(p); + } catch (err) { + if (err) { + if (err.code === "ENOENT") { + const dir = dirname(fs, p); + if (dir === p) { + throw err; } + mkdirpSync(fs, dir); + fs.mkdirSync(p); + return; + } else if (err.code === "EEXIST") { + return; } - if (bestGroup === undefined) { - break; - } - const items = new Set(bestGroupItems); - const options = bestGroupOptions; + throw err; + } + } +}; +exports.mkdirpSync = mkdirpSync; - const groupChildren = !options || options.groupChildren !== false; +/** + * @param {InputFileSystem} fs a file system + * @param {string} p an absolute path + * @param {ReadJsonCallback} callback callback + * @returns {void} + */ +const readJson = (fs, p, callback) => { + if ("readJson" in fs) return fs.readJson(p, callback); + fs.readFile(p, (err, buf) => { + if (err) return callback(err); + let data; + try { + data = JSON.parse(buf.toString("utf-8")); + } catch (e) { + return callback(e); + } + return callback(null, data); + }); +}; +exports.readJson = readJson; - for (const item of items) { - itemsWithGroups.delete(item); - // Remove all groups that items have from the map to not select them again - for (const group of item.groups) { - const state = groupMap.get(group); - if (state !== undefined) { - state.items.delete(item); - if (state.items.size === 0) { - groupMap.delete(group); - } else { - state.options = undefined; - if (groupChildren) { - state.used = true; - } - } - } - } +/** + * @param {InputFileSystem} fs a file system + * @param {string} p an absolute path + * @param {ReadJsonCallback} callback callback + * @returns {void} + */ +const lstatReadlinkAbsolute = (fs, p, callback) => { + let i = 3; + const doReadLink = () => { + fs.readlink(p, (err, target) => { + if (err && --i > 0) { + // It might was just changed from symlink to file + // we retry 2 times to catch this case before throwing the error + return doStat(); } - groupMap.delete(bestGroup); - - const key = bestGroup.name; - const groupConfig = bestGroup.config; - - const allItems = Array.from(items, ({ item }) => item); - - bestGroup.alreadyGrouped = true; - const children = groupChildren ? runGrouping(items) : allItems; - bestGroup.alreadyGrouped = false; - - results.push(groupConfig.createGroup(key, children, allItems)); - } - for (const { item } of itemsWithGroups) { - results.push(item); + if (err || !target) return doStat(); + const value = target.toString(); + callback(null, join(fs, dirname(fs, p), value)); + }); + }; + const doStat = () => { + if ("lstat" in fs) { + return fs.lstat(p, (err, stats) => { + if (err) return callback(err); + if (stats.isSymbolicLink()) { + return doReadLink(); + } + callback(null, stats); + }); + } else { + return fs.stat(p, callback); } - return results; }; - return runGrouping(itemsWithGroups); + if ("lstat" in fs) return doStat(); + doReadLink(); }; - -module.exports = smartGrouping; +exports.lstatReadlinkAbsolute = lstatReadlinkAbsolute; /***/ }), -/***/ 4002: -/***/ (function(__unused_webpack_module, exports) { +/***/ 32928: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; /* @@ -130622,65 +129499,72 @@ module.exports = smartGrouping; -/** @typedef {import("webpack-sources").Source} Source */ - -/** @type {WeakMap>} */ -const equalityCache = new WeakMap(); - -/** - * @param {Source} a a source - * @param {Source} b another source - * @returns {boolean} true, when both sources are equal - */ -const _isSourceEqual = (a, b) => { - // prefer .buffer(), it's called anyway during emit - /** @type {Buffer|string} */ - let aSource = typeof a.buffer === "function" ? a.buffer() : a.source(); - /** @type {Buffer|string} */ - let bSource = typeof b.buffer === "function" ? b.buffer() : b.source(); - if (aSource === bSource) return true; - if (typeof aSource === "string" && typeof bSource === "string") return false; - if (!Buffer.isBuffer(aSource)) aSource = Buffer.from(aSource, "utf-8"); - if (!Buffer.isBuffer(bSource)) bSource = Buffer.from(bSource, "utf-8"); - return aSource.equals(bSource); -}; +const Hash = __webpack_require__(21301); +const MAX_SHORT_STRING = __webpack_require__(21941).MAX_SHORT_STRING; -/** - * @param {Source} a a source - * @param {Source} b another source - * @returns {boolean} true, when both sources are equal - */ -const isSourceEqual = (a, b) => { - if (a === b) return true; - const cache1 = equalityCache.get(a); - if (cache1 !== undefined) { - const result = cache1.get(b); - if (result !== undefined) return result; +class BatchedHash extends Hash { + constructor(hash) { + super(); + this.string = undefined; + this.encoding = undefined; + this.hash = hash; } - const result = _isSourceEqual(a, b); - if (cache1 !== undefined) { - cache1.set(b, result); - } else { - const map = new WeakMap(); - map.set(b, result); - equalityCache.set(a, map); + + /** + * Update hash {@link https://nodejs.org/api/crypto.html#crypto_hash_update_data_inputencoding} + * @param {string|Buffer} data data + * @param {string=} inputEncoding data encoding + * @returns {this} updated hash + */ + update(data, inputEncoding) { + if (this.string !== undefined) { + if ( + typeof data === "string" && + inputEncoding === this.encoding && + this.string.length + data.length < MAX_SHORT_STRING + ) { + this.string += data; + return this; + } + this.hash.update(this.string, this.encoding); + this.string = undefined; + } + if (typeof data === "string") { + if ( + data.length < MAX_SHORT_STRING && + // base64 encoding is not valid since it may contain padding chars + (!inputEncoding || !inputEncoding.startsWith("ba")) + ) { + this.string = data; + this.encoding = inputEncoding; + } else { + this.hash.update(data, inputEncoding); + } + } else { + this.hash.update(data); + } + return this; } - const cache2 = equalityCache.get(b); - if (cache2 !== undefined) { - cache2.set(a, result); - } else { - const map = new WeakMap(); - map.set(a, result); - equalityCache.set(b, map); + + /** + * Calculates the digest {@link https://nodejs.org/api/crypto.html#crypto_hash_digest_encoding} + * @param {string=} encoding encoding of the return value + * @returns {string|Buffer} digest + */ + digest(encoding) { + if (this.string !== undefined) { + this.hash.update(this.string, this.encoding); + } + return this.hash.digest(encoding); } - return result; -}; -exports.isSourceEqual = isSourceEqual; +} + +module.exports = BatchedHash; /***/ }), -/***/ 55959: +/***/ 20487: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; @@ -130691,179 +129575,195 @@ exports.isSourceEqual = isSourceEqual; -const { validate } = __webpack_require__(79286); +const create = __webpack_require__(21941); -/* cSpell:disable */ -const DID_YOU_MEAN = { - rules: "module.rules", - loaders: "module.rules or module.rules.*.use", - query: "module.rules.*.options (BREAKING CHANGE since webpack 5)", - noParse: "module.noParse", - filename: "output.filename or module.rules.*.generator.filename", - file: "output.filename", - chunkFilename: "output.chunkFilename", - chunkfilename: "output.chunkFilename", - ecmaVersion: - "output.environment (output.ecmaVersion was a temporary configuration option during webpack 5 beta)", - ecmaversion: - "output.environment (output.ecmaVersion was a temporary configuration option during webpack 5 beta)", - ecma: "output.environment (output.ecmaVersion was a temporary configuration option during webpack 5 beta)", - path: "output.path", - pathinfo: "output.pathinfo", - pathInfo: "output.pathinfo", - jsonpFunction: "output.chunkLoadingGlobal (BREAKING CHANGE since webpack 5)", - chunkCallbackName: - "output.chunkLoadingGlobal (BREAKING CHANGE since webpack 5)", - jsonpScriptType: "output.scriptType (BREAKING CHANGE since webpack 5)", - hotUpdateFunction: "output.hotUpdateGlobal (BREAKING CHANGE since webpack 5)", - splitChunks: "optimization.splitChunks", - immutablePaths: "snapshot.immutablePaths", - managedPaths: "snapshot.managedPaths", - maxModules: "stats.modulesSpace (BREAKING CHANGE since webpack 5)", - hashedModuleIds: - 'optimization.moduleIds: "hashed" (BREAKING CHANGE since webpack 5)', - namedChunks: - 'optimization.chunkIds: "named" (BREAKING CHANGE since webpack 5)', - namedModules: - 'optimization.moduleIds: "named" (BREAKING CHANGE since webpack 5)', - occurrenceOrder: - 'optimization.chunkIds: "size" and optimization.moduleIds: "size" (BREAKING CHANGE since webpack 5)', - automaticNamePrefix: - "optimization.splitChunks.[cacheGroups.*].idHint (BREAKING CHANGE since webpack 5)", - noEmitOnErrors: - "optimization.emitOnErrors (BREAKING CHANGE since webpack 5: logic is inverted to avoid negative flags)", - Buffer: - "to use the ProvidePlugin to process the Buffer variable to modules as polyfill\n" + - "BREAKING CHANGE: webpack 5 no longer provided Node.js polyfills by default.\n" + - "Note: if you are using 'node.Buffer: false', you can just remove that as this is the default behavior now.\n" + - "To provide a polyfill to modules use:\n" + - 'new ProvidePlugin({ Buffer: ["buffer", "Buffer"] }) and npm install buffer.', - process: - "to use the ProvidePlugin to process the process variable to modules as polyfill\n" + - "BREAKING CHANGE: webpack 5 no longer provided Node.js polyfills by default.\n" + - "Note: if you are using 'node.process: false', you can just remove that as this is the default behavior now.\n" + - "To provide a polyfill to modules use:\n" + - 'new ProvidePlugin({ process: "process" }) and npm install buffer.' -}; +//#region wasm code: md4 (../../../assembly/hash/md4.asm.ts) --initialMemory 1 +const md4 = new WebAssembly.Module( + Buffer.from( + // 2156 bytes + "AGFzbQEAAAABCAJgAX8AYAAAAwUEAQAAAAUDAQABBhoFfwFBAAt/AUEAC38BQQALfwFBAAt/AUEACwciBARpbml0AAAGdXBkYXRlAAIFZmluYWwAAwZtZW1vcnkCAAqLEAQmAEGBxpS6BiQBQYnXtv5+JAJB/rnrxXkkA0H2qMmBASQEQQAkAAvSCgEZfyMBIQUjAiECIwMhAyMEIQQDQCAAIAFLBEAgASgCJCISIAEoAiAiEyABKAIcIgkgASgCGCIIIAEoAhQiByABKAIQIg4gASgCDCIGIAEoAggiDyABKAIEIhAgASgCACIRIAMgBHMgAnEgBHMgBWpqQQN3IgogAiADc3EgA3MgBGpqQQd3IgsgAiAKc3EgAnMgA2pqQQt3IgwgCiALc3EgCnMgAmpqQRN3Ig0gCyAMc3EgC3MgCmpqQQN3IgogDCANc3EgDHMgC2pqQQd3IgsgCiANc3EgDXMgDGpqQQt3IgwgCiALc3EgCnMgDWpqQRN3Ig0gCyAMc3EgC3MgCmpqQQN3IhQgDCANc3EgDHMgC2pqQQd3IRUgASgCLCILIAEoAigiCiAMIA0gDSAUcyAVcXNqakELdyIWIBQgFXNxIBRzIA1qakETdyEXIAEoAjQiGCABKAIwIhkgFSAWcyAXcSAVcyAUampBA3ciFCAWIBdzcSAWcyAVampBB3chFSABKAI8Ig0gASgCOCIMIBQgF3MgFXEgF3MgFmpqQQt3IhYgFCAVc3EgFHMgF2pqQRN3IRcgEyAOIBEgFCAVIBZyIBdxIBUgFnFyampBmfOJ1AVqQQN3IhQgFiAXcnEgFiAXcXIgFWpqQZnzidQFakEFdyIVIBQgF3JxIBQgF3FyIBZqakGZ84nUBWpBCXchFiAPIBggEiAWIAcgFSAQIBQgGSAUIBVyIBZxIBQgFXFyIBdqakGZ84nUBWpBDXciFCAVIBZycSAVIBZxcmpqQZnzidQFakEDdyIVIBQgFnJxIBQgFnFyampBmfOJ1AVqQQV3IhcgFCAVcnEgFCAVcXJqakGZ84nUBWpBCXciFiAVIBdycSAVIBdxciAUampBmfOJ1AVqQQ13IhQgFiAXcnEgFiAXcXIgFWpqQZnzidQFakEDdyEVIBEgBiAVIAwgFCAKIBYgCCAUIBZyIBVxIBQgFnFyIBdqakGZ84nUBWpBBXciFyAUIBVycSAUIBVxcmpqQZnzidQFakEJdyIWIBUgF3JxIBUgF3FyampBmfOJ1AVqQQ13IhQgFiAXcnEgFiAXcXJqakGZ84nUBWpBA3ciFSALIBYgCSAUIBZyIBVxIBQgFnFyIBdqakGZ84nUBWpBBXciFiAUIBVycSAUIBVxcmpqQZnzidQFakEJdyIXIA0gFSAWciAXcSAVIBZxciAUampBmfOJ1AVqQQ13IhRzIBZzampBodfn9gZqQQN3IREgByAIIA4gFCARIBcgESAUc3MgFmogE2pBodfn9gZqQQl3IhNzcyAXampBodfn9gZqQQt3Ig4gDyARIBMgDiARIA4gE3NzIBRqIBlqQaHX5/YGakEPdyIRc3NqakGh1+f2BmpBA3ciDyAOIA8gEXNzIBNqIApqQaHX5/YGakEJdyIKcyARc2pqQaHX5/YGakELdyIIIBAgDyAKIAggDCAPIAggCnNzIBFqakGh1+f2BmpBD3ciDHNzampBodfn9gZqQQN3Ig4gEiAIIAwgDnNzIApqakGh1+f2BmpBCXciCHMgDHNqakGh1+f2BmpBC3chByAFIAYgCCAHIBggDiAHIAhzcyAMampBodfn9gZqQQ93IgpzcyAOampBodfn9gZqQQN3IgZqIQUgDSAGIAkgByAGIAsgByAGIApzcyAIampBodfn9gZqQQl3IgdzIApzampBodfn9gZqQQt3IgYgB3NzIApqakGh1+f2BmpBD3cgAmohAiADIAZqIQMgBCAHaiEEIAFBQGshAQwBCwsgBSQBIAIkAiADJAMgBCQECw0AIAAQASAAIwBqJAAL/wQCA38BfiAAIwBqrUIDhiEEIABByABqQUBxIgJBCGshAyAAIgFBAWohACABQYABOgAAA0AgACACSUEAIABBB3EbBEAgAEEAOgAAIABBAWohAAwBCwsDQCAAIAJJBEAgAEIANwMAIABBCGohAAwBCwsgAyAENwMAIAIQAUEAIwGtIgRC//8DgyAEQoCA/P8Pg0IQhoQiBEL/gYCA8B+DIARCgP6DgIDgP4NCCIaEIgRCj4C8gPCBwAeDQgiGIARC8IHAh4CegPgAg0IEiIQiBEKGjJiw4MCBgwZ8QgSIQoGChIiQoMCAAYNCJ34gBEKw4MCBg4aMmDCEfDcDAEEIIwKtIgRC//8DgyAEQoCA/P8Pg0IQhoQiBEL/gYCA8B+DIARCgP6DgIDgP4NCCIaEIgRCj4C8gPCBwAeDQgiGIARC8IHAh4CegPgAg0IEiIQiBEKGjJiw4MCBgwZ8QgSIQoGChIiQoMCAAYNCJ34gBEKw4MCBg4aMmDCEfDcDAEEQIwOtIgRC//8DgyAEQoCA/P8Pg0IQhoQiBEL/gYCA8B+DIARCgP6DgIDgP4NCCIaEIgRCj4C8gPCBwAeDQgiGIARC8IHAh4CegPgAg0IEiIQiBEKGjJiw4MCBgwZ8QgSIQoGChIiQoMCAAYNCJ34gBEKw4MCBg4aMmDCEfDcDAEEYIwStIgRC//8DgyAEQoCA/P8Pg0IQhoQiBEL/gYCA8B+DIARCgP6DgIDgP4NCCIaEIgRCj4C8gPCBwAeDQgiGIARC8IHAh4CegPgAg0IEiIQiBEKGjJiw4MCBgwZ8QgSIQoGChIiQoMCAAYNCJ34gBEKw4MCBg4aMmDCEfDcDAAs=", + "base64" + ) +); +//#endregion -const REMOVED = { - concord: - "BREAKING CHANGE: resolve.concord has been removed and is no longer available.", - devtoolLineToLine: - "BREAKING CHANGE: output.devtoolLineToLine has been removed and is no longer available." -}; -/* cSpell:enable */ +module.exports = create.bind(null, md4, [], 64, 32); -/** - * @param {Parameters[0]} schema a json schema - * @param {Parameters[1]} options the options that should be validated - * @param {Parameters[2]=} validationConfiguration configuration for generating errors - * @returns {void} - */ -const validateSchema = (schema, options, validationConfiguration) => { - validate( - schema, - options, - validationConfiguration || { - name: "Webpack", - postFormatter: (formattedError, error) => { - const children = error.children; - if ( - children && - children.some( - child => - child.keyword === "absolutePath" && - child.dataPath === ".output.filename" - ) - ) { - return `${formattedError}\nPlease use output.path to specify absolute path and output.filename for the file name.`; - } - if ( - children && - children.some( - child => - child.keyword === "pattern" && child.dataPath === ".devtool" - ) - ) { - return ( - `${formattedError}\n` + - "BREAKING CHANGE since webpack 5: The devtool option is more strict.\n" + - "Please strictly follow the order of the keywords in the pattern." - ); - } +/***/ }), - if (error.keyword === "additionalProperties") { - const params = - /** @type {import("ajv").AdditionalPropertiesParams} */ ( - error.params - ); - if ( - Object.prototype.hasOwnProperty.call( - DID_YOU_MEAN, - params.additionalProperty - ) - ) { - return `${formattedError}\nDid you mean ${ - DID_YOU_MEAN[params.additionalProperty] - }?`; - } +/***/ 21941: +/***/ (function(module) { - if ( - Object.prototype.hasOwnProperty.call( - REMOVED, - params.additionalProperty - ) - ) { - return `${formattedError}\n${REMOVED[params.additionalProperty]}?`; - } +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ - if (!error.dataPath) { - if (params.additionalProperty === "debug") { - return ( - `${formattedError}\n` + - "The 'debug' property was removed in webpack 2.0.0.\n" + - "Loaders should be updated to allow passing this option via loader options in module.rules.\n" + - "Until loaders are updated one can use the LoaderOptionsPlugin to switch loaders into debug mode:\n" + - "plugins: [\n" + - " new webpack.LoaderOptionsPlugin({\n" + - " debug: true\n" + - " })\n" + - "]" - ); - } - if (params.additionalProperty) { - return ( - `${formattedError}\n` + - "For typos: please correct them.\n" + - "For loader options: webpack >= v2.0.0 no longer allows custom properties in configuration.\n" + - " Loaders should be updated to allow passing options via loader options in module.rules.\n" + - " Until loaders are updated one can use the LoaderOptionsPlugin to pass these options to the loader:\n" + - " plugins: [\n" + - " new webpack.LoaderOptionsPlugin({\n" + - " // test: /\\.xxx$/, // may apply this only for some modules\n" + - " options: {\n" + - ` ${params.additionalProperty}: …\n` + - " }\n" + - " })\n" + - " ]" - ); - } + +// 65536 is the size of a wasm memory page +// 64 is the maximum chunk size for every possible wasm hash implementation +// 4 is the maximum number of bytes per char for string encoding (max is utf-8) +// ~3 makes sure that it's always a block of 4 chars, so avoid partially encoded bytes for base64 +const MAX_SHORT_STRING = Math.floor((65536 - 64) / 4) & ~3; + +class WasmHash { + /** + * @param {WebAssembly.Instance} instance wasm instance + * @param {WebAssembly.Instance[]} instancesPool pool of instances + * @param {number} chunkSize size of data chunks passed to wasm + * @param {number} digestSize size of digest returned by wasm + */ + constructor(instance, instancesPool, chunkSize, digestSize) { + const exports = /** @type {any} */ (instance.exports); + exports.init(); + this.exports = exports; + this.mem = Buffer.from(exports.memory.buffer, 0, 65536); + this.buffered = 0; + this.instancesPool = instancesPool; + this.chunkSize = chunkSize; + this.digestSize = digestSize; + } + + reset() { + this.buffered = 0; + this.exports.init(); + } + + /** + * @param {Buffer | string} data data + * @param {BufferEncoding=} encoding encoding + * @returns {this} itself + */ + update(data, encoding) { + if (typeof data === "string") { + while (data.length > MAX_SHORT_STRING) { + this._updateWithShortString(data.slice(0, MAX_SHORT_STRING), encoding); + data = data.slice(MAX_SHORT_STRING); + } + this._updateWithShortString(data, encoding); + return this; + } + this._updateWithBuffer(data); + return this; + } + + /** + * @param {string} data data + * @param {BufferEncoding=} encoding encoding + * @returns {void} + */ + _updateWithShortString(data, encoding) { + const { exports, buffered, mem, chunkSize } = this; + let endPos; + if (data.length < 70) { + if (!encoding || encoding === "utf-8" || encoding === "utf8") { + endPos = buffered; + for (let i = 0; i < data.length; i++) { + const cc = data.charCodeAt(i); + if (cc < 0x80) mem[endPos++] = cc; + else if (cc < 0x800) { + mem[endPos] = (cc >> 6) | 0xc0; + mem[endPos + 1] = (cc & 0x3f) | 0x80; + endPos += 2; + } else { + // bail-out for weird chars + endPos += mem.write(data.slice(i), endPos, encoding); + break; } } + } else if (encoding === "latin1") { + endPos = buffered; + for (let i = 0; i < data.length; i++) { + const cc = data.charCodeAt(i); + mem[endPos++] = cc; + } + } else { + endPos = buffered + mem.write(data, buffered, encoding); + } + } else { + endPos = buffered + mem.write(data, buffered, encoding); + } + if (endPos < chunkSize) { + this.buffered = endPos; + } else { + const l = endPos & ~(this.chunkSize - 1); + exports.update(l); + const newBuffered = endPos - l; + this.buffered = newBuffered; + if (newBuffered > 0) mem.copyWithin(0, l, endPos); + } + } - return formattedError; + /** + * @param {Buffer} data data + * @returns {void} + */ + _updateWithBuffer(data) { + const { exports, buffered, mem } = this; + const length = data.length; + if (buffered + length < this.chunkSize) { + data.copy(mem, buffered, 0, length); + this.buffered += length; + } else { + const l = (buffered + length) & ~(this.chunkSize - 1); + if (l > 65536) { + let i = 65536 - buffered; + data.copy(mem, buffered, 0, i); + exports.update(65536); + const stop = l - buffered - 65536; + while (i < stop) { + data.copy(mem, 0, i, i + 65536); + exports.update(65536); + i += 65536; + } + data.copy(mem, 0, i, l - buffered); + exports.update(l - buffered - i); + } else { + data.copy(mem, buffered, 0, l - buffered); + exports.update(l); } + const newBuffered = length + buffered - l; + this.buffered = newBuffered; + if (newBuffered > 0) data.copy(mem, 0, length - newBuffered, length); } - ); + } + + digest(type) { + const { exports, buffered, mem, digestSize } = this; + exports.final(buffered); + this.instancesPool.push(this); + const hex = mem.toString("latin1", 0, digestSize); + if (type === "hex") return hex; + if (type === "binary" || !type) return Buffer.from(hex, "hex"); + return Buffer.from(hex, "hex").toString(type); + } +} + +const create = (wasmModule, instancesPool, chunkSize, digestSize) => { + if (instancesPool.length > 0) { + const old = instancesPool.pop(); + old.reset(); + return old; + } else { + return new WasmHash( + new WebAssembly.Instance(wasmModule), + instancesPool, + chunkSize, + digestSize + ); + } }; -module.exports = validateSchema; + +module.exports = create; +module.exports.MAX_SHORT_STRING = MAX_SHORT_STRING; /***/ }), -/***/ 84465: +/***/ 37364: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; @@ -130874,339 +129774,388 @@ module.exports = validateSchema; -const RuntimeGlobals = __webpack_require__(49404); -const RuntimeModule = __webpack_require__(61439); -const Template = __webpack_require__(92066); - -class AsyncWasmLoadingRuntimeModule extends RuntimeModule { - constructor({ generateLoadBinaryCode, supportsStreaming }) { - super("wasm loading", RuntimeModule.STAGE_NORMAL); - this.generateLoadBinaryCode = generateLoadBinaryCode; - this.supportsStreaming = supportsStreaming; - } +const create = __webpack_require__(21941); - /** - * @returns {string} runtime code - */ - generate() { - const { compilation, chunk } = this; - const { outputOptions, runtimeTemplate } = compilation; - const fn = RuntimeGlobals.instantiateWasm; - const wasmModuleSrcPath = compilation.getPath( - JSON.stringify(outputOptions.webassemblyModuleFilename), - { - hash: `" + ${RuntimeGlobals.getFullHash}() + "`, - hashWithLength: length => - `" + ${RuntimeGlobals.getFullHash}}().slice(0, ${length}) + "`, - module: { - id: '" + wasmModuleId + "', - hash: `" + wasmModuleHash + "`, - hashWithLength(length) { - return `" + wasmModuleHash.slice(0, ${length}) + "`; - } - }, - runtime: chunk.runtime - } - ); - return `${fn} = ${runtimeTemplate.basicFunction( - "exports, wasmModuleId, wasmModuleHash, importsObj", - [ - `var req = ${this.generateLoadBinaryCode(wasmModuleSrcPath)};`, - this.supportsStreaming - ? Template.asString([ - "if (typeof WebAssembly.instantiateStreaming === 'function') {", - Template.indent([ - "return WebAssembly.instantiateStreaming(req, importsObj)", - Template.indent([ - `.then(${runtimeTemplate.returningFunction( - "Object.assign(exports, res.instance.exports)", - "res" - )});` - ]) - ]), - "}" - ]) - : "// no support for streaming compilation", - "return req", - Template.indent([ - `.then(${runtimeTemplate.returningFunction("x.arrayBuffer()", "x")})`, - `.then(${runtimeTemplate.returningFunction( - "WebAssembly.instantiate(bytes, importsObj)", - "bytes" - )})`, - `.then(${runtimeTemplate.returningFunction( - "Object.assign(exports, res.instance.exports)", - "res" - )});` - ]) - ] - )};`; - } -} +//#region wasm code: xxhash64 (../../../assembly/hash/xxhash64.asm.ts) --initialMemory 1 +const xxhash64 = new WebAssembly.Module( + Buffer.from( + // 1173 bytes + "AGFzbQEAAAABCAJgAX8AYAAAAwQDAQAABQMBAAEGGgV+AUIAC34BQgALfgFCAAt+AUIAC34BQgALByIEBGluaXQAAAZ1cGRhdGUAAQVmaW5hbAACBm1lbW9yeQIACrUIAzAAQtbrgu7q/Yn14AAkAELP1tO+0ser2UIkAUIAJAJC+erQ0OfJoeThACQDQgAkBAvUAQIBfwR+IABFBEAPCyMEIACtfCQEIwAhAiMBIQMjAiEEIwMhBQNAIAIgASkDAELP1tO+0ser2UJ+fEIfiUKHla+vmLbem55/fiECIAMgASkDCELP1tO+0ser2UJ+fEIfiUKHla+vmLbem55/fiEDIAQgASkDEELP1tO+0ser2UJ+fEIfiUKHla+vmLbem55/fiEEIAUgASkDGELP1tO+0ser2UJ+fEIfiUKHla+vmLbem55/fiEFIAAgAUEgaiIBSw0ACyACJAAgAyQBIAQkAiAFJAMLqwYCAX8EfiMEQgBSBH4jACICQgGJIwEiA0IHiXwjAiIEQgyJfCMDIgVCEol8IAJCz9bTvtLHq9lCfkIfiUKHla+vmLbem55/foVCh5Wvr5i23puef35CnaO16oOxjYr6AH0gA0LP1tO+0ser2UJ+Qh+JQoeVr6+Ytt6bnn9+hUKHla+vmLbem55/fkKdo7Xqg7GNivoAfSAEQs/W077Sx6vZQn5CH4lCh5Wvr5i23puef36FQoeVr6+Ytt6bnn9+Qp2jteqDsY2K+gB9IAVCz9bTvtLHq9lCfkIfiUKHla+vmLbem55/foVCh5Wvr5i23puef35CnaO16oOxjYr6AH0FQsXP2bLx5brqJwsjBCAArXx8IQIDQCABQQhqIABNBEAgAiABKQMAQs/W077Sx6vZQn5CH4lCh5Wvr5i23puef36FQhuJQoeVr6+Ytt6bnn9+Qp2jteqDsY2K+gB9IQIgAUEIaiEBDAELCyABQQRqIABNBEACfyACIAE1AgBCh5Wvr5i23puef36FQheJQs/W077Sx6vZQn5C+fPd8Zn2masWfCECIAFBBGoLIQELA0AgACABRwRAIAIgATEAAELFz9my8eW66id+hUILiUKHla+vmLbem55/fiECIAFBAWohAQwBCwtBACACIAJCIYiFQs/W077Sx6vZQn4iAkIdiCAChUL5893xmfaZqxZ+IgJCIIggAoUiAkIgiCIDQv//A4NCIIYgA0KAgPz/D4NCEIiEIgNC/4GAgPAfg0IQhiADQoD+g4CA4D+DQgiIhCIDQo+AvIDwgcAHg0IIhiADQvCBwIeAnoD4AINCBIiEIgNChoyYsODAgYMGfEIEiEKBgoSIkKDAgAGDQid+IANCsODAgYOGjJgwhHw3AwBBCCACQv////8PgyICQv//A4NCIIYgAkKAgPz/D4NCEIiEIgJC/4GAgPAfg0IQhiACQoD+g4CA4D+DQgiIhCICQo+AvIDwgcAHg0IIhiACQvCBwIeAnoD4AINCBIiEIgJChoyYsODAgYMGfEIEiEKBgoSIkKDAgAGDQid+IAJCsODAgYOGjJgwhHw3AwAL", + "base64" + ) +); +//#endregion -module.exports = AsyncWasmLoadingRuntimeModule; +module.exports = create.bind(null, xxhash64, [], 32, 16); /***/ }), -/***/ 60072: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { +/***/ 96236: +/***/ (function(__unused_webpack_module, exports, __webpack_require__) { "use strict"; /* MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra */ -const Generator = __webpack_require__(1826); +const path = __webpack_require__(85622); -/** @typedef {import("webpack-sources").Source} Source */ -/** @typedef {import("../Generator").GenerateContext} GenerateContext */ -/** @typedef {import("../NormalModule")} NormalModule */ +const WINDOWS_ABS_PATH_REGEXP = /^[a-zA-Z]:[\\/]/; +const SEGMENTS_SPLIT_REGEXP = /([|!])/; +const WINDOWS_PATH_SEPARATOR_REGEXP = /\\/g; -const TYPES = new Set(["webassembly"]); +/** + * @typedef {Object} MakeRelativePathsCache + * @property {Map>=} relativePaths + */ -class AsyncWebAssemblyGenerator extends Generator { - constructor(options) { - super(); - this.options = options; +const relativePathToRequest = relativePath => { + if (relativePath === "") return "./."; + if (relativePath === "..") return "../."; + if (relativePath.startsWith("../")) return relativePath; + return `./${relativePath}`; +}; + +/** + * @param {string} context context for relative path + * @param {string} maybeAbsolutePath path to make relative + * @returns {string} relative path in request style + */ +const absoluteToRequest = (context, maybeAbsolutePath) => { + if (maybeAbsolutePath[0] === "/") { + if ( + maybeAbsolutePath.length > 1 && + maybeAbsolutePath[maybeAbsolutePath.length - 1] === "/" + ) { + // this 'path' is actually a regexp generated by dynamic requires. + // Don't treat it as an absolute path. + return maybeAbsolutePath; + } + + const querySplitPos = maybeAbsolutePath.indexOf("?"); + let resource = + querySplitPos === -1 + ? maybeAbsolutePath + : maybeAbsolutePath.slice(0, querySplitPos); + resource = relativePathToRequest(path.posix.relative(context, resource)); + return querySplitPos === -1 + ? resource + : resource + maybeAbsolutePath.slice(querySplitPos); } - /** - * @param {NormalModule} module fresh module - * @returns {Set} available types (do not mutate) - */ - getTypes(module) { - return TYPES; + if (WINDOWS_ABS_PATH_REGEXP.test(maybeAbsolutePath)) { + const querySplitPos = maybeAbsolutePath.indexOf("?"); + let resource = + querySplitPos === -1 + ? maybeAbsolutePath + : maybeAbsolutePath.slice(0, querySplitPos); + resource = path.win32.relative(context, resource); + if (!WINDOWS_ABS_PATH_REGEXP.test(resource)) { + resource = relativePathToRequest( + resource.replace(WINDOWS_PATH_SEPARATOR_REGEXP, "/") + ); + } + return querySplitPos === -1 + ? resource + : resource + maybeAbsolutePath.slice(querySplitPos); } + // not an absolute path + return maybeAbsolutePath; +}; + +/** + * @param {string} context context for relative path + * @param {string} relativePath path + * @returns {string} absolute path + */ +const requestToAbsolute = (context, relativePath) => { + if (relativePath.startsWith("./") || relativePath.startsWith("../")) + return path.join(context, relativePath); + return relativePath; +}; + +const makeCacheable = fn => { + /** @type {WeakMap>>} */ + const cache = new WeakMap(); + /** - * @param {NormalModule} module the module - * @param {string=} type source type - * @returns {number} estimate size of the module + * @param {string} context context used to create relative path + * @param {string} identifier identifier used to create relative path + * @param {Object=} associatedObjectForCache an object to which the cache will be attached + * @returns {string} the returned relative path */ - getSize(module, type) { - const originalSource = module.originalSource(); - if (!originalSource) { - return 0; + const cachedFn = (context, identifier, associatedObjectForCache) => { + if (!associatedObjectForCache) return fn(context, identifier); + + let innerCache = cache.get(associatedObjectForCache); + if (innerCache === undefined) { + innerCache = new Map(); + cache.set(associatedObjectForCache, innerCache); } - return originalSource.size(); - } + + let cachedResult; + let innerSubCache = innerCache.get(context); + if (innerSubCache === undefined) { + innerCache.set(context, (innerSubCache = new Map())); + } else { + cachedResult = innerSubCache.get(identifier); + } + + if (cachedResult !== undefined) { + return cachedResult; + } else { + const result = fn(context, identifier); + innerSubCache.set(identifier, result); + return result; + } + }; /** - * @param {NormalModule} module module for which the code should be generated - * @param {GenerateContext} generateContext context for generate - * @returns {Source} generated code + * @param {Object=} associatedObjectForCache an object to which the cache will be attached + * @returns {function(string, string): string} cached function */ - generate(module, generateContext) { - return module.originalSource(); - } -} + cachedFn.bindCache = associatedObjectForCache => { + let innerCache; + if (associatedObjectForCache) { + innerCache = cache.get(associatedObjectForCache); + if (innerCache === undefined) { + innerCache = new Map(); + cache.set(associatedObjectForCache, innerCache); + } + } else { + innerCache = new Map(); + } -module.exports = AsyncWebAssemblyGenerator; + /** + * @param {string} context context used to create relative path + * @param {string} identifier identifier used to create relative path + * @returns {string} the returned relative path + */ + const boundFn = (context, identifier) => { + let cachedResult; + let innerSubCache = innerCache.get(context); + if (innerSubCache === undefined) { + innerCache.set(context, (innerSubCache = new Map())); + } else { + cachedResult = innerSubCache.get(identifier); + } + if (cachedResult !== undefined) { + return cachedResult; + } else { + const result = fn(context, identifier); + innerSubCache.set(identifier, result); + return result; + } + }; -/***/ }), + return boundFn; + }; -/***/ 33838: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + /** + * @param {string} context context used to create relative path + * @param {Object=} associatedObjectForCache an object to which the cache will be attached + * @returns {function(string): string} cached function + */ + cachedFn.bindContextCache = (context, associatedObjectForCache) => { + let innerSubCache; + if (associatedObjectForCache) { + let innerCache = cache.get(associatedObjectForCache); + if (innerCache === undefined) { + innerCache = new Map(); + cache.set(associatedObjectForCache, innerCache); + } -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ + innerSubCache = innerCache.get(context); + if (innerSubCache === undefined) { + innerCache.set(context, (innerSubCache = new Map())); + } + } else { + innerSubCache = new Map(); + } + /** + * @param {string} identifier identifier used to create relative path + * @returns {string} the returned relative path + */ + const boundFn = identifier => { + const cachedResult = innerSubCache.get(identifier); + if (cachedResult !== undefined) { + return cachedResult; + } else { + const result = fn(context, identifier); + innerSubCache.set(identifier, result); + return result; + } + }; + return boundFn; + }; -const { RawSource } = __webpack_require__(96192); -const Generator = __webpack_require__(1826); -const InitFragment = __webpack_require__(51739); -const RuntimeGlobals = __webpack_require__(49404); -const Template = __webpack_require__(92066); -const WebAssemblyImportDependency = __webpack_require__(97093); + return cachedFn; +}; -/** @typedef {import("webpack-sources").Source} Source */ -/** @typedef {import("../DependencyTemplates")} DependencyTemplates */ -/** @typedef {import("../Generator").GenerateContext} GenerateContext */ -/** @typedef {import("../Module")} Module */ -/** @typedef {import("../NormalModule")} NormalModule */ -/** @typedef {import("../RuntimeTemplate")} RuntimeTemplate */ +/** + * + * @param {string} context context for relative path + * @param {string} identifier identifier for path + * @returns {string} a converted relative path + */ +const _makePathsRelative = (context, identifier) => { + return identifier + .split(SEGMENTS_SPLIT_REGEXP) + .map(str => absoluteToRequest(context, str)) + .join(""); +}; -const TYPES = new Set(["webassembly"]); +exports.makePathsRelative = makeCacheable(_makePathsRelative); -class AsyncWebAssemblyJavascriptGenerator extends Generator { - constructor(filenameTemplate) { - super(); - this.filenameTemplate = filenameTemplate; - } +/** + * + * @param {string} context context for relative path + * @param {string} identifier identifier for path + * @returns {string} a converted relative path + */ +const _makePathsAbsolute = (context, identifier) => { + return identifier + .split(SEGMENTS_SPLIT_REGEXP) + .map(str => requestToAbsolute(context, str)) + .join(""); +}; - /** - * @param {NormalModule} module fresh module - * @returns {Set} available types (do not mutate) - */ - getTypes(module) { - return TYPES; - } +exports.makePathsAbsolute = makeCacheable(_makePathsAbsolute); - /** - * @param {NormalModule} module the module - * @param {string=} type source type - * @returns {number} estimate size of the module - */ - getSize(module, type) { - return 40 + module.dependencies.length * 10; - } +/** + * @param {string} context absolute context path + * @param {string} request any request string may containing absolute paths, query string, etc. + * @returns {string} a new request string avoiding absolute paths when possible + */ +const _contextify = (context, request) => { + return request + .split("!") + .map(r => absoluteToRequest(context, r)) + .join("!"); +}; - /** - * @param {NormalModule} module module for which the code should be generated - * @param {GenerateContext} generateContext context for generate - * @returns {Source} generated code - */ - generate(module, generateContext) { - const { - runtimeTemplate, - chunkGraph, - moduleGraph, - runtimeRequirements, - runtime - } = generateContext; - runtimeRequirements.add(RuntimeGlobals.module); - runtimeRequirements.add(RuntimeGlobals.moduleId); - runtimeRequirements.add(RuntimeGlobals.exports); - runtimeRequirements.add(RuntimeGlobals.instantiateWasm); - /** @type {InitFragment[]} */ - const initFragments = []; - /** @type {Map} */ - const depModules = new Map(); - /** @type {Map} */ - const wasmDepsByRequest = new Map(); - for (const dep of module.dependencies) { - if (dep instanceof WebAssemblyImportDependency) { - const module = moduleGraph.getModule(dep); - if (!depModules.has(module)) { - depModules.set(module, { - request: dep.request, - importVar: `WEBPACK_IMPORTED_MODULE_${depModules.size}` - }); - } - let list = wasmDepsByRequest.get(dep.request); - if (list === undefined) { - list = []; - wasmDepsByRequest.set(dep.request, list); - } - list.push(dep); - } - } +const contextify = makeCacheable(_contextify); +exports.contextify = contextify; - const promises = []; +/** + * @param {string} context absolute context path + * @param {string} request any request string + * @returns {string} a new request string using absolute paths when possible + */ +const _absolutify = (context, request) => { + return request + .split("!") + .map(r => requestToAbsolute(context, r)) + .join("!"); +}; - const importStatements = Array.from( - depModules, - ([importedModule, { request, importVar }]) => { - if (moduleGraph.isAsync(importedModule)) { - promises.push(importVar); - } - return runtimeTemplate.importStatement({ - update: false, - module: importedModule, - chunkGraph, - request, - originModule: module, - importVar, - runtimeRequirements - }); - } - ); - const importsCode = importStatements.map(([x]) => x).join(""); - const importsCompatCode = importStatements.map(([_, x]) => x).join(""); +const absolutify = makeCacheable(_absolutify); +exports.absolutify = absolutify; - const importObjRequestItems = Array.from( - wasmDepsByRequest, - ([request, deps]) => { - const exportItems = deps.map(dep => { - const importedModule = moduleGraph.getModule(dep); - const importVar = depModules.get(importedModule).importVar; - return `${JSON.stringify( - dep.name - )}: ${runtimeTemplate.exportFromImport({ - moduleGraph, - module: importedModule, - request, - exportName: dep.name, - originModule: module, - asiSafe: true, - isCall: false, - callContext: false, - defaultInterop: true, - importVar, - initFragments, - runtime, - runtimeRequirements - })}`; - }); - return Template.asString([ - `${JSON.stringify(request)}: {`, - Template.indent(exportItems.join(",\n")), - "}" - ]); - } - ); +const PATH_QUERY_FRAGMENT_REGEXP = + /^((?:\0.|[^?#\0])*)(\?(?:\0.|[^#\0])*)?(#.*)?$/; - const importsObj = - importObjRequestItems.length > 0 - ? Template.asString([ - "{", - Template.indent(importObjRequestItems.join(",\n")), - "}" - ]) - : undefined; +/** @typedef {{ resource: string, path: string, query: string, fragment: string }} ParsedResource */ - const instantiateCall = - `${RuntimeGlobals.instantiateWasm}(${module.exportsArgument}, ${ - module.moduleArgument - }.id, ${JSON.stringify( - chunkGraph.getRenderedModuleHash(module, runtime) - )}` + (importsObj ? `, ${importsObj})` : `)`); +/** + * @param {string} str the path with query and fragment + * @returns {ParsedResource} parsed parts + */ +const _parseResource = str => { + const match = PATH_QUERY_FRAGMENT_REGEXP.exec(str); + return { + resource: str, + path: match[1].replace(/\0(.)/g, "$1"), + query: match[2] ? match[2].replace(/\0(.)/g, "$1") : "", + fragment: match[3] || "" + }; +}; +exports.parseResource = (realFn => { + /** @type {WeakMap>} */ + const cache = new WeakMap(); - if (promises.length > 0) - runtimeRequirements.add(RuntimeGlobals.asyncModule); + const getCache = associatedObjectForCache => { + const entry = cache.get(associatedObjectForCache); + if (entry !== undefined) return entry; + /** @type {Map} */ + const map = new Map(); + cache.set(associatedObjectForCache, map); + return map; + }; - const source = new RawSource( - promises.length > 0 - ? Template.asString([ - `var __webpack_instantiate__ = ${runtimeTemplate.basicFunction( - `[${promises.join(", ")}]`, - `${importsCompatCode}return ${instantiateCall};` - )}`, - `${RuntimeGlobals.asyncModule}(${ - module.moduleArgument - }, ${runtimeTemplate.basicFunction( - "__webpack_handle_async_dependencies__", - [ - importsCode, - `var __webpack_async_dependencies__ = __webpack_handle_async_dependencies__([${promises.join( - ", " - )}]);`, - "return __webpack_async_dependencies__.then ? __webpack_async_dependencies__.then(__webpack_instantiate__) : __webpack_instantiate__(__webpack_async_dependencies__);" - ] - )}, 1);` - ]) - : `${importsCode}${importsCompatCode}module.exports = ${instantiateCall};` - ); + /** + * @param {string} str the path with query and fragment + * @param {Object=} associatedObjectForCache an object to which the cache will be attached + * @returns {ParsedResource} parsed parts + */ + const fn = (str, associatedObjectForCache) => { + if (!associatedObjectForCache) return realFn(str); + const cache = getCache(associatedObjectForCache); + const entry = cache.get(str); + if (entry !== undefined) return entry; + const result = realFn(str); + cache.set(str, result); + return result; + }; - return InitFragment.addToSource(source, initFragments, generateContext); + fn.bindCache = associatedObjectForCache => { + const cache = getCache(associatedObjectForCache); + return str => { + const entry = cache.get(str); + if (entry !== undefined) return entry; + const result = realFn(str); + cache.set(str, result); + return result; + }; + }; + + return fn; +})(_parseResource); + +/** + * @param {string} filename the filename which should be undone + * @param {string} outputPath the output path that is restored (only relevant when filename contains "..") + * @param {boolean} enforceRelative true returns ./ for empty paths + * @returns {string} repeated ../ to leave the directory of the provided filename to be back on output dir + */ +exports.getUndoPath = (filename, outputPath, enforceRelative) => { + let depth = -1; + let append = ""; + outputPath = outputPath.replace(/[\\/]$/, ""); + for (const part of filename.split(/[/\\]+/)) { + if (part === "..") { + if (depth > -1) { + depth--; + } else { + const i = outputPath.lastIndexOf("/"); + const j = outputPath.lastIndexOf("\\"); + const pos = i < 0 ? j : j < 0 ? i : Math.max(i, j); + if (pos < 0) return outputPath + "/"; + append = outputPath.slice(pos + 1) + "/" + append; + outputPath = outputPath.slice(0, pos); + } + } else if (part !== ".") { + depth++; + } } -} - -module.exports = AsyncWebAssemblyJavascriptGenerator; + return depth > 0 + ? `${"../".repeat(depth)}${append}` + : enforceRelative + ? `./${append}` + : append; +}; /***/ }), -/***/ 13804: +/***/ 7679: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; @@ -131217,690 +130166,490 @@ module.exports = AsyncWebAssemblyJavascriptGenerator; -const { SyncWaterfallHook } = __webpack_require__(34718); -const Compilation = __webpack_require__(59622); -const Generator = __webpack_require__(1826); -const { tryRunOrWebpackError } = __webpack_require__(89935); -const WebAssemblyImportDependency = __webpack_require__(97093); -const { compareModulesByIdentifier } = __webpack_require__(26296); -const memoize = __webpack_require__(84297); - -/** @typedef {import("webpack-sources").Source} Source */ -/** @typedef {import("../Chunk")} Chunk */ -/** @typedef {import("../ChunkGraph")} ChunkGraph */ -/** @typedef {import("../CodeGenerationResults")} CodeGenerationResults */ -/** @typedef {import("../Compiler")} Compiler */ -/** @typedef {import("../DependencyTemplates")} DependencyTemplates */ -/** @typedef {import("../Module")} Module */ -/** @typedef {import("../ModuleGraph")} ModuleGraph */ -/** @typedef {import("../RuntimeTemplate")} RuntimeTemplate */ -/** @typedef {import("../Template").RenderManifestEntry} RenderManifestEntry */ -/** @typedef {import("../Template").RenderManifestOptions} RenderManifestOptions */ - -const getAsyncWebAssemblyGenerator = memoize(() => - __webpack_require__(60072) -); -const getAsyncWebAssemblyJavascriptGenerator = memoize(() => - __webpack_require__(33838) -); -const getAsyncWebAssemblyParser = memoize(() => - __webpack_require__(20595) -); - -/** - * @typedef {Object} WebAssemblyRenderContext - * @property {Chunk} chunk the chunk - * @property {DependencyTemplates} dependencyTemplates the dependency templates - * @property {RuntimeTemplate} runtimeTemplate the runtime template - * @property {ModuleGraph} moduleGraph the module graph - * @property {ChunkGraph} chunkGraph the chunk graph - * @property {CodeGenerationResults} codeGenerationResults results of code generation - */ - -/** - * @typedef {Object} CompilationHooks - * @property {SyncWaterfallHook<[Source, Module, WebAssemblyRenderContext]>} renderModuleContent - */ - -/** @type {WeakMap} */ -const compilationHooksMap = new WeakMap(); +// We need to include a list of requires here +// to allow webpack to be bundled with only static requires +// We could use a dynamic require(`../${request}`) but this +// would include too many modules and not every tool is able +// to process this +module.exports = { + AsyncDependenciesBlock: () => __webpack_require__(11315), + CommentCompilationWarning: () => __webpack_require__(28151), + ContextModule: () => __webpack_require__(80207), + "cache/PackFileCacheStrategy": () => + __webpack_require__(46810), + "cache/ResolverCachePlugin": () => __webpack_require__(11740), + "container/ContainerEntryDependency": () => + __webpack_require__(44055), + "container/ContainerEntryModule": () => + __webpack_require__(3234), + "container/ContainerExposedDependency": () => + __webpack_require__(50), + "container/FallbackDependency": () => + __webpack_require__(41061), + "container/FallbackItemDependency": () => + __webpack_require__(33393), + "container/FallbackModule": () => __webpack_require__(95193), + "container/RemoteModule": () => __webpack_require__(581), + "container/RemoteToExternalDependency": () => + __webpack_require__(44637), + "dependencies/AMDDefineDependency": () => + __webpack_require__(76309), + "dependencies/AMDRequireArrayDependency": () => + __webpack_require__(98233), + "dependencies/AMDRequireContextDependency": () => + __webpack_require__(60958), + "dependencies/AMDRequireDependenciesBlock": () => + __webpack_require__(69675), + "dependencies/AMDRequireDependency": () => + __webpack_require__(11311), + "dependencies/AMDRequireItemDependency": () => + __webpack_require__(90377), + "dependencies/CachedConstDependency": () => + __webpack_require__(64177), + "dependencies/CreateScriptUrlDependency": () => + __webpack_require__(29829), + "dependencies/CommonJsRequireContextDependency": () => + __webpack_require__(84175), + "dependencies/CommonJsExportRequireDependency": () => + __webpack_require__(76922), + "dependencies/CommonJsExportsDependency": () => + __webpack_require__(9585), + "dependencies/CommonJsFullRequireDependency": () => + __webpack_require__(29496), + "dependencies/CommonJsRequireDependency": () => + __webpack_require__(38604), + "dependencies/CommonJsSelfReferenceDependency": () => + __webpack_require__(69217), + "dependencies/ConstDependency": () => + __webpack_require__(60864), + "dependencies/ContextDependency": () => + __webpack_require__(67840), + "dependencies/ContextElementDependency": () => + __webpack_require__(83853), + "dependencies/CriticalDependencyWarning": () => + __webpack_require__(14190), + "dependencies/DelegatedSourceDependency": () => + __webpack_require__(82766), + "dependencies/DllEntryDependency": () => + __webpack_require__(57839), + "dependencies/EntryDependency": () => + __webpack_require__(41075), + "dependencies/ExportsInfoDependency": () => + __webpack_require__(30474), + "dependencies/HarmonyAcceptDependency": () => + __webpack_require__(38421), + "dependencies/HarmonyAcceptImportDependency": () => + __webpack_require__(35316), + "dependencies/HarmonyCompatibilityDependency": () => + __webpack_require__(56164), + "dependencies/HarmonyExportExpressionDependency": () => + __webpack_require__(22705), + "dependencies/HarmonyExportHeaderDependency": () => + __webpack_require__(67159), + "dependencies/HarmonyExportImportedSpecifierDependency": () => + __webpack_require__(77952), + "dependencies/HarmonyExportSpecifierDependency": () => + __webpack_require__(59042), + "dependencies/HarmonyImportSideEffectDependency": () => + __webpack_require__(76853), + "dependencies/HarmonyImportSpecifierDependency": () => + __webpack_require__(61994), + "dependencies/ImportContextDependency": () => + __webpack_require__(75785), + "dependencies/ImportDependency": () => + __webpack_require__(16727), + "dependencies/ImportEagerDependency": () => + __webpack_require__(91941), + "dependencies/ImportWeakDependency": () => + __webpack_require__(58426), + "dependencies/JsonExportsDependency": () => + __webpack_require__(36986), + "dependencies/LocalModule": () => __webpack_require__(930), + "dependencies/LocalModuleDependency": () => + __webpack_require__(67494), + "dependencies/ModuleDecoratorDependency": () => + __webpack_require__(58969), + "dependencies/ModuleHotAcceptDependency": () => + __webpack_require__(90200), + "dependencies/ModuleHotDeclineDependency": () => + __webpack_require__(72986), + "dependencies/ImportMetaHotAcceptDependency": () => + __webpack_require__(58287), + "dependencies/ImportMetaHotDeclineDependency": () => + __webpack_require__(89911), + "dependencies/ProvidedDependency": () => + __webpack_require__(88915), + "dependencies/PureExpressionDependency": () => + __webpack_require__(24746), + "dependencies/RequireContextDependency": () => + __webpack_require__(98854), + "dependencies/RequireEnsureDependenciesBlock": () => + __webpack_require__(91421), + "dependencies/RequireEnsureDependency": () => + __webpack_require__(975), + "dependencies/RequireEnsureItemDependency": () => + __webpack_require__(56867), + "dependencies/RequireHeaderDependency": () => + __webpack_require__(57010), + "dependencies/RequireIncludeDependency": () => + __webpack_require__(17046), + "dependencies/RequireIncludeDependencyParserPlugin": () => + __webpack_require__(29984), + "dependencies/RequireResolveContextDependency": () => + __webpack_require__(48789), + "dependencies/RequireResolveDependency": () => + __webpack_require__(93172), + "dependencies/RequireResolveHeaderDependency": () => + __webpack_require__(24128), + "dependencies/RuntimeRequirementsDependency": () => + __webpack_require__(75941), + "dependencies/StaticExportsDependency": () => + __webpack_require__(67967), + "dependencies/SystemPlugin": () => __webpack_require__(88768), + "dependencies/UnsupportedDependency": () => + __webpack_require__(41381), + "dependencies/URLDependency": () => __webpack_require__(30990), + "dependencies/WebAssemblyExportImportedDependency": () => + __webpack_require__(18248), + "dependencies/WebAssemblyImportDependency": () => + __webpack_require__(97093), + "dependencies/WebpackIsIncludedDependency": () => + __webpack_require__(41744), + "dependencies/WorkerDependency": () => + __webpack_require__(73016), + "json/JsonData": () => __webpack_require__(97637), + "optimize/ConcatenatedModule": () => + __webpack_require__(1881), + DelegatedModule: () => __webpack_require__(68719), + DependenciesBlock: () => __webpack_require__(21484), + DllModule: () => __webpack_require__(52692), + ExternalModule: () => __webpack_require__(89805), + FileSystemInfo: () => __webpack_require__(13679), + InitFragment: () => __webpack_require__(51739), + InvalidDependenciesModuleWarning: () => + __webpack_require__(2822), + Module: () => __webpack_require__(85887), + ModuleBuildError: () => __webpack_require__(37991), + ModuleDependencyWarning: () => __webpack_require__(61528), + ModuleError: () => __webpack_require__(11686), + ModuleGraph: () => __webpack_require__(20258), + ModuleParseError: () => __webpack_require__(13110), + ModuleWarning: () => __webpack_require__(92085), + NormalModule: () => __webpack_require__(11026), + RawModule: () => __webpack_require__(82329), + "sharing/ConsumeSharedModule": () => + __webpack_require__(61474), + "sharing/ConsumeSharedFallbackDependency": () => + __webpack_require__(90489), + "sharing/ProvideSharedModule": () => + __webpack_require__(65945), + "sharing/ProvideSharedDependency": () => + __webpack_require__(99355), + "sharing/ProvideForSharedDependency": () => + __webpack_require__(40235), + UnsupportedFeatureWarning: () => __webpack_require__(9532), + "util/LazySet": () => __webpack_require__(59534), + UnhandledSchemeError: () => __webpack_require__(63859), + NodeStuffInWebError: () => __webpack_require__(5771), + WebpackError: () => __webpack_require__(68422), -class AsyncWebAssemblyModulesPlugin { - /** - * @param {Compilation} compilation the compilation - * @returns {CompilationHooks} the attached hooks - */ - static getCompilationHooks(compilation) { - if (!(compilation instanceof Compilation)) { - throw new TypeError( - "The 'compilation' argument must be an instance of Compilation" - ); - } - let hooks = compilationHooksMap.get(compilation); - if (hooks === undefined) { - hooks = { - renderModuleContent: new SyncWaterfallHook([ - "source", - "module", - "renderContext" - ]) - }; - compilationHooksMap.set(compilation, hooks); - } - return hooks; + "util/registerExternalSerializer": () => { + // already registered } +}; - constructor(options) { - this.options = options; - } - /** - * Apply the plugin - * @param {Compiler} compiler the compiler instance - * @returns {void} - */ - apply(compiler) { - compiler.hooks.compilation.tap( - "AsyncWebAssemblyModulesPlugin", - (compilation, { normalModuleFactory }) => { - const hooks = - AsyncWebAssemblyModulesPlugin.getCompilationHooks(compilation); - compilation.dependencyFactories.set( - WebAssemblyImportDependency, - normalModuleFactory - ); +/***/ }), - normalModuleFactory.hooks.createParser - .for("webassembly/async") - .tap("AsyncWebAssemblyModulesPlugin", () => { - const AsyncWebAssemblyParser = getAsyncWebAssemblyParser(); +/***/ 26522: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - return new AsyncWebAssemblyParser(); - }); - normalModuleFactory.hooks.createGenerator - .for("webassembly/async") - .tap("AsyncWebAssemblyModulesPlugin", () => { - const AsyncWebAssemblyJavascriptGenerator = - getAsyncWebAssemblyJavascriptGenerator(); - const AsyncWebAssemblyGenerator = getAsyncWebAssemblyGenerator(); +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php +*/ - return Generator.byType({ - javascript: new AsyncWebAssemblyJavascriptGenerator( - compilation.outputOptions.webassemblyModuleFilename - ), - webassembly: new AsyncWebAssemblyGenerator(this.options) - }); - }); - compilation.hooks.renderManifest.tap( - "WebAssemblyModulesPlugin", - (result, options) => { - const { moduleGraph, chunkGraph, runtimeTemplate } = compilation; - const { - chunk, - outputOptions, - dependencyTemplates, - codeGenerationResults - } = options; - for (const module of chunkGraph.getOrderedChunkModulesIterable( - chunk, - compareModulesByIdentifier - )) { - if (module.type === "webassembly/async") { - const filenameTemplate = - outputOptions.webassemblyModuleFilename; +const { register } = __webpack_require__(99551); - result.push({ - render: () => - this.renderModule( - module, - { - chunk, - dependencyTemplates, - runtimeTemplate, - moduleGraph, - chunkGraph, - codeGenerationResults - }, - hooks - ), - filenameTemplate, - pathOptions: { - module, - runtime: chunk.runtime, - chunkGraph - }, - auxiliary: true, - identifier: `webassemblyAsyncModule${chunkGraph.getModuleId( - module - )}`, - hash: chunkGraph.getModuleHash(module, chunk.runtime) - }); - } - } +class ClassSerializer { + constructor(Constructor) { + this.Constructor = Constructor; + } - return result; - } - ); - } - ); + serialize(obj, context) { + obj.serialize(context); } - renderModule(module, renderContext, hooks) { - const { codeGenerationResults, chunk } = renderContext; - try { - const moduleSource = codeGenerationResults.getSource( - module, - chunk.runtime, - "webassembly" - ); - return tryRunOrWebpackError( - () => - hooks.renderModuleContent.call(moduleSource, module, renderContext), - "AsyncWebAssemblyModulesPlugin.getCompilationHooks().renderModuleContent" - ); - } catch (e) { - e.module = module; - throw e; + deserialize(context) { + if (typeof this.Constructor.deserialize === "function") { + return this.Constructor.deserialize(context); } + const obj = new this.Constructor(); + obj.deserialize(context); + return obj; } } -module.exports = AsyncWebAssemblyModulesPlugin; +module.exports = (Constructor, request, name = null) => { + register(Constructor, request, name, new ClassSerializer(Constructor)); +}; /***/ }), -/***/ 20595: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { +/***/ 84297: +/***/ (function(module) { "use strict"; /* MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra */ -const t = __webpack_require__(98688); -const { decode } = __webpack_require__(8062); -const Parser = __webpack_require__(68214); -const StaticExportsDependency = __webpack_require__(67967); -const WebAssemblyImportDependency = __webpack_require__(97093); - -/** @typedef {import("../Parser").ParserState} ParserState */ -/** @typedef {import("../Parser").PreparsedAst} PreparsedAst */ - -const decoderOpts = { - ignoreCodeSection: true, - ignoreDataSection: true, - - // this will avoid having to lookup with identifiers in the ModuleContext - ignoreCustomNameSection: true -}; - -class WebAssemblyParser extends Parser { - constructor(options) { - super(); - this.hooks = Object.freeze({}); - this.options = options; - } +/** @template T @typedef {function(): T} FunctionReturning */ - /** - * @param {string | Buffer | PreparsedAst} source the source to parse - * @param {ParserState} state the parser state - * @returns {ParserState} the parser state - */ - parse(source, state) { - if (!Buffer.isBuffer(source)) { - throw new Error("WebAssemblyParser input must be a Buffer"); +/** + * @template T + * @param {FunctionReturning} fn memorized function + * @returns {FunctionReturning} new function + */ +const memoize = fn => { + let cache = false; + /** @type {T} */ + let result = undefined; + return () => { + if (cache) { + return result; + } else { + result = fn(); + cache = true; + // Allow to clean up memory for fn + // and all dependent resources + fn = undefined; + return result; } + }; +}; - // flag it as async module - state.module.buildInfo.strict = true; - state.module.buildMeta.exportsType = "namespace"; - state.module.buildMeta.async = true; - - // parse it - const program = decode(source, decoderOpts); - const module = program.body[0]; - - const exports = []; - t.traverse(module, { - ModuleExport({ node }) { - exports.push(node.name); - }, - - ModuleImport({ node }) { - const dep = new WebAssemblyImportDependency( - node.module, - node.name, - node.descr, - false - ); - - state.module.addDependency(dep); - } - }); - - state.module.addDependency(new StaticExportsDependency(exports, false)); - - return state; - } -} - -module.exports = WebAssemblyParser; +module.exports = memoize; /***/ }), -/***/ 13475: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { +/***/ 91679: +/***/ (function(module) { "use strict"; /* MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra */ -const WebpackError = __webpack_require__(68422); +const SAFE_LIMIT = 0x80000000; +const SAFE_PART = SAFE_LIMIT - 1; +const COUNT = 4; +const arr = [0, 0, 0, 0, 0]; +const primes = [3, 7, 17, 19]; -module.exports = class UnsupportedWebAssemblyFeatureError extends WebpackError { - /** @param {string} message Error message */ - constructor(message) { - super(message); - this.name = "UnsupportedWebAssemblyFeatureError"; - this.hideStack = true; +module.exports = (str, range) => { + arr.fill(0); + for (let i = 0; i < str.length; i++) { + const c = str.charCodeAt(i); + for (let j = 0; j < COUNT; j++) { + const p = (j + COUNT - 1) % COUNT; + arr[j] = (arr[j] + c * primes[j] + arr[p]) & SAFE_PART; + } + for (let j = 0; j < COUNT; j++) { + const q = arr[j] % COUNT; + arr[j] = arr[j] ^ (arr[q] >> 1); + } + } + if (range <= SAFE_PART) { + let sum = 0; + for (let j = 0; j < COUNT; j++) { + sum = (sum + arr[j]) % range; + } + return sum; + } else { + let sum1 = 0; + let sum2 = 0; + const rangeExt = Math.floor(range / SAFE_LIMIT); + for (let j = 0; j < COUNT; j += 2) { + sum1 = (sum1 + arr[j]) & SAFE_PART; + } + for (let j = 1; j < COUNT; j += 2) { + sum2 = (sum2 + arr[j]) % rangeExt; + } + return (sum2 * SAFE_LIMIT + sum1) % range; } }; /***/ }), -/***/ 92153: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { +/***/ 76815: +/***/ (function(module) { "use strict"; /* MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra */ -const RuntimeGlobals = __webpack_require__(49404); -const RuntimeModule = __webpack_require__(61439); -const Template = __webpack_require__(92066); -const { compareModulesByIdentifier } = __webpack_require__(26296); -const WebAssemblyUtils = __webpack_require__(41520); +/** + * @template T + * @template {Error} E + * @param {Iterable} items initial items + * @param {number} concurrency number of items running in parallel + * @param {function(T, function(T): void, function(E=): void): void} processor worker which pushes more items + * @param {function(E=): void} callback all items processed + * @returns {void} + */ +const processAsyncTree = (items, concurrency, processor, callback) => { + const queue = Array.from(items); + if (queue.length === 0) return callback(); + let processing = 0; + let finished = false; + let processScheduled = true; -/** @typedef {import("../ChunkGraph")} ChunkGraph */ -/** @typedef {import("../Compilation")} Compilation */ -/** @typedef {import("../Module")} Module */ -/** @typedef {import("../util/runtime").RuntimeSpec} RuntimeSpec */ + const push = item => { + queue.push(item); + if (!processScheduled && processing < concurrency) { + processScheduled = true; + process.nextTick(processQueue); + } + }; -// TODO webpack 6 remove the whole folder + const processorCallback = err => { + processing--; + if (err && !finished) { + finished = true; + callback(err); + return; + } + if (!processScheduled) { + processScheduled = true; + process.nextTick(processQueue); + } + }; -// Get all wasm modules -const getAllWasmModules = (moduleGraph, chunkGraph, chunk) => { - const wasmModules = chunk.getAllAsyncChunks(); - const array = []; - for (const chunk of wasmModules) { - for (const m of chunkGraph.getOrderedChunkModulesIterable( - chunk, - compareModulesByIdentifier - )) { - if (m.type.startsWith("webassembly")) { - array.push(m); - } + const processQueue = () => { + if (finished) return; + while (processing < concurrency && queue.length > 0) { + processing++; + const item = queue.pop(); + processor(item, push, processorCallback); } - } + processScheduled = false; + if (queue.length === 0 && processing === 0 && !finished) { + finished = true; + callback(); + } + }; - return array; + processQueue(); }; -/** - * generates the import object function for a module - * @param {ChunkGraph} chunkGraph the chunk graph - * @param {Module} module the module - * @param {boolean} mangle mangle imports - * @param {string[]} declarations array where declarations are pushed to - * @param {RuntimeSpec} runtime the runtime - * @returns {string} source code - */ -const generateImportObject = ( - chunkGraph, - module, - mangle, - declarations, - runtime -) => { - const moduleGraph = chunkGraph.moduleGraph; - const waitForInstances = new Map(); - const properties = []; - const usedWasmDependencies = WebAssemblyUtils.getUsedDependencies( - moduleGraph, - module, - mangle - ); - for (const usedDep of usedWasmDependencies) { - const dep = usedDep.dependency; - const importedModule = moduleGraph.getModule(dep); - const exportName = dep.name; - const usedName = - importedModule && - moduleGraph - .getExportsInfo(importedModule) - .getUsedName(exportName, runtime); - const description = dep.description; - const direct = dep.onlyDirectImport; - - const module = usedDep.module; - const name = usedDep.name; - - if (direct) { - const instanceVar = `m${waitForInstances.size}`; - waitForInstances.set(instanceVar, chunkGraph.getModuleId(importedModule)); - properties.push({ - module, - name, - value: `${instanceVar}[${JSON.stringify(usedName)}]` - }); - } else { - const params = description.signature.params.map( - (param, k) => "p" + k + param.valtype - ); - - const mod = `${RuntimeGlobals.moduleCache}[${JSON.stringify( - chunkGraph.getModuleId(importedModule) - )}]`; - const modExports = `${mod}.exports`; +module.exports = processAsyncTree; - const cache = `wasmImportedFuncCache${declarations.length}`; - declarations.push(`var ${cache};`); - properties.push({ - module, - name, - value: Template.asString([ - (importedModule.type.startsWith("webassembly") - ? `${mod} ? ${modExports}[${JSON.stringify(usedName)}] : ` - : "") + `function(${params}) {`, - Template.indent([ - `if(${cache} === undefined) ${cache} = ${modExports};`, - `return ${cache}[${JSON.stringify(usedName)}](${params});` - ]), - "}" - ]) - }); - } - } +/***/ }), - let importObject; - if (mangle) { - importObject = [ - "return {", - Template.indent([ - properties.map(p => `${JSON.stringify(p.name)}: ${p.value}`).join(",\n") - ]), - "};" - ]; - } else { - const propertiesByModule = new Map(); - for (const p of properties) { - let list = propertiesByModule.get(p.module); - if (list === undefined) { - propertiesByModule.set(p.module, (list = [])); - } - list.push(p); - } - importObject = [ - "return {", - Template.indent([ - Array.from(propertiesByModule, ([module, list]) => { - return Template.asString([ - `${JSON.stringify(module)}: {`, - Template.indent([ - list.map(p => `${JSON.stringify(p.name)}: ${p.value}`).join(",\n") - ]), - "}" - ]); - }).join(",\n") - ]), - "};" - ]; - } +/***/ 86709: +/***/ (function(module) { - const moduleIdStringified = JSON.stringify(chunkGraph.getModuleId(module)); - if (waitForInstances.size === 1) { - const moduleId = Array.from(waitForInstances.values())[0]; - const promise = `installedWasmModules[${JSON.stringify(moduleId)}]`; - const variable = Array.from(waitForInstances.keys())[0]; - return Template.asString([ - `${moduleIdStringified}: function() {`, - Template.indent([ - `return promiseResolve().then(function() { return ${promise}; }).then(function(${variable}) {`, - Template.indent(importObject), - "});" - ]), - "}," - ]); - } else if (waitForInstances.size > 0) { - const promises = Array.from( - waitForInstances.values(), - id => `installedWasmModules[${JSON.stringify(id)}]` - ).join(", "); - const variables = Array.from( - waitForInstances.keys(), - (name, i) => `${name} = array[${i}]` - ).join(", "); - return Template.asString([ - `${moduleIdStringified}: function() {`, - Template.indent([ - `return promiseResolve().then(function() { return Promise.all([${promises}]); }).then(function(array) {`, - Template.indent([`var ${variables};`, ...importObject]), - "});" - ]), - "}," - ]); - } else { - return Template.asString([ - `${moduleIdStringified}: function() {`, - Template.indent(importObject), - "}," - ]); - } -}; +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ -class WasmChunkLoadingRuntimeModule extends RuntimeModule { - constructor({ - generateLoadBinaryCode, - supportsStreaming, - mangleImports, - runtimeRequirements - }) { - super("wasm chunk loading", RuntimeModule.STAGE_ATTACH); - this.generateLoadBinaryCode = generateLoadBinaryCode; - this.supportsStreaming = supportsStreaming; - this.mangleImports = mangleImports; - this._runtimeRequirements = runtimeRequirements; - } - /** - * @returns {string} runtime code - */ - generate() { - const { chunkGraph, compilation, chunk, mangleImports } = this; - const { moduleGraph, outputOptions } = compilation; - const fn = RuntimeGlobals.ensureChunkHandlers; - const withHmr = this._runtimeRequirements.has( - RuntimeGlobals.hmrDownloadUpdateHandlers - ); - const wasmModules = getAllWasmModules(moduleGraph, chunkGraph, chunk); - const declarations = []; - const importObjects = wasmModules.map(module => { - return generateImportObject( - chunkGraph, - module, - this.mangleImports, - declarations, - chunk.runtime - ); - }); - const chunkModuleIdMap = chunkGraph.getChunkModuleIdMap(chunk, m => - m.type.startsWith("webassembly") - ); - const createImportObject = content => - mangleImports - ? `{ ${JSON.stringify(WebAssemblyUtils.MANGLED_MODULE)}: ${content} }` - : content; - const wasmModuleSrcPath = compilation.getPath( - JSON.stringify(outputOptions.webassemblyModuleFilename), - { - hash: `" + ${RuntimeGlobals.getFullHash}() + "`, - hashWithLength: length => - `" + ${RuntimeGlobals.getFullHash}}().slice(0, ${length}) + "`, - module: { - id: '" + wasmModuleId + "', - hash: `" + ${JSON.stringify( - chunkGraph.getChunkModuleRenderedHashMap(chunk, m => - m.type.startsWith("webassembly") - ) - )}[chunkId][wasmModuleId] + "`, - hashWithLength(length) { - return `" + ${JSON.stringify( - chunkGraph.getChunkModuleRenderedHashMap( - chunk, - m => m.type.startsWith("webassembly"), - length - ) - )}[chunkId][wasmModuleId] + "`; - } - }, - runtime: chunk.runtime - } - ); - const stateExpression = withHmr - ? `${RuntimeGlobals.hmrRuntimeStatePrefix}_wasm` - : undefined; +const SAFE_IDENTIFIER = /^[_a-zA-Z$][_a-zA-Z$0-9]*$/; +const RESERVED_IDENTIFIER = new Set([ + "break", + "case", + "catch", + "class", + "const", + "continue", + "debugger", + "default", + "delete", + "do", + "else", + "export", + "extends", + "finally", + "for", + "function", + "if", + "import", + "in", + "instanceof", + "new", + "return", + "super", + "switch", + "this", + "throw", + "try", + "typeof", + "var", + "void", + "while", + "with", + "enum", + // strict mode + "implements", + "interface", + "let", + "package", + "private", + "protected", + "public", + "static", + "yield", + "yield", + // module code + "await", + // skip future reserved keywords defined under ES1 till ES3 + // additional + "null", + "true", + "false" +]); - return Template.asString([ - "// object to store loaded and loading wasm modules", - `var installedWasmModules = ${ - stateExpression ? `${stateExpression} = ${stateExpression} || ` : "" - }{};`, - "", - // This function is used to delay reading the installed wasm module promises - // by a microtask. Sorting them doesn't help because there are edge cases where - // sorting is not possible (modules splitted into different chunks). - // So we not even trying and solve this by a microtask delay. - "function promiseResolve() { return Promise.resolve(); }", - "", - Template.asString(declarations), - "var wasmImportObjects = {", - Template.indent(importObjects), - "};", - "", - `var wasmModuleMap = ${JSON.stringify( - chunkModuleIdMap, - undefined, - "\t" - )};`, - "", - "// object with all WebAssembly.instance exports", - `${RuntimeGlobals.wasmInstances} = {};`, - "", - "// Fetch + compile chunk loading for webassembly", - `${fn}.wasm = function(chunkId, promises) {`, - Template.indent([ - "", - `var wasmModules = wasmModuleMap[chunkId] || [];`, - "", - "wasmModules.forEach(function(wasmModuleId, idx) {", - Template.indent([ - "var installedWasmModuleData = installedWasmModules[wasmModuleId];", - "", - '// a Promise means "currently loading" or "already loaded".', - "if(installedWasmModuleData)", - Template.indent(["promises.push(installedWasmModuleData);"]), - "else {", - Template.indent([ - `var importObject = wasmImportObjects[wasmModuleId]();`, - `var req = ${this.generateLoadBinaryCode(wasmModuleSrcPath)};`, - "var promise;", - this.supportsStreaming - ? Template.asString([ - "if(importObject && typeof importObject.then === 'function' && typeof WebAssembly.compileStreaming === 'function') {", - Template.indent([ - "promise = Promise.all([WebAssembly.compileStreaming(req), importObject]).then(function(items) {", - Template.indent([ - `return WebAssembly.instantiate(items[0], ${createImportObject( - "items[1]" - )});` - ]), - "});" - ]), - "} else if(typeof WebAssembly.instantiateStreaming === 'function') {", - Template.indent([ - `promise = WebAssembly.instantiateStreaming(req, ${createImportObject( - "importObject" - )});` - ]) - ]) - : Template.asString([ - "if(importObject && typeof importObject.then === 'function') {", - Template.indent([ - "var bytesPromise = req.then(function(x) { return x.arrayBuffer(); });", - "promise = Promise.all([", - Template.indent([ - "bytesPromise.then(function(bytes) { return WebAssembly.compile(bytes); }),", - "importObject" - ]), - "]).then(function(items) {", - Template.indent([ - `return WebAssembly.instantiate(items[0], ${createImportObject( - "items[1]" - )});` - ]), - "});" - ]) - ]), - "} else {", - Template.indent([ - "var bytesPromise = req.then(function(x) { return x.arrayBuffer(); });", - "promise = bytesPromise.then(function(bytes) {", - Template.indent([ - `return WebAssembly.instantiate(bytes, ${createImportObject( - "importObject" - )});` - ]), - "});" - ]), - "}", - "promises.push(installedWasmModules[wasmModuleId] = promise.then(function(res) {", - Template.indent([ - `return ${RuntimeGlobals.wasmInstances}[wasmModuleId] = (res.instance || res).exports;` - ]), - "}));" - ]), - "}" - ]), - "});" - ]), - "};" - ]); +const propertyAccess = (properties, start = 0) => { + let str = ""; + for (let i = start; i < properties.length; i++) { + const p = properties[i]; + if (`${+p}` === p) { + str += `[${p}]`; + } else if (SAFE_IDENTIFIER.test(p) && !RESERVED_IDENTIFIER.has(p)) { + str += `.${p}`; + } else { + str += `[${JSON.stringify(p)}]`; + } } -} + return str; +}; -module.exports = WasmChunkLoadingRuntimeModule; +module.exports = propertyAccess; /***/ }), -/***/ 12995: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { +/***/ 31107: +/***/ (function(__unused_webpack_module, __unused_webpack_exports, __webpack_require__) { "use strict"; /* @@ -131910,87 +130659,342 @@ module.exports = WasmChunkLoadingRuntimeModule; -const formatLocation = __webpack_require__(57261); -const UnsupportedWebAssemblyFeatureError = __webpack_require__(13475); +const { register } = __webpack_require__(99551); -/** @typedef {import("../Compiler")} Compiler */ +const Position = /** @type {TODO} */ __webpack_require__(29089).Position; +const SourceLocation = __webpack_require__(29089).SourceLocation; +const ValidationError = __webpack_require__(40321)/* .default */ .Z; +const { + CachedSource, + ConcatSource, + OriginalSource, + PrefixSource, + RawSource, + ReplaceSource, + SourceMapSource +} = __webpack_require__(96192); -class WasmFinalizeExportsPlugin { - /** - * Apply the plugin - * @param {Compiler} compiler the compiler instance - * @returns {void} - */ - apply(compiler) { - compiler.hooks.compilation.tap("WasmFinalizeExportsPlugin", compilation => { - compilation.hooks.finishModules.tap( - "WasmFinalizeExportsPlugin", - modules => { - for (const module of modules) { - // 1. if a WebAssembly module - if (module.type.startsWith("webassembly") === true) { - const jsIncompatibleExports = - module.buildMeta.jsIncompatibleExports; +/** @typedef {import("acorn").Position} Position */ +/** @typedef {import("../Dependency").RealDependencyLocation} RealDependencyLocation */ +/** @typedef {import("../Dependency").SourcePosition} SourcePosition */ +/** @typedef {import("./serialization").ObjectDeserializerContext} ObjectDeserializerContext */ +/** @typedef {import("./serialization").ObjectSerializerContext} ObjectSerializerContext */ - if (jsIncompatibleExports === undefined) { - continue; - } +/** @typedef {ObjectSerializerContext & { writeLazy?: (any) => void }} WebpackObjectSerializerContext */ - for (const connection of compilation.moduleGraph.getIncomingConnections( - module - )) { - // 2. is active and referenced by a non-WebAssembly module - if ( - connection.isTargetActive(undefined) && - connection.originModule.type.startsWith("webassembly") === - false - ) { - const referencedExports = - compilation.getDependencyReferencedExports( - connection.dependency, - undefined - ); +const CURRENT_MODULE = "webpack/lib/util/registerExternalSerializer"; - for (const info of referencedExports) { - const names = Array.isArray(info) ? info : info.name; - if (names.length === 0) continue; - const name = names[0]; - if (typeof name === "object") continue; - // 3. and uses a func with an incompatible JS signature - if ( - Object.prototype.hasOwnProperty.call( - jsIncompatibleExports, - name - ) - ) { - // 4. error - const error = new UnsupportedWebAssemblyFeatureError( - `Export "${name}" with ${jsIncompatibleExports[name]} can only be used for direct wasm to wasm dependencies\n` + - `It's used from ${connection.originModule.readableIdentifier( - compilation.requestShortener - )} at ${formatLocation(connection.dependency.loc)}.` - ); - error.module = module; - compilation.errors.push(error); - } - } - } - } - } - } +register( + CachedSource, + CURRENT_MODULE, + "webpack-sources/CachedSource", + new (class CachedSourceSerializer { + /** + * @param {CachedSource} source the cached source to be serialized + * @param {WebpackObjectSerializerContext} context context + * @returns {void} + */ + serialize(source, { write, writeLazy }) { + if (writeLazy) { + writeLazy(source.originalLazy()); + } else { + write(source.original()); + } + write(source.getCachedData()); + } + + /** + * @param {ObjectDeserializerContext} context context + * @returns {CachedSource} cached source + */ + deserialize({ read }) { + const source = read(); + const cachedData = read(); + return new CachedSource(source, cachedData); + } + })() +); + +register( + RawSource, + CURRENT_MODULE, + "webpack-sources/RawSource", + new (class RawSourceSerializer { + /** + * @param {RawSource} source the raw source to be serialized + * @param {WebpackObjectSerializerContext} context context + * @returns {void} + */ + serialize(source, { write }) { + write(source.buffer()); + write(!source.isBuffer()); + } + + /** + * @param {ObjectDeserializerContext} context context + * @returns {RawSource} raw source + */ + deserialize({ read }) { + const source = read(); + const convertToString = read(); + return new RawSource(source, convertToString); + } + })() +); + +register( + ConcatSource, + CURRENT_MODULE, + "webpack-sources/ConcatSource", + new (class ConcatSourceSerializer { + /** + * @param {ConcatSource} source the concat source to be serialized + * @param {WebpackObjectSerializerContext} context context + * @returns {void} + */ + serialize(source, { write }) { + write(source.getChildren()); + } + + /** + * @param {ObjectDeserializerContext} context context + * @returns {ConcatSource} concat source + */ + deserialize({ read }) { + const source = new ConcatSource(); + source.addAllSkipOptimizing(read()); + return source; + } + })() +); + +register( + PrefixSource, + CURRENT_MODULE, + "webpack-sources/PrefixSource", + new (class PrefixSourceSerializer { + /** + * @param {PrefixSource} source the prefix source to be serialized + * @param {WebpackObjectSerializerContext} context context + * @returns {void} + */ + serialize(source, { write }) { + write(source.getPrefix()); + write(source.original()); + } + + /** + * @param {ObjectDeserializerContext} context context + * @returns {PrefixSource} prefix source + */ + deserialize({ read }) { + return new PrefixSource(read(), read()); + } + })() +); + +register( + ReplaceSource, + CURRENT_MODULE, + "webpack-sources/ReplaceSource", + new (class ReplaceSourceSerializer { + /** + * @param {ReplaceSource} source the replace source to be serialized + * @param {WebpackObjectSerializerContext} context context + * @returns {void} + */ + serialize(source, { write }) { + write(source.original()); + write(source.getName()); + const replacements = source.getReplacements(); + write(replacements.length); + for (const repl of replacements) { + write(repl.start); + write(repl.end); + } + for (const repl of replacements) { + write(repl.content); + write(repl.name); + } + } + + /** + * @param {ObjectDeserializerContext} context context + * @returns {ReplaceSource} replace source + */ + deserialize({ read }) { + const source = new ReplaceSource(read(), read()); + const len = read(); + const startEndBuffer = []; + for (let i = 0; i < len; i++) { + startEndBuffer.push(read(), read()); + } + let j = 0; + for (let i = 0; i < len; i++) { + source.replace( + startEndBuffer[j++], + startEndBuffer[j++], + read(), + read() + ); + } + return source; + } + })() +); + +register( + OriginalSource, + CURRENT_MODULE, + "webpack-sources/OriginalSource", + new (class OriginalSourceSerializer { + /** + * @param {OriginalSource} source the original source to be serialized + * @param {WebpackObjectSerializerContext} context context + * @returns {void} + */ + serialize(source, { write }) { + write(source.buffer()); + write(source.getName()); + } + + /** + * @param {ObjectDeserializerContext} context context + * @returns {OriginalSource} original source + */ + deserialize({ read }) { + const buffer = read(); + const name = read(); + return new OriginalSource(buffer, name); + } + })() +); + +register( + SourceLocation, + CURRENT_MODULE, + "acorn/SourceLocation", + new (class SourceLocationSerializer { + /** + * @param {SourceLocation} loc the location to be serialized + * @param {WebpackObjectSerializerContext} context context + * @returns {void} + */ + serialize(loc, { write }) { + write(loc.start.line); + write(loc.start.column); + write(loc.end.line); + write(loc.end.column); + } + + /** + * @param {ObjectDeserializerContext} context context + * @returns {RealDependencyLocation} location + */ + deserialize({ read }) { + return { + start: { + line: read(), + column: read() + }, + end: { + line: read(), + column: read() } - ); - }); - } -} + }; + } + })() +); -module.exports = WasmFinalizeExportsPlugin; +register( + Position, + CURRENT_MODULE, + "acorn/Position", + new (class PositionSerializer { + /** + * @param {Position} pos the position to be serialized + * @param {WebpackObjectSerializerContext} context context + * @returns {void} + */ + serialize(pos, { write }) { + write(pos.line); + write(pos.column); + } + + /** + * @param {ObjectDeserializerContext} context context + * @returns {SourcePosition} position + */ + deserialize({ read }) { + return { + line: read(), + column: read() + }; + } + })() +); + +register( + SourceMapSource, + CURRENT_MODULE, + "webpack-sources/SourceMapSource", + new (class SourceMapSourceSerializer { + /** + * @param {SourceMapSource} source the source map source to be serialized + * @param {WebpackObjectSerializerContext} context context + * @returns {void} + */ + serialize(source, { write }) { + write(source.getArgsAsBuffers()); + } + + /** + * @param {ObjectDeserializerContext} context context + * @returns {SourceMapSource} source source map source + */ + deserialize({ read }) { + // @ts-expect-error + return new SourceMapSource(...read()); + } + })() +); + +register( + ValidationError, + CURRENT_MODULE, + "schema-utils/ValidationError", + new (class ValidationErrorSerializer { + // TODO error should be ValidationError, but this fails the type checks + /** + * @param {TODO} error the source map source to be serialized + * @param {WebpackObjectSerializerContext} context context + * @returns {void} + */ + serialize(error, { write }) { + write(error.errors); + write(error.schema); + write({ + name: error.headerName, + baseDataPath: error.baseDataPath, + postFormatter: error.postFormatter + }); + } + + /** + * @param {ObjectDeserializerContext} context context + * @returns {TODO} error + */ + deserialize({ read }) { + return new ValidationError(read(), read(), read()); + } + })() +); /***/ }), -/***/ 35303: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { +/***/ 19655: +/***/ (function(__unused_webpack_module, exports, __webpack_require__) { "use strict"; /* @@ -132000,994 +131004,1249 @@ module.exports = WasmFinalizeExportsPlugin; -const { RawSource } = __webpack_require__(96192); -const Generator = __webpack_require__(1826); -const WebAssemblyUtils = __webpack_require__(41520); - -const t = __webpack_require__(98688); -const { moduleContextFromModuleAST } = __webpack_require__(98688); -const { editWithAST, addWithAST } = __webpack_require__(65584); -const { decode } = __webpack_require__(8062); - -const WebAssemblyExportImportedDependency = __webpack_require__(18248); - -/** @typedef {import("webpack-sources").Source} Source */ -/** @typedef {import("../DependencyTemplates")} DependencyTemplates */ -/** @typedef {import("../Generator").GenerateContext} GenerateContext */ -/** @typedef {import("../Module")} Module */ -/** @typedef {import("../ModuleGraph")} ModuleGraph */ -/** @typedef {import("../NormalModule")} NormalModule */ -/** @typedef {import("../RuntimeTemplate")} RuntimeTemplate */ -/** @typedef {import("../util/runtime").RuntimeSpec} RuntimeSpec */ -/** @typedef {import("./WebAssemblyUtils").UsedWasmDependency} UsedWasmDependency */ +const SortableSet = __webpack_require__(67563); -/** - * @typedef {(ArrayBuffer) => ArrayBuffer} ArrayBufferTransform - */ +/** @typedef {import("../Compilation")} Compilation */ +/** @typedef {import("../Entrypoint").EntryOptions} EntryOptions */ -/** - * @template T - * @param {Function[]} fns transforms - * @returns {Function} composed transform - */ -const compose = (...fns) => { - return fns.reduce( - (prevFn, nextFn) => { - return value => nextFn(prevFn(value)); - }, - value => value - ); -}; +/** @typedef {string | SortableSet | undefined} RuntimeSpec */ +/** @typedef {RuntimeSpec | boolean} RuntimeCondition */ /** - * Removes the start instruction - * - * @param {Object} state unused state - * @returns {ArrayBufferTransform} transform + * @param {Compilation} compilation the compilation + * @param {string} name name of the entry + * @param {EntryOptions=} options optionally already received entry options + * @returns {RuntimeSpec} runtime */ -const removeStartFunc = state => bin => { - return editWithAST(state.ast, bin, { - Start(path) { - path.remove(); +exports.getEntryRuntime = (compilation, name, options) => { + let dependOn; + let runtime; + if (options) { + ({ dependOn, runtime } = options); + } else { + const entry = compilation.entries.get(name); + if (!entry) return name; + ({ dependOn, runtime } = entry.options); + } + if (dependOn) { + /** @type {RuntimeSpec} */ + let result = undefined; + const queue = new Set(dependOn); + for (const name of queue) { + const dep = compilation.entries.get(name); + if (!dep) continue; + const { dependOn, runtime } = dep.options; + if (dependOn) { + for (const name of dependOn) { + queue.add(name); + } + } else { + result = mergeRuntimeOwned(result, runtime || name); + } } - }); + return result || name; + } else { + return runtime || name; + } }; /** - * Get imported globals - * - * @param {Object} ast Module's AST - * @returns {Array} - nodes + * @param {RuntimeSpec} runtime runtime + * @param {function(string): void} fn functor + * @param {boolean} deterministicOrder enforce a deterministic order + * @returns {void} */ -const getImportedGlobals = ast => { - const importedGlobals = []; - - t.traverse(ast, { - ModuleImport({ node }) { - if (t.isGlobalType(node.descr)) { - importedGlobals.push(node); - } +exports.forEachRuntime = (runtime, fn, deterministicOrder = false) => { + if (runtime === undefined) { + fn(undefined); + } else if (typeof runtime === "string") { + fn(runtime); + } else { + if (deterministicOrder) runtime.sort(); + for (const r of runtime) { + fn(r); } - }); + } +}; - return importedGlobals; +const getRuntimesKey = set => { + set.sort(); + return Array.from(set).join("\n"); }; /** - * Get the count for imported func - * - * @param {Object} ast Module's AST - * @returns {Number} - count + * @param {RuntimeSpec} runtime runtime(s) + * @returns {string} key of runtimes */ -const getCountImportedFunc = ast => { - let count = 0; - - t.traverse(ast, { - ModuleImport({ node }) { - if (t.isFuncImportDescr(node.descr)) { - count++; - } - } - }); - - return count; +const getRuntimeKey = runtime => { + if (runtime === undefined) return "*"; + if (typeof runtime === "string") return runtime; + return runtime.getFromUnorderedCache(getRuntimesKey); }; +exports.getRuntimeKey = getRuntimeKey; /** - * Get next type index - * - * @param {Object} ast Module's AST - * @returns {t.Index} - index + * @param {string} key key of runtimes + * @returns {RuntimeSpec} runtime(s) */ -const getNextTypeIndex = ast => { - const typeSectionMetadata = t.getSectionMetadata(ast, "type"); +const keyToRuntime = key => { + if (key === "*") return undefined; + const items = key.split("\n"); + if (items.length === 1) return items[0]; + return new SortableSet(items); +}; +exports.keyToRuntime = keyToRuntime; - if (typeSectionMetadata === undefined) { - return t.indexLiteral(0); - } +const getRuntimesString = set => { + set.sort(); + return Array.from(set).join("+"); +}; - return t.indexLiteral(typeSectionMetadata.vectorOfSize.value); +/** + * @param {RuntimeSpec} runtime runtime(s) + * @returns {string} readable version + */ +const runtimeToString = runtime => { + if (runtime === undefined) return "*"; + if (typeof runtime === "string") return runtime; + return runtime.getFromUnorderedCache(getRuntimesString); }; +exports.runtimeToString = runtimeToString; /** - * Get next func index - * - * The Func section metadata provide informations for implemented funcs - * in order to have the correct index we shift the index by number of external - * functions. - * - * @param {Object} ast Module's AST - * @param {Number} countImportedFunc number of imported funcs - * @returns {t.Index} - index + * @param {RuntimeCondition} runtimeCondition runtime condition + * @returns {string} readable version */ -const getNextFuncIndex = (ast, countImportedFunc) => { - const funcSectionMetadata = t.getSectionMetadata(ast, "func"); +exports.runtimeConditionToString = runtimeCondition => { + if (runtimeCondition === true) return "true"; + if (runtimeCondition === false) return "false"; + return runtimeToString(runtimeCondition); +}; - if (funcSectionMetadata === undefined) { - return t.indexLiteral(0 + countImportedFunc); +/** + * @param {RuntimeSpec} a first + * @param {RuntimeSpec} b second + * @returns {boolean} true, when they are equal + */ +const runtimeEqual = (a, b) => { + if (a === b) { + return true; + } else if ( + a === undefined || + b === undefined || + typeof a === "string" || + typeof b === "string" + ) { + return false; + } else if (a.size !== b.size) { + return false; + } else { + a.sort(); + b.sort(); + const aIt = a[Symbol.iterator](); + const bIt = b[Symbol.iterator](); + for (;;) { + const aV = aIt.next(); + if (aV.done) return true; + const bV = bIt.next(); + if (aV.value !== bV.value) return false; + } } - - const vectorOfSize = funcSectionMetadata.vectorOfSize.value; - - return t.indexLiteral(vectorOfSize + countImportedFunc); }; +exports.runtimeEqual = runtimeEqual; /** - * Creates an init instruction for a global type - * @param {t.GlobalType} globalType the global type - * @returns {t.Instruction} init expression + * @param {RuntimeSpec} a first + * @param {RuntimeSpec} b second + * @returns {-1|0|1} compare */ -const createDefaultInitForGlobal = globalType => { - if (globalType.valtype[0] === "i") { - // create NumberLiteral global initializer - return t.objectInstruction("const", globalType.valtype, [ - t.numberLiteralFromRaw(66) - ]); - } else if (globalType.valtype[0] === "f") { - // create FloatLiteral global initializer - return t.objectInstruction("const", globalType.valtype, [ - t.floatLiteral(66, false, false, "66") - ]); +exports.compareRuntime = (a, b) => { + if (a === b) { + return 0; + } else if (a === undefined) { + return -1; + } else if (b === undefined) { + return 1; } else { - throw new Error("unknown type: " + globalType.valtype); + const aKey = getRuntimeKey(a); + const bKey = getRuntimeKey(b); + if (aKey < bKey) return -1; + if (aKey > bKey) return 1; + return 0; } }; /** - * Rewrite the import globals: - * - removes the ModuleImport instruction - * - injects at the same offset a mutable global of the same type - * - * Since the imported globals are before the other global declarations, our - * indices will be preserved. - * - * Note that globals will become mutable. - * - * @param {Object} state unused state - * @returns {ArrayBufferTransform} transform + * @param {RuntimeSpec} a first + * @param {RuntimeSpec} b second + * @returns {RuntimeSpec} merged */ -const rewriteImportedGlobals = state => bin => { - const additionalInitCode = state.additionalInitCode; - const newGlobals = []; - - bin = editWithAST(state.ast, bin, { - ModuleImport(path) { - if (t.isGlobalType(path.node.descr)) { - const globalType = path.node.descr; - - globalType.mutability = "var"; - - const init = [ - createDefaultInitForGlobal(globalType), - t.instruction("end") - ]; - - newGlobals.push(t.global(globalType, init)); - - path.remove(); - } - }, - - // in order to preserve non-imported global's order we need to re-inject - // those as well - Global(path) { - const { node } = path; - const [init] = node.init; - - if (init.id === "get_global") { - node.globalType.mutability = "var"; - - const initialGlobalIdx = init.args[0]; - - node.init = [ - createDefaultInitForGlobal(node.globalType), - t.instruction("end") - ]; - - additionalInitCode.push( - /** - * get_global in global initializer only works for imported globals. - * They have the same indices as the init params, so use the - * same index. - */ - t.instruction("get_local", [initialGlobalIdx]), - t.instruction("set_global", [t.indexLiteral(newGlobals.length)]) - ); - } - - newGlobals.push(node); - - path.remove(); +const mergeRuntime = (a, b) => { + if (a === undefined) { + return b; + } else if (b === undefined) { + return a; + } else if (a === b) { + return a; + } else if (typeof a === "string") { + if (typeof b === "string") { + const set = new SortableSet(); + set.add(a); + set.add(b); + return set; + } else if (b.has(a)) { + return b; + } else { + const set = new SortableSet(b); + set.add(a); + return set; } - }); - - // Add global declaration instructions - return addWithAST(state.ast, bin, newGlobals); + } else { + if (typeof b === "string") { + if (a.has(b)) return a; + const set = new SortableSet(a); + set.add(b); + return set; + } else { + const set = new SortableSet(a); + for (const item of b) set.add(item); + if (set.size === a.size) return a; + return set; + } + } }; +exports.mergeRuntime = mergeRuntime; /** - * Rewrite the export names - * @param {Object} state state - * @param {Object} state.ast Module's ast - * @param {Module} state.module Module - * @param {ModuleGraph} state.moduleGraph module graph - * @param {Set} state.externalExports Module - * @param {RuntimeSpec} state.runtime runtime - * @returns {ArrayBufferTransform} transform + * @param {RuntimeCondition} a first + * @param {RuntimeCondition} b second + * @param {RuntimeSpec} runtime full runtime + * @returns {RuntimeCondition} result */ -const rewriteExportNames = - ({ ast, moduleGraph, module, externalExports, runtime }) => - bin => { - return editWithAST(ast, bin, { - ModuleExport(path) { - const isExternal = externalExports.has(path.node.name); - if (isExternal) { - path.remove(); - return; - } - const usedName = moduleGraph - .getExportsInfo(module) - .getUsedName(path.node.name, runtime); - if (!usedName) { - path.remove(); - return; - } - path.node.name = usedName; - } - }); - }; +exports.mergeRuntimeCondition = (a, b, runtime) => { + if (a === false) return b; + if (b === false) return a; + if (a === true || b === true) return true; + const merged = mergeRuntime(a, b); + if (merged === undefined) return undefined; + if (typeof merged === "string") { + if (typeof runtime === "string" && merged === runtime) return true; + return merged; + } + if (typeof runtime === "string" || runtime === undefined) return merged; + if (merged.size === runtime.size) return true; + return merged; +}; /** - * Mangle import names and modules - * @param {Object} state state - * @param {Object} state.ast Module's ast - * @param {Map} state.usedDependencyMap mappings to mangle names - * @returns {ArrayBufferTransform} transform + * @param {RuntimeSpec | true} a first + * @param {RuntimeSpec | true} b second + * @param {RuntimeSpec} runtime full runtime + * @returns {RuntimeSpec | true} result */ -const rewriteImports = - ({ ast, usedDependencyMap }) => - bin => { - return editWithAST(ast, bin, { - ModuleImport(path) { - const result = usedDependencyMap.get( - path.node.module + ":" + path.node.name - ); - - if (result !== undefined) { - path.node.module = result.module; - path.node.name = result.name; - } - } - }); - }; +exports.mergeRuntimeConditionNonFalse = (a, b, runtime) => { + if (a === true || b === true) return true; + const merged = mergeRuntime(a, b); + if (merged === undefined) return undefined; + if (typeof merged === "string") { + if (typeof runtime === "string" && merged === runtime) return true; + return merged; + } + if (typeof runtime === "string" || runtime === undefined) return merged; + if (merged.size === runtime.size) return true; + return merged; +}; /** - * Add an init function. - * - * The init function fills the globals given input arguments. - * - * @param {Object} state transformation state - * @param {Object} state.ast Module's ast - * @param {t.Identifier} state.initFuncId identifier of the init function - * @param {t.Index} state.startAtFuncOffset index of the start function - * @param {t.ModuleImport[]} state.importedGlobals list of imported globals - * @param {t.Instruction[]} state.additionalInitCode list of addition instructions for the init function - * @param {t.Index} state.nextFuncIndex index of the next function - * @param {t.Index} state.nextTypeIndex index of the next type - * @returns {ArrayBufferTransform} transform + * @param {RuntimeSpec} a first (may be modified) + * @param {RuntimeSpec} b second + * @returns {RuntimeSpec} merged */ -const addInitFunction = - ({ - ast, - initFuncId, - startAtFuncOffset, - importedGlobals, - additionalInitCode, - nextFuncIndex, - nextTypeIndex - }) => - bin => { - const funcParams = importedGlobals.map(importedGlobal => { - // used for debugging - const id = t.identifier( - `${importedGlobal.module}.${importedGlobal.name}` - ); - - return t.funcParam(importedGlobal.descr.valtype, id); - }); - - const funcBody = []; - importedGlobals.forEach((importedGlobal, index) => { - const args = [t.indexLiteral(index)]; - const body = [ - t.instruction("get_local", args), - t.instruction("set_global", args) - ]; - - funcBody.push(...body); - }); - - if (typeof startAtFuncOffset === "number") { - funcBody.push( - t.callInstruction(t.numberLiteralFromRaw(startAtFuncOffset)) - ); +const mergeRuntimeOwned = (a, b) => { + if (b === undefined) { + return a; + } else if (a === b) { + return a; + } else if (a === undefined) { + if (typeof b === "string") { + return b; + } else { + return new SortableSet(b); } - - for (const instr of additionalInitCode) { - funcBody.push(instr); + } else if (typeof a === "string") { + if (typeof b === "string") { + const set = new SortableSet(); + set.add(a); + set.add(b); + return set; + } else { + const set = new SortableSet(b); + set.add(a); + return set; } + } else { + if (typeof b === "string") { + a.add(b); + return a; + } else { + for (const item of b) a.add(item); + return a; + } + } +}; +exports.mergeRuntimeOwned = mergeRuntimeOwned; - funcBody.push(t.instruction("end")); - - const funcResults = []; - - // Code section - const funcSignature = t.signature(funcParams, funcResults); - const func = t.func(initFuncId, funcSignature, funcBody); - - // Type section - const functype = t.typeInstruction(undefined, funcSignature); - - // Func section - const funcindex = t.indexInFuncSection(nextTypeIndex); - - // Export section - const moduleExport = t.moduleExport( - initFuncId.value, - t.moduleExportDescr("Func", nextFuncIndex) - ); - - return addWithAST(ast, bin, [func, moduleExport, funcindex, functype]); - }; +/** + * @param {RuntimeSpec} a first + * @param {RuntimeSpec} b second + * @returns {RuntimeSpec} merged + */ +exports.intersectRuntime = (a, b) => { + if (a === undefined) { + return b; + } else if (b === undefined) { + return a; + } else if (a === b) { + return a; + } else if (typeof a === "string") { + if (typeof b === "string") { + return undefined; + } else if (b.has(a)) { + return a; + } else { + return undefined; + } + } else { + if (typeof b === "string") { + if (a.has(b)) return b; + return undefined; + } else { + const set = new SortableSet(); + for (const item of b) { + if (a.has(item)) set.add(item); + } + if (set.size === 0) return undefined; + if (set.size === 1) for (const item of set) return item; + return set; + } + } +}; /** - * Extract mangle mappings from module - * @param {ModuleGraph} moduleGraph module graph - * @param {Module} module current module - * @param {boolean} mangle mangle imports - * @returns {Map} mappings to mangled names + * @param {RuntimeSpec} a first + * @param {RuntimeSpec} b second + * @returns {RuntimeSpec} result */ -const getUsedDependencyMap = (moduleGraph, module, mangle) => { - /** @type {Map} */ - const map = new Map(); - for (const usedDep of WebAssemblyUtils.getUsedDependencies( - moduleGraph, - module, - mangle - )) { - const dep = usedDep.dependency; - const request = dep.request; - const exportName = dep.name; - map.set(request + ":" + exportName, usedDep); +const subtractRuntime = (a, b) => { + if (a === undefined) { + return undefined; + } else if (b === undefined) { + return a; + } else if (a === b) { + return undefined; + } else if (typeof a === "string") { + if (typeof b === "string") { + return a; + } else if (b.has(a)) { + return undefined; + } else { + return a; + } + } else { + if (typeof b === "string") { + if (!a.has(b)) return a; + if (a.size === 2) { + for (const item of a) { + if (item !== b) return item; + } + } + const set = new SortableSet(a); + set.delete(b); + } else { + const set = new SortableSet(); + for (const item of a) { + if (!b.has(item)) set.add(item); + } + if (set.size === 0) return undefined; + if (set.size === 1) for (const item of set) return item; + return set; + } } - return map; }; +exports.subtractRuntime = subtractRuntime; -const TYPES = new Set(["webassembly"]); +/** + * @param {RuntimeCondition} a first + * @param {RuntimeCondition} b second + * @param {RuntimeSpec} runtime runtime + * @returns {RuntimeCondition} result + */ +exports.subtractRuntimeCondition = (a, b, runtime) => { + if (b === true) return false; + if (b === false) return a; + if (a === false) return false; + const result = subtractRuntime(a === true ? runtime : a, b); + return result === undefined ? false : result; +}; -class WebAssemblyGenerator extends Generator { - constructor(options) { - super(); - this.options = options; +/** + * @param {RuntimeSpec} runtime runtime + * @param {function(RuntimeSpec): boolean} filter filter function + * @returns {boolean | RuntimeSpec} true/false if filter is constant for all runtimes, otherwise runtimes that are active + */ +exports.filterRuntime = (runtime, filter) => { + if (runtime === undefined) return filter(undefined); + if (typeof runtime === "string") return filter(runtime); + let some = false; + let every = true; + let result = undefined; + for (const r of runtime) { + const v = filter(r); + if (v) { + some = true; + result = mergeRuntimeOwned(result, r); + } else { + every = false; + } } + if (!some) return false; + if (every) return true; + return result; +}; +/** + * @template T + */ +class RuntimeSpecMap { /** - * @param {NormalModule} module fresh module - * @returns {Set} available types (do not mutate) + * @param {RuntimeSpecMap=} clone copy form this */ - getTypes(module) { - return TYPES; + constructor(clone) { + this._mode = clone ? clone._mode : 0; // 0 = empty, 1 = single entry, 2 = map + /** @type {RuntimeSpec} */ + this._singleRuntime = clone ? clone._singleRuntime : undefined; + /** @type {T} */ + this._singleValue = clone ? clone._singleValue : undefined; + /** @type {Map | undefined} */ + this._map = clone && clone._map ? new Map(clone._map) : undefined; } /** - * @param {NormalModule} module the module - * @param {string=} type source type - * @returns {number} estimate size of the module + * @param {RuntimeSpec} runtime the runtimes + * @returns {T} value */ - getSize(module, type) { - const originalSource = module.originalSource(); - if (!originalSource) { - return 0; + get(runtime) { + switch (this._mode) { + case 0: + return undefined; + case 1: + return runtimeEqual(this._singleRuntime, runtime) + ? this._singleValue + : undefined; + default: + return this._map.get(getRuntimeKey(runtime)); } - return originalSource.size(); } /** - * @param {NormalModule} module module for which the code should be generated - * @param {GenerateContext} generateContext context for generate - * @returns {Source} generated code + * @param {RuntimeSpec} runtime the runtimes + * @returns {boolean} true, when the runtime is stored */ - generate(module, { moduleGraph, runtime }) { - const bin = module.originalSource().source(); - - const initFuncId = t.identifier(""); + has(runtime) { + switch (this._mode) { + case 0: + return false; + case 1: + return runtimeEqual(this._singleRuntime, runtime); + default: + return this._map.has(getRuntimeKey(runtime)); + } + } - // parse it - const ast = decode(bin, { - ignoreDataSection: true, - ignoreCodeSection: true, - ignoreCustomNameSection: true - }); + set(runtime, value) { + switch (this._mode) { + case 0: + this._mode = 1; + this._singleRuntime = runtime; + this._singleValue = value; + break; + case 1: + if (runtimeEqual(this._singleRuntime, runtime)) { + this._singleValue = value; + break; + } + this._mode = 2; + this._map = new Map(); + this._map.set(getRuntimeKey(this._singleRuntime), this._singleValue); + this._singleRuntime = undefined; + this._singleValue = undefined; + /* falls through */ + default: + this._map.set(getRuntimeKey(runtime), value); + } + } - const moduleContext = moduleContextFromModuleAST(ast.body[0]); + provide(runtime, computer) { + switch (this._mode) { + case 0: + this._mode = 1; + this._singleRuntime = runtime; + return (this._singleValue = computer()); + case 1: { + if (runtimeEqual(this._singleRuntime, runtime)) { + return this._singleValue; + } + this._mode = 2; + this._map = new Map(); + this._map.set(getRuntimeKey(this._singleRuntime), this._singleValue); + this._singleRuntime = undefined; + this._singleValue = undefined; + const newValue = computer(); + this._map.set(getRuntimeKey(runtime), newValue); + return newValue; + } + default: { + const key = getRuntimeKey(runtime); + const value = this._map.get(key); + if (value !== undefined) return value; + const newValue = computer(); + this._map.set(key, newValue); + return newValue; + } + } + } - const importedGlobals = getImportedGlobals(ast); - const countImportedFunc = getCountImportedFunc(ast); - const startAtFuncOffset = moduleContext.getStart(); - const nextFuncIndex = getNextFuncIndex(ast, countImportedFunc); - const nextTypeIndex = getNextTypeIndex(ast); + delete(runtime) { + switch (this._mode) { + case 0: + return; + case 1: + if (runtimeEqual(this._singleRuntime, runtime)) { + this._mode = 0; + this._singleRuntime = undefined; + this._singleValue = undefined; + } + return; + default: + this._map.delete(getRuntimeKey(runtime)); + } + } - const usedDependencyMap = getUsedDependencyMap( - moduleGraph, - module, - this.options.mangleImports - ); - const externalExports = new Set( - module.dependencies - .filter(d => d instanceof WebAssemblyExportImportedDependency) - .map(d => { - const wasmDep = /** @type {WebAssemblyExportImportedDependency} */ ( - d - ); - return wasmDep.exportName; - }) - ); + update(runtime, fn) { + switch (this._mode) { + case 0: + throw new Error("runtime passed to update must exist"); + case 1: { + if (runtimeEqual(this._singleRuntime, runtime)) { + this._singleValue = fn(this._singleValue); + break; + } + const newValue = fn(undefined); + if (newValue !== undefined) { + this._mode = 2; + this._map = new Map(); + this._map.set(getRuntimeKey(this._singleRuntime), this._singleValue); + this._singleRuntime = undefined; + this._singleValue = undefined; + this._map.set(getRuntimeKey(runtime), newValue); + } + break; + } + default: { + const key = getRuntimeKey(runtime); + const oldValue = this._map.get(key); + const newValue = fn(oldValue); + if (newValue !== oldValue) this._map.set(key, newValue); + } + } + } - /** @type {t.Instruction[]} */ - const additionalInitCode = []; + keys() { + switch (this._mode) { + case 0: + return []; + case 1: + return [this._singleRuntime]; + default: + return Array.from(this._map.keys(), keyToRuntime); + } + } - const transform = compose( - rewriteExportNames({ - ast, - moduleGraph, - module, - externalExports, - runtime - }), + values() { + switch (this._mode) { + case 0: + return [][Symbol.iterator](); + case 1: + return [this._singleValue][Symbol.iterator](); + default: + return this._map.values(); + } + } - removeStartFunc({ ast }), + get size() { + if (this._mode <= 1) return this._mode; + return this._map.size; + } +} - rewriteImportedGlobals({ ast, additionalInitCode }), +exports.RuntimeSpecMap = RuntimeSpecMap; - rewriteImports({ - ast, - usedDependencyMap - }), +class RuntimeSpecSet { + constructor(iterable) { + /** @type {Map} */ + this._map = new Map(); + if (iterable) { + for (const item of iterable) { + this.add(item); + } + } + } - addInitFunction({ - ast, - initFuncId, - importedGlobals, - additionalInitCode, - startAtFuncOffset, - nextFuncIndex, - nextTypeIndex - }) - ); + add(runtime) { + this._map.set(getRuntimeKey(runtime), runtime); + } - const newBin = transform(bin); + has(runtime) { + return this._map.has(getRuntimeKey(runtime)); + } - const newBuf = Buffer.from(newBin); + [Symbol.iterator]() { + return this._map.values(); + } - return new RawSource(newBuf); + get size() { + return this._map.size; } } -module.exports = WebAssemblyGenerator; +exports.RuntimeSpecSet = RuntimeSpecSet; /***/ }), -/***/ 14073: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { +/***/ 60473: +/***/ (function(__unused_webpack_module, exports) { "use strict"; /* MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra */ -const WebpackError = __webpack_require__(68422); +/** @typedef {(string|number|undefined|[])[]} SemVerRange */ -/** @typedef {import("../ChunkGraph")} ChunkGraph */ -/** @typedef {import("../Module")} Module */ -/** @typedef {import("../ModuleGraph")} ModuleGraph */ -/** @typedef {import("../RequestShortener")} RequestShortener */ +/** + * @param {string} str version string + * @returns {(string|number|undefined|[])[]} parsed version + */ +const parseVersion = str => { + var splitAndConvert = function (str) { + return str.split(".").map(function (item) { + // eslint-disable-next-line eqeqeq + return +item == item ? +item : item; + }); + }; + var match = /^([^-+]+)?(?:-([^+]+))?(?:\+(.+))?$/.exec(str); + /** @type {(string|number|undefined|[])[]} */ + var ver = match[1] ? splitAndConvert(match[1]) : []; + if (match[2]) { + ver.length++; + ver.push.apply(ver, splitAndConvert(match[2])); + } + if (match[3]) { + ver.push([]); + ver.push.apply(ver, splitAndConvert(match[3])); + } + return ver; +}; +exports.parseVersion = parseVersion; +/* eslint-disable eqeqeq */ /** - * @param {Module} module module to get chains from - * @param {ModuleGraph} moduleGraph the module graph - * @param {ChunkGraph} chunkGraph the chunk graph - * @param {RequestShortener} requestShortener to make readable identifiers - * @returns {string[]} all chains to the module + * @param {string} a version + * @param {string} b version + * @returns {boolean} true, iff a < b */ -const getInitialModuleChains = ( - module, - moduleGraph, - chunkGraph, - requestShortener -) => { - const queue = [ - { head: module, message: module.readableIdentifier(requestShortener) } - ]; - /** @type {Set} */ - const results = new Set(); - /** @type {Set} */ - const incompleteResults = new Set(); - /** @type {Set} */ - const visitedModules = new Set(); +const versionLt = (a, b) => { + // @ts-expect-error + a = parseVersion(a); + // @ts-expect-error + b = parseVersion(b); + var i = 0; + for (;;) { + // a b EOA object undefined number string + // EOA a == b a < b b < a a < b a < b + // object b < a (0) b < a a < b a < b + // undefined a < b a < b (0) a < b a < b + // number b < a b < a b < a (1) a < b + // string b < a b < a b < a b < a (1) + // EOA end of array + // (0) continue on + // (1) compare them via "<" - for (const chain of queue) { - const { head, message } = chain; - let final = true; - /** @type {Set} */ - const alreadyReferencedModules = new Set(); - for (const connection of moduleGraph.getIncomingConnections(head)) { - const newHead = connection.originModule; - if (newHead) { - if (!chunkGraph.getModuleChunks(newHead).some(c => c.canBeInitial())) - continue; - final = false; - if (alreadyReferencedModules.has(newHead)) continue; - alreadyReferencedModules.add(newHead); - const moduleName = newHead.readableIdentifier(requestShortener); - const detail = connection.explanation - ? ` (${connection.explanation})` - : ""; - const newMessage = `${moduleName}${detail} --> ${message}`; - if (visitedModules.has(newHead)) { - incompleteResults.add(`... --> ${newMessage}`); - continue; + // Handles first row in table + if (i >= a.length) return i < b.length && (typeof b[i])[0] != "u"; + + var aValue = a[i]; + var aType = (typeof aValue)[0]; + + // Handles first column in table + if (i >= b.length) return aType == "u"; + + var bValue = b[i]; + var bType = (typeof bValue)[0]; + + if (aType == bType) { + if (aType != "o" && aType != "u" && aValue != bValue) { + return aValue < bValue; + } + i++; + } else { + // Handles remaining cases + if (aType == "o" && bType == "n") return true; + return bType == "s" || aType == "u"; + } + } +}; +/* eslint-enable eqeqeq */ +exports.versionLt = versionLt; + +/** + * @param {string} str range string + * @returns {SemVerRange} parsed range + */ +exports.parseRange = str => { + const splitAndConvert = str => { + return str.split(".").map(item => (`${+item}` === item ? +item : item)); + }; + // see https://docs.npmjs.com/misc/semver#range-grammar for grammar + const parsePartial = str => { + const match = /^([^-+]+)?(?:-([^+]+))?(?:\+(.+))?$/.exec(str); + /** @type {(string|number|undefined|[])[]} */ + const ver = match[1] ? [0, ...splitAndConvert(match[1])] : [0]; + if (match[2]) { + ver.length++; + ver.push.apply(ver, splitAndConvert(match[2])); + } + + // remove trailing any matchers + let last = ver[ver.length - 1]; + while ( + ver.length && + (last === undefined || /^[*xX]$/.test(/** @type {string} */ (last))) + ) { + ver.pop(); + last = ver[ver.length - 1]; + } + + return ver; + }; + const toFixed = range => { + if (range.length === 1) { + // Special case for "*" is "x.x.x" instead of "=" + return [0]; + } else if (range.length === 2) { + // Special case for "1" is "1.x.x" instead of "=1" + return [1, ...range.slice(1)]; + } else if (range.length === 3) { + // Special case for "1.2" is "1.2.x" instead of "=1.2" + return [2, ...range.slice(1)]; + } else { + return [range.length, ...range.slice(1)]; + } + }; + const negate = range => { + return [-range[0] - 1, ...range.slice(1)]; + }; + const parseSimple = str => { + // simple ::= primitive | partial | tilde | caret + // primitive ::= ( '<' | '>' | '>=' | '<=' | '=' ) partial + // tilde ::= '~' partial + // caret ::= '^' partial + const match = /^(\^|~|<=|<|>=|>|=|v|!)/.exec(str); + const start = match ? match[0] : ""; + const remainder = parsePartial(str.slice(start.length)); + switch (start) { + case "^": + if (remainder.length > 1 && remainder[1] === 0) { + if (remainder.length > 2 && remainder[2] === 0) { + return [3, ...remainder.slice(1)]; + } + return [2, ...remainder.slice(1)]; } - visitedModules.add(newHead); - queue.push({ - head: newHead, - message: newMessage - }); + return [1, ...remainder.slice(1)]; + case "~": + return [2, ...remainder.slice(1)]; + case ">=": + return remainder; + case "=": + case "v": + case "": + return toFixed(remainder); + case "<": + return negate(remainder); + case ">": { + // and( >=, not( = ) ) => >=, =, not, and + const fixed = toFixed(remainder); + // eslint-disable-next-line no-sparse-arrays + return [, fixed, 0, remainder, 2]; + } + case "<=": + // or( <, = ) => <, =, or + // eslint-disable-next-line no-sparse-arrays + return [, toFixed(remainder), negate(remainder), 1]; + case "!": { + // not = + const fixed = toFixed(remainder); + // eslint-disable-next-line no-sparse-arrays + return [, fixed, 0]; + } + default: + throw new Error("Unexpected start value"); + } + }; + const combine = (items, fn) => { + if (items.length === 1) return items[0]; + const arr = []; + for (const item of items.slice().reverse()) { + if (0 in item) { + arr.push(item); } else { - final = false; - const newMessage = connection.explanation - ? `(${connection.explanation}) --> ${message}` - : message; - results.add(newMessage); + arr.push(...item.slice(1)); } } - if (final) { - results.add(message); + // eslint-disable-next-line no-sparse-arrays + return [, ...arr, ...items.slice(1).map(() => fn)]; + }; + const parseRange = str => { + // range ::= hyphen | simple ( ' ' simple ) * | '' + // hyphen ::= partial ' - ' partial + const items = str.split(" - "); + if (items.length === 1) { + const items = str.trim().split(/\s+/g).map(parseSimple); + return combine(items, 2); } - } - for (const result of incompleteResults) { - results.add(result); - } - return Array.from(results); + const a = parsePartial(items[0]); + const b = parsePartial(items[1]); + // >=a <=b => and( >=a, or( >=a, { + // range-set ::= range ( logical-or range ) * + // logical-or ::= ( ' ' ) * '||' ( ' ' ) * + const items = str.split(/\s*\|\|\s*/).map(parseRange); + return combine(items, 1); + }; + return parseLogicalOr(str); }; -module.exports = class WebAssemblyInInitialChunkError extends WebpackError { - /** - * @param {Module} module WASM module - * @param {ModuleGraph} moduleGraph the module graph - * @param {ChunkGraph} chunkGraph the chunk graph - * @param {RequestShortener} requestShortener request shortener - */ - constructor(module, moduleGraph, chunkGraph, requestShortener) { - const moduleChains = getInitialModuleChains( - module, - moduleGraph, - chunkGraph, - requestShortener - ); - const message = `WebAssembly module is included in initial chunk. -This is not allowed, because WebAssembly download and compilation must happen asynchronous. -Add an async split point (i. e. import()) somewhere between your entrypoint and the WebAssembly module: -${moduleChains.map(s => `* ${s}`).join("\n")}`; - - super(message); - this.name = "WebAssemblyInInitialChunkError"; - this.hideStack = true; - this.module = module; +/* eslint-disable eqeqeq */ +const rangeToString = range => { + var fixCount = range[0]; + var str = ""; + if (range.length === 1) { + return "*"; + } else if (fixCount + 0.5) { + str += + fixCount == 0 + ? ">=" + : fixCount == -1 + ? "<" + : fixCount == 1 + ? "^" + : fixCount == 2 + ? "~" + : fixCount > 0 + ? "=" + : "!="; + var needDot = 1; + // eslint-disable-next-line no-redeclare + for (var i = 1; i < range.length; i++) { + var item = range[i]; + var t = (typeof item)[0]; + needDot--; + str += + t == "u" + ? // undefined: prerelease marker, add an "-" + "-" + : // number or string: add the item, set flag to add an "." between two of them + (needDot > 0 ? "." : "") + ((needDot = 2), item); + } + return str; + } else { + var stack = []; + // eslint-disable-next-line no-redeclare + for (var i = 1; i < range.length; i++) { + // eslint-disable-next-line no-redeclare + var item = range[i]; + stack.push( + item === 0 + ? "not(" + pop() + ")" + : item === 1 + ? "(" + pop() + " || " + pop() + ")" + : item === 2 + ? stack.pop() + " " + stack.pop() + : rangeToString(item) + ); + } + return pop(); + } + function pop() { + return stack.pop().replace(/^\((.+)\)$/, "$1"); } }; +/* eslint-enable eqeqeq */ +exports.rangeToString = rangeToString; +/* eslint-disable eqeqeq */ +/** + * @param {SemVerRange} range version range + * @param {string} version the version + * @returns {boolean} if version satisfy the range + */ +const satisfy = (range, version) => { + if (0 in range) { + // @ts-expect-error + version = parseVersion(version); + var fixCount = range[0]; + // when negated is set it swill set for < instead of >= + var negated = fixCount < 0; + if (negated) fixCount = -fixCount - 1; + for (var i = 0, j = 1, isEqual = true; ; j++, i++) { + // cspell:word nequal nequ -/***/ }), - -/***/ 88890: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ - - - -const { RawSource } = __webpack_require__(96192); -const { UsageState } = __webpack_require__(4295); -const Generator = __webpack_require__(1826); -const InitFragment = __webpack_require__(51739); -const RuntimeGlobals = __webpack_require__(49404); -const Template = __webpack_require__(92066); -const ModuleDependency = __webpack_require__(80944); -const WebAssemblyExportImportedDependency = __webpack_require__(18248); -const WebAssemblyImportDependency = __webpack_require__(97093); - -/** @typedef {import("webpack-sources").Source} Source */ -/** @typedef {import("../Dependency")} Dependency */ -/** @typedef {import("../DependencyTemplates")} DependencyTemplates */ -/** @typedef {import("../Generator").GenerateContext} GenerateContext */ -/** @typedef {import("../NormalModule")} NormalModule */ -/** @typedef {import("../RuntimeTemplate")} RuntimeTemplate */ + // when isEqual = true: + // range version: EOA/object undefined number string + // EOA equal block big-ver big-ver + // undefined bigger next big-ver big-ver + // number smaller block cmp big-cmp + // fixed number smaller block cmp-fix differ + // string smaller block differ cmp + // fixed string smaller block small-cmp cmp-fix -const TYPES = new Set(["webassembly"]); + // when isEqual = false: + // range version: EOA/object undefined number string + // EOA nequal block next-ver next-ver + // undefined nequal block next-ver next-ver + // number nequal block next next + // fixed number nequal block next next (this never happens) + // string nequal block next next + // fixed string nequal block next next (this never happens) -class WebAssemblyJavascriptGenerator extends Generator { - /** - * @param {NormalModule} module fresh module - * @returns {Set} available types (do not mutate) - */ - getTypes(module) { - return TYPES; - } + // EOA end of array + // equal (version is equal range): + // when !negated: return true, + // when negated: return false + // bigger (version is bigger as range): + // when fixed: return false, + // when !negated: return true, + // when negated: return false, + // smaller (version is smaller as range): + // when !negated: return false, + // when negated: return true + // nequal (version is not equal range (> resp <)): return true + // block (version is in different prerelease area): return false + // differ (version is different from fixed range (string vs. number)): return false + // next: continues to the next items + // next-ver: when fixed: return false, continues to the next item only for the version, sets isEqual=false + // big-ver: when fixed || negated: return false, continues to the next item only for the version, sets isEqual=false + // next-nequ: continues to the next items, sets isEqual=false + // cmp (negated === false): version < range => return false, version > range => next-nequ, else => next + // cmp (negated === true): version > range => return false, version < range => next-nequ, else => next + // cmp-fix: version == range => next, else => return false + // big-cmp: when negated => return false, else => next-nequ + // small-cmp: when negated => next-nequ, else => return false - /** - * @param {NormalModule} module the module - * @param {string=} type source type - * @returns {number} estimate size of the module - */ - getSize(module, type) { - return 95 + module.dependencies.length * 5; - } + var rangeType = j < range.length ? (typeof range[j])[0] : ""; - /** - * @param {NormalModule} module module for which the code should be generated - * @param {GenerateContext} generateContext context for generate - * @returns {Source} generated code - */ - generate(module, generateContext) { - const { - runtimeTemplate, - moduleGraph, - chunkGraph, - runtimeRequirements, - runtime - } = generateContext; - /** @type {InitFragment[]} */ - const initFragments = []; + var versionValue; + var versionType; - const exportsInfo = moduleGraph.getExportsInfo(module); + // Handles first column in both tables (end of version or object) + if ( + i >= version.length || + ((versionValue = version[i]), + (versionType = (typeof versionValue)[0]) == "o") + ) { + // Handles nequal + if (!isEqual) return true; + // Handles bigger + if (rangeType == "u") return j > fixCount && !negated; + // Handles equal and smaller: (range === EOA) XOR negated + return (rangeType == "") != negated; // equal + smaller + } - let needExportsCopy = false; - const importedModules = new Map(); - const initParams = []; - let index = 0; - for (const dep of module.dependencies) { - const moduleDep = - dep && dep instanceof ModuleDependency ? dep : undefined; - if (moduleGraph.getModule(dep)) { - let importData = importedModules.get(moduleGraph.getModule(dep)); - if (importData === undefined) { - importedModules.set( - moduleGraph.getModule(dep), - (importData = { - importVar: `m${index}`, - index, - request: (moduleDep && moduleDep.userRequest) || undefined, - names: new Set(), - reexports: [] - }) - ); - index++; + // Handles second column in both tables (version = undefined) + if (versionType == "u") { + if (!isEqual || rangeType != "u") { + return false; } - if (dep instanceof WebAssemblyImportDependency) { - importData.names.add(dep.name); - if (dep.description.type === "GlobalType") { - const exportName = dep.name; - const importedModule = moduleGraph.getModule(dep); + } - if (importedModule) { - const usedName = moduleGraph - .getExportsInfo(importedModule) - .getUsedName(exportName, runtime); - if (usedName) { - initParams.push( - runtimeTemplate.exportFromImport({ - moduleGraph, - module: importedModule, - request: dep.request, - importVar: importData.importVar, - originModule: module, - exportName: dep.name, - asiSafe: true, - isCall: false, - callContext: null, - defaultInterop: true, - initFragments, - runtime, - runtimeRequirements - }) - ); - } + // switch between first and second table + else if (isEqual) { + // Handle diagonal + if (rangeType == versionType) { + if (j <= fixCount) { + // Handles "cmp-fix" cases + if (versionValue != range[j]) { + return false; + } + } else { + // Handles "cmp" cases + if (negated ? versionValue > range[j] : versionValue < range[j]) { + return false; } + if (versionValue != range[j]) isEqual = false; } } - if (dep instanceof WebAssemblyExportImportedDependency) { - importData.names.add(dep.name); - const usedName = moduleGraph - .getExportsInfo(module) - .getUsedName(dep.exportName, runtime); - if (usedName) { - runtimeRequirements.add(RuntimeGlobals.exports); - const exportProp = `${module.exportsArgument}[${JSON.stringify( - usedName - )}]`; - const defineStatement = Template.asString([ - `${exportProp} = ${runtimeTemplate.exportFromImport({ - moduleGraph, - module: moduleGraph.getModule(dep), - request: dep.request, - importVar: importData.importVar, - originModule: module, - exportName: dep.name, - asiSafe: true, - isCall: false, - callContext: null, - defaultInterop: true, - initFragments, - runtime, - runtimeRequirements - })};`, - `if(WebAssembly.Global) ${exportProp} = ` + - `new WebAssembly.Global({ value: ${JSON.stringify( - dep.valueType - )} }, ${exportProp});` - ]); - importData.reexports.push(defineStatement); - needExportsCopy = true; - } + + // Handle big-ver + else if (rangeType != "s" && rangeType != "n") { + if (negated || j <= fixCount) return false; + isEqual = false; + j--; + } + + // Handle differ, big-cmp and small-cmp + else if (j <= fixCount || versionType < rangeType != negated) { + return false; + } else { + isEqual = false; + } + } else { + // Handles all "next-ver" cases in the second table + if (rangeType != "s" && rangeType != "n") { + isEqual = false; + j--; } + + // next is applied by default } } - const importsCode = Template.asString( - Array.from( - importedModules, - ([module, { importVar, request, reexports }]) => { - const importStatement = runtimeTemplate.importStatement({ - module, - chunkGraph, - request, - importVar, - originModule: module, - runtimeRequirements - }); - return importStatement[0] + importStatement[1] + reexports.join("\n"); - } - ) + } + /** @type {(boolean | number)[]} */ + var stack = []; + var p = stack.pop.bind(stack); + // eslint-disable-next-line no-redeclare + for (var i = 1; i < range.length; i++) { + var item = /** @type {SemVerRange | 0 | 1 | 2} */ (range[i]); + stack.push( + item == 1 + ? p() | p() + : item == 2 + ? p() & p() + : item + ? satisfy(item, version) + : !p() ); + } + return !!p(); +}; +/* eslint-enable eqeqeq */ +exports.satisfy = satisfy; - const copyAllExports = - exportsInfo.otherExportsInfo.getUsed(runtime) === UsageState.Unused && - !needExportsCopy; - - // need these globals - runtimeRequirements.add(RuntimeGlobals.module); - runtimeRequirements.add(RuntimeGlobals.moduleId); - runtimeRequirements.add(RuntimeGlobals.wasmInstances); - if (exportsInfo.otherExportsInfo.getUsed(runtime) !== UsageState.Unused) { - runtimeRequirements.add(RuntimeGlobals.makeNamespaceObject); - runtimeRequirements.add(RuntimeGlobals.exports); - } - if (!copyAllExports) { - runtimeRequirements.add(RuntimeGlobals.exports); - } +exports.stringifyHoley = json => { + switch (typeof json) { + case "undefined": + return ""; + case "object": + if (Array.isArray(json)) { + let str = "["; + for (let i = 0; i < json.length; i++) { + if (i !== 0) str += ","; + str += this.stringifyHoley(json[i]); + } + str += "]"; + return str; + } else { + return JSON.stringify(json); + } + default: + return JSON.stringify(json); + } +}; - // create source - const source = new RawSource( - [ - '"use strict";', - "// Instantiate WebAssembly module", - `var wasmExports = ${RuntimeGlobals.wasmInstances}[${module.moduleArgument}.id];`, +//#region runtime code: parseVersion +exports.parseVersionRuntimeCode = runtimeTemplate => + `var parseVersion = ${runtimeTemplate.basicFunction("str", [ + "// see webpack/lib/util/semver.js for original code", + `var p=${ + runtimeTemplate.supportsArrowFunction() ? "p=>" : "function(p)" + }{return p.split(".").map((${ + runtimeTemplate.supportsArrowFunction() ? "p=>" : "function(p)" + }{return+p==p?+p:p}))},n=/^([^-+]+)?(?:-([^+]+))?(?:\\+(.+))?$/.exec(str),r=n[1]?p(n[1]):[];return n[2]&&(r.length++,r.push.apply(r,p(n[2]))),n[3]&&(r.push([]),r.push.apply(r,p(n[3]))),r;` + ])}`; +//#endregion - exportsInfo.otherExportsInfo.getUsed(runtime) !== UsageState.Unused - ? `${RuntimeGlobals.makeNamespaceObject}(${module.exportsArgument});` - : "", +//#region runtime code: versionLt +exports.versionLtRuntimeCode = runtimeTemplate => + `var versionLt = ${runtimeTemplate.basicFunction("a, b", [ + "// see webpack/lib/util/semver.js for original code", + 'a=parseVersion(a),b=parseVersion(b);for(var r=0;;){if(r>=a.length)return r=b.length)return"u"==n;var t=b[r],f=(typeof t)[0];if(n!=f)return"o"==n&&"n"==f||("s"==f||"u"==n);if("o"!=n&&"u"!=n&&e!=t)return e + `var rangeToString = ${runtimeTemplate.basicFunction("range", [ + "// see webpack/lib/util/semver.js for original code", + 'var r=range[0],n="";if(1===range.length)return"*";if(r+.5){n+=0==r?">=":-1==r?"<":1==r?"^":2==r?"~":r>0?"=":"!=";for(var e=1,a=1;a0?".":"")+(e=2,t)}return n}var g=[];for(a=1;a + `var satisfy = ${runtimeTemplate.basicFunction("range, version", [ + "// see webpack/lib/util/semver.js for original code", + 'if(0 in range){version=parseVersion(version);var e=range[0],r=e<0;r&&(e=-e-1);for(var n=0,i=1,a=!0;;i++,n++){var f,s,g=i=version.length||"o"==(s=(typeof(f=version[n]))[0]))return!a||("u"==g?i>e&&!r:""==g!=r);if("u"==s){if(!a||"u"!=g)return!1}else if(a)if(g==s)if(i<=e){if(f!=range[i])return!1}else{if(r?f>range[i]:f - __webpack_require__(35303) +const getBinaryMiddleware = memoize(() => + __webpack_require__(7732) ); -const getWebAssemblyJavascriptGenerator = memoize(() => - __webpack_require__(88890) +const getObjectMiddleware = memoize(() => + __webpack_require__(77815) +); +const getSingleItemMiddleware = memoize(() => + __webpack_require__(63340) +); +const getSerializer = memoize(() => __webpack_require__(24754)); +const getSerializerMiddleware = memoize(() => + __webpack_require__(37063) ); -const getWebAssemblyParser = memoize(() => __webpack_require__(52288)); - -class WebAssemblyModulesPlugin { - constructor(options) { - this.options = options; - } - - /** - * Apply the plugin - * @param {Compiler} compiler the compiler instance - * @returns {void} - */ - apply(compiler) { - compiler.hooks.compilation.tap( - "WebAssemblyModulesPlugin", - (compilation, { normalModuleFactory }) => { - compilation.dependencyFactories.set( - WebAssemblyImportDependency, - normalModuleFactory - ); - - compilation.dependencyFactories.set( - WebAssemblyExportImportedDependency, - normalModuleFactory - ); - - normalModuleFactory.hooks.createParser - .for("webassembly/sync") - .tap("WebAssemblyModulesPlugin", () => { - const WebAssemblyParser = getWebAssemblyParser(); - - return new WebAssemblyParser(); - }); - - normalModuleFactory.hooks.createGenerator - .for("webassembly/sync") - .tap("WebAssemblyModulesPlugin", () => { - const WebAssemblyJavascriptGenerator = - getWebAssemblyJavascriptGenerator(); - const WebAssemblyGenerator = getWebAssemblyGenerator(); - - return Generator.byType({ - javascript: new WebAssemblyJavascriptGenerator(), - webassembly: new WebAssemblyGenerator(this.options) - }); - }); - compilation.hooks.renderManifest.tap( - "WebAssemblyModulesPlugin", - (result, options) => { - const { chunkGraph } = compilation; - const { chunk, outputOptions, codeGenerationResults } = options; +const getBinaryMiddlewareInstance = memoize( + () => new (getBinaryMiddleware())() +); - for (const module of chunkGraph.getOrderedChunkModulesIterable( - chunk, - compareModulesByIdentifier - )) { - if (module.type === "webassembly/sync") { - const filenameTemplate = - outputOptions.webassemblyModuleFilename; +const registerSerializers = memoize(() => { + __webpack_require__(31107); - result.push({ - render: () => - codeGenerationResults.getSource( - module, - chunk.runtime, - "webassembly" - ), - filenameTemplate, - pathOptions: { - module, - runtime: chunk.runtime, - chunkGraph - }, - auxiliary: true, - identifier: `webassemblyModule${chunkGraph.getModuleId( - module - )}`, - hash: chunkGraph.getModuleHash(module, chunk.runtime) - }); - } - } + // Load internal paths with a relative require + // This allows bundling all internal serializers + const internalSerializables = __webpack_require__(7679); + getObjectMiddleware().registerLoader(/^webpack\/lib\//, req => { + const loader = internalSerializables[req.slice("webpack/lib/".length)]; + if (loader) { + loader(); + } else { + console.warn(`${req} not found in internalSerializables`); + } + return true; + }); +}); - return result; - } - ); +/** @type {Serializer} */ +let buffersSerializer; - compilation.hooks.afterChunks.tap("WebAssemblyModulesPlugin", () => { - const chunkGraph = compilation.chunkGraph; - const initialWasmModules = new Set(); - for (const chunk of compilation.chunks) { - if (chunk.canBeInitial()) { - for (const module of chunkGraph.getChunkModulesIterable(chunk)) { - if (module.type === "webassembly/sync") { - initialWasmModules.add(module); - } - } - } - } - for (const module of initialWasmModules) { - compilation.errors.push( - new WebAssemblyInInitialChunkError( - module, - compilation.moduleGraph, - compilation.chunkGraph, - compilation.requestShortener - ) +// Expose serialization API +module.exports = { + get register() { + return getObjectMiddleware().register; + }, + get registerLoader() { + return getObjectMiddleware().registerLoader; + }, + get registerNotSerializable() { + return getObjectMiddleware().registerNotSerializable; + }, + get NOT_SERIALIZABLE() { + return getObjectMiddleware().NOT_SERIALIZABLE; + }, + /** @type {MEASURE_START_OPERATION} */ + get MEASURE_START_OPERATION() { + return getBinaryMiddleware().MEASURE_START_OPERATION; + }, + /** @type {MEASURE_END_OPERATION} */ + get MEASURE_END_OPERATION() { + return getBinaryMiddleware().MEASURE_END_OPERATION; + }, + get buffersSerializer() { + if (buffersSerializer !== undefined) return buffersSerializer; + registerSerializers(); + const Serializer = getSerializer(); + const binaryMiddleware = getBinaryMiddlewareInstance(); + const SerializerMiddleware = getSerializerMiddleware(); + const SingleItemMiddleware = getSingleItemMiddleware(); + return (buffersSerializer = new Serializer([ + new SingleItemMiddleware(), + new (getObjectMiddleware())(context => { + if (context.write) { + context.writeLazy = value => { + context.write( + SerializerMiddleware.createLazy(value, binaryMiddleware) ); - } - }); - } - ); + }; + } + }, "md4"), + binaryMiddleware + ])); + }, + createFileSerializer: (fs, hashFunction) => { + registerSerializers(); + const Serializer = getSerializer(); + const FileMiddleware = __webpack_require__(40572); + const fileMiddleware = new FileMiddleware(fs, hashFunction); + const binaryMiddleware = getBinaryMiddlewareInstance(); + const SerializerMiddleware = getSerializerMiddleware(); + const SingleItemMiddleware = getSingleItemMiddleware(); + return new Serializer([ + new SingleItemMiddleware(), + new (getObjectMiddleware())(context => { + if (context.write) { + context.writeLazy = value => { + context.write( + SerializerMiddleware.createLazy(value, binaryMiddleware) + ); + }; + context.writeSeparate = (value, options) => { + const lazy = SerializerMiddleware.createLazy( + value, + fileMiddleware, + options + ); + context.write(lazy); + return lazy; + }; + } + }, hashFunction), + binaryMiddleware, + fileMiddleware + ]); } -} - -module.exports = WebAssemblyModulesPlugin; +}; /***/ }), -/***/ 52288: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { +/***/ 84820: +/***/ (function(module) { "use strict"; /* @@ -132997,197 +132256,280 @@ module.exports = WebAssemblyModulesPlugin; -const t = __webpack_require__(98688); -const { moduleContextFromModuleAST } = __webpack_require__(98688); -const { decode } = __webpack_require__(8062); -const Parser = __webpack_require__(68214); -const StaticExportsDependency = __webpack_require__(67967); -const WebAssemblyExportImportedDependency = __webpack_require__(18248); -const WebAssemblyImportDependency = __webpack_require__(97093); +/** + * @typedef {Object} GroupOptions + * @property {boolean=} groupChildren + * @property {boolean=} force + * @property {number=} targetGroupCount + */ -/** @typedef {import("../Module")} Module */ -/** @typedef {import("../Parser").ParserState} ParserState */ -/** @typedef {import("../Parser").PreparsedAst} PreparsedAst */ +/** + * @template T + * @template R + * @typedef {Object} GroupConfig + * @property {function(T): string[]} getKeys + * @property {function(string, (R | T)[], T[]): R} createGroup + * @property {function(string, T[]): GroupOptions=} getOptions + */ -const JS_COMPAT_TYPES = new Set(["i32", "f32", "f64"]); +/** + * @template T + * @template R + * @typedef {Object} ItemWithGroups + * @property {T} item + * @property {Set>} groups + */ /** - * @param {t.Signature} signature the func signature - * @returns {null | string} the type incompatible with js types + * @template T + * @template R + * @typedef {{ config: GroupConfig, name: string, alreadyGrouped: boolean, items: Set> | undefined }} Group */ -const getJsIncompatibleType = signature => { - for (const param of signature.params) { - if (!JS_COMPAT_TYPES.has(param.valtype)) { - return `${param.valtype} as parameter`; - } - } - for (const type of signature.results) { - if (!JS_COMPAT_TYPES.has(type)) return `${type} as result`; - } - return null; -}; /** - * TODO why are there two different Signature types? - * @param {t.FuncSignature} signature the func signature - * @returns {null | string} the type incompatible with js types + * @template T + * @template R + * @param {T[]} items the list of items + * @param {GroupConfig[]} groupConfigs configuration + * @returns {(R | T)[]} grouped items */ -const getJsIncompatibleTypeOfFuncSignature = signature => { - for (const param of signature.args) { - if (!JS_COMPAT_TYPES.has(param)) { - return `${param} as parameter`; +const smartGrouping = (items, groupConfigs) => { + /** @type {Set>} */ + const itemsWithGroups = new Set(); + /** @type {Map>} */ + const allGroups = new Map(); + for (const item of items) { + /** @type {Set>} */ + const groups = new Set(); + for (let i = 0; i < groupConfigs.length; i++) { + const groupConfig = groupConfigs[i]; + const keys = groupConfig.getKeys(item); + if (keys) { + for (const name of keys) { + const key = `${i}:${name}`; + let group = allGroups.get(key); + if (group === undefined) { + allGroups.set( + key, + (group = { + config: groupConfig, + name, + alreadyGrouped: false, + items: undefined + }) + ); + } + groups.add(group); + } + } } + itemsWithGroups.add({ + item, + groups + }); } - for (const type of signature.result) { - if (!JS_COMPAT_TYPES.has(type)) return `${type} as result`; - } - return null; -}; - -const decoderOpts = { - ignoreCodeSection: true, - ignoreDataSection: true, - - // this will avoid having to lookup with identifiers in the ModuleContext - ignoreCustomNameSection: true -}; - -class WebAssemblyParser extends Parser { - constructor(options) { - super(); - this.hooks = Object.freeze({}); - this.options = options; - } - /** - * @param {string | Buffer | PreparsedAst} source the source to parse - * @param {ParserState} state the parser state - * @returns {ParserState} the parser state + * @param {Set>} itemsWithGroups input items with groups + * @returns {(T | R)[]} groups items */ - parse(source, state) { - if (!Buffer.isBuffer(source)) { - throw new Error("WebAssemblyParser input must be a Buffer"); + const runGrouping = itemsWithGroups => { + const totalSize = itemsWithGroups.size; + for (const entry of itemsWithGroups) { + for (const group of entry.groups) { + if (group.alreadyGrouped) continue; + const items = group.items; + if (items === undefined) { + group.items = new Set([entry]); + } else { + items.add(entry); + } + } } + /** @type {Map, { items: Set>, options: GroupOptions | false | undefined, used: boolean }>} */ + const groupMap = new Map(); + for (const group of allGroups.values()) { + if (group.items) { + const items = group.items; + group.items = undefined; + groupMap.set(group, { + items, + options: undefined, + used: false + }); + } + } + /** @type {(T | R)[]} */ + const results = []; + for (;;) { + /** @type {Group} */ + let bestGroup = undefined; + let bestGroupSize = -1; + let bestGroupItems = undefined; + let bestGroupOptions = undefined; + for (const [group, state] of groupMap) { + const { items, used } = state; + let options = state.options; + if (options === undefined) { + const groupConfig = group.config; + state.options = options = + (groupConfig.getOptions && + groupConfig.getOptions( + group.name, + Array.from(items, ({ item }) => item) + )) || + false; + } - // flag it as ESM - state.module.buildInfo.strict = true; - state.module.buildMeta.exportsType = "namespace"; - - // parse it - const program = decode(source, decoderOpts); - const module = program.body[0]; - - const moduleContext = moduleContextFromModuleAST(module); - - // extract imports and exports - const exports = []; - let jsIncompatibleExports = (state.module.buildMeta.jsIncompatibleExports = - undefined); - - const importedGlobals = []; - t.traverse(module, { - ModuleExport({ node }) { - const descriptor = node.descr; - - if (descriptor.exportType === "Func") { - const funcIdx = descriptor.id.value; - - /** @type {t.FuncSignature} */ - const funcSignature = moduleContext.getFunction(funcIdx); - - const incompatibleType = - getJsIncompatibleTypeOfFuncSignature(funcSignature); - - if (incompatibleType) { - if (jsIncompatibleExports === undefined) { - jsIncompatibleExports = - state.module.buildMeta.jsIncompatibleExports = {}; - } - jsIncompatibleExports[node.name] = incompatibleType; + const force = options && options.force; + if (!force) { + if (bestGroupOptions && bestGroupOptions.force) continue; + if (used) continue; + if (items.size <= 1 || totalSize - items.size <= 1) { + continue; } } + const targetGroupCount = (options && options.targetGroupCount) || 4; + let sizeValue = force + ? items.size + : Math.min( + items.size, + (totalSize * 2) / targetGroupCount + + itemsWithGroups.size - + items.size + ); + if ( + sizeValue > bestGroupSize || + (force && (!bestGroupOptions || !bestGroupOptions.force)) + ) { + bestGroup = group; + bestGroupSize = sizeValue; + bestGroupItems = items; + bestGroupOptions = options; + } + } + if (bestGroup === undefined) { + break; + } + const items = new Set(bestGroupItems); + const options = bestGroupOptions; - exports.push(node.name); - - if (node.descr && node.descr.exportType === "Global") { - const refNode = importedGlobals[node.descr.id.value]; - if (refNode) { - const dep = new WebAssemblyExportImportedDependency( - node.name, - refNode.module, - refNode.name, - refNode.descr.valtype - ); + const groupChildren = !options || options.groupChildren !== false; - state.module.addDependency(dep); + for (const item of items) { + itemsWithGroups.delete(item); + // Remove all groups that items have from the map to not select them again + for (const group of item.groups) { + const state = groupMap.get(group); + if (state !== undefined) { + state.items.delete(item); + if (state.items.size === 0) { + groupMap.delete(group); + } else { + state.options = undefined; + if (groupChildren) { + state.used = true; + } + } } } - }, + } + groupMap.delete(bestGroup); - Global({ node }) { - const init = node.init[0]; + const key = bestGroup.name; + const groupConfig = bestGroup.config; - let importNode = null; + const allItems = Array.from(items, ({ item }) => item); - if (init.id === "get_global") { - const globalIdx = init.args[0].value; + bestGroup.alreadyGrouped = true; + const children = groupChildren ? runGrouping(items) : allItems; + bestGroup.alreadyGrouped = false; - if (globalIdx < importedGlobals.length) { - importNode = importedGlobals[globalIdx]; - } - } + results.push(groupConfig.createGroup(key, children, allItems)); + } + for (const { item } of itemsWithGroups) { + results.push(item); + } + return results; + }; + return runGrouping(itemsWithGroups); +}; - importedGlobals.push(importNode); - }, +module.exports = smartGrouping; - ModuleImport({ node }) { - /** @type {false | string} */ - let onlyDirectImport = false; - if (t.isMemory(node.descr) === true) { - onlyDirectImport = "Memory"; - } else if (t.isTable(node.descr) === true) { - onlyDirectImport = "Table"; - } else if (t.isFuncImportDescr(node.descr) === true) { - const incompatibleType = getJsIncompatibleType(node.descr.signature); - if (incompatibleType) { - onlyDirectImport = `Non-JS-compatible Func Signature (${incompatibleType})`; - } - } else if (t.isGlobalType(node.descr) === true) { - const type = node.descr.valtype; - if (!JS_COMPAT_TYPES.has(type)) { - onlyDirectImport = `Non-JS-compatible Global Type (${type})`; - } - } +/***/ }), - const dep = new WebAssemblyImportDependency( - node.module, - node.name, - node.descr, - onlyDirectImport - ); +/***/ 4002: +/***/ (function(__unused_webpack_module, exports) { - state.module.addDependency(dep); +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ - if (t.isGlobalType(node.descr)) { - importedGlobals.push(node); - } - } - }); - state.module.addDependency(new StaticExportsDependency(exports, false)); - return state; - } -} +/** @typedef {import("webpack-sources").Source} Source */ -module.exports = WebAssemblyParser; +/** @type {WeakMap>} */ +const equalityCache = new WeakMap(); + +/** + * @param {Source} a a source + * @param {Source} b another source + * @returns {boolean} true, when both sources are equal + */ +const _isSourceEqual = (a, b) => { + // prefer .buffer(), it's called anyway during emit + /** @type {Buffer|string} */ + let aSource = typeof a.buffer === "function" ? a.buffer() : a.source(); + /** @type {Buffer|string} */ + let bSource = typeof b.buffer === "function" ? b.buffer() : b.source(); + if (aSource === bSource) return true; + if (typeof aSource === "string" && typeof bSource === "string") return false; + if (!Buffer.isBuffer(aSource)) aSource = Buffer.from(aSource, "utf-8"); + if (!Buffer.isBuffer(bSource)) bSource = Buffer.from(bSource, "utf-8"); + return aSource.equals(bSource); +}; + +/** + * @param {Source} a a source + * @param {Source} b another source + * @returns {boolean} true, when both sources are equal + */ +const isSourceEqual = (a, b) => { + if (a === b) return true; + const cache1 = equalityCache.get(a); + if (cache1 !== undefined) { + const result = cache1.get(b); + if (result !== undefined) return result; + } + const result = _isSourceEqual(a, b); + if (cache1 !== undefined) { + cache1.set(b, result); + } else { + const map = new WeakMap(); + map.set(b, result); + equalityCache.set(a, map); + } + const cache2 = equalityCache.get(b); + if (cache2 !== undefined) { + cache2.set(a, result); + } else { + const map = new WeakMap(); + map.set(a, result); + equalityCache.set(b, map); + } + return result; +}; +exports.isSourceEqual = isSourceEqual; /***/ }), -/***/ 41520: -/***/ (function(__unused_webpack_module, exports, __webpack_require__) { +/***/ 55959: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; /* @@ -133197,69 +132539,179 @@ module.exports = WebAssemblyParser; -const Template = __webpack_require__(92066); -const WebAssemblyImportDependency = __webpack_require__(97093); - -/** @typedef {import("../Module")} Module */ -/** @typedef {import("../ModuleGraph")} ModuleGraph */ +const { validate } = __webpack_require__(79286); -/** @typedef {Object} UsedWasmDependency - * @property {WebAssemblyImportDependency} dependency the dependency - * @property {string} name the export name - * @property {string} module the module name - */ +/* cSpell:disable */ +const DID_YOU_MEAN = { + rules: "module.rules", + loaders: "module.rules or module.rules.*.use", + query: "module.rules.*.options (BREAKING CHANGE since webpack 5)", + noParse: "module.noParse", + filename: "output.filename or module.rules.*.generator.filename", + file: "output.filename", + chunkFilename: "output.chunkFilename", + chunkfilename: "output.chunkFilename", + ecmaVersion: + "output.environment (output.ecmaVersion was a temporary configuration option during webpack 5 beta)", + ecmaversion: + "output.environment (output.ecmaVersion was a temporary configuration option during webpack 5 beta)", + ecma: "output.environment (output.ecmaVersion was a temporary configuration option during webpack 5 beta)", + path: "output.path", + pathinfo: "output.pathinfo", + pathInfo: "output.pathinfo", + jsonpFunction: "output.chunkLoadingGlobal (BREAKING CHANGE since webpack 5)", + chunkCallbackName: + "output.chunkLoadingGlobal (BREAKING CHANGE since webpack 5)", + jsonpScriptType: "output.scriptType (BREAKING CHANGE since webpack 5)", + hotUpdateFunction: "output.hotUpdateGlobal (BREAKING CHANGE since webpack 5)", + splitChunks: "optimization.splitChunks", + immutablePaths: "snapshot.immutablePaths", + managedPaths: "snapshot.managedPaths", + maxModules: "stats.modulesSpace (BREAKING CHANGE since webpack 5)", + hashedModuleIds: + 'optimization.moduleIds: "hashed" (BREAKING CHANGE since webpack 5)', + namedChunks: + 'optimization.chunkIds: "named" (BREAKING CHANGE since webpack 5)', + namedModules: + 'optimization.moduleIds: "named" (BREAKING CHANGE since webpack 5)', + occurrenceOrder: + 'optimization.chunkIds: "size" and optimization.moduleIds: "size" (BREAKING CHANGE since webpack 5)', + automaticNamePrefix: + "optimization.splitChunks.[cacheGroups.*].idHint (BREAKING CHANGE since webpack 5)", + noEmitOnErrors: + "optimization.emitOnErrors (BREAKING CHANGE since webpack 5: logic is inverted to avoid negative flags)", + Buffer: + "to use the ProvidePlugin to process the Buffer variable to modules as polyfill\n" + + "BREAKING CHANGE: webpack 5 no longer provided Node.js polyfills by default.\n" + + "Note: if you are using 'node.Buffer: false', you can just remove that as this is the default behavior now.\n" + + "To provide a polyfill to modules use:\n" + + 'new ProvidePlugin({ Buffer: ["buffer", "Buffer"] }) and npm install buffer.', + process: + "to use the ProvidePlugin to process the process variable to modules as polyfill\n" + + "BREAKING CHANGE: webpack 5 no longer provided Node.js polyfills by default.\n" + + "Note: if you are using 'node.process: false', you can just remove that as this is the default behavior now.\n" + + "To provide a polyfill to modules use:\n" + + 'new ProvidePlugin({ process: "process" }) and npm install buffer.' +}; -const MANGLED_MODULE = "a"; +const REMOVED = { + concord: + "BREAKING CHANGE: resolve.concord has been removed and is no longer available.", + devtoolLineToLine: + "BREAKING CHANGE: output.devtoolLineToLine has been removed and is no longer available." +}; +/* cSpell:enable */ /** - * @param {ModuleGraph} moduleGraph the module graph - * @param {Module} module the module - * @param {boolean} mangle mangle module and export names - * @returns {UsedWasmDependency[]} used dependencies and (mangled) name + * @param {Parameters[0]} schema a json schema + * @param {Parameters[1]} options the options that should be validated + * @param {Parameters[2]=} validationConfiguration configuration for generating errors + * @returns {void} */ -const getUsedDependencies = (moduleGraph, module, mangle) => { - /** @type {UsedWasmDependency[]} */ - const array = []; - let importIndex = 0; - for (const dep of module.dependencies) { - if (dep instanceof WebAssemblyImportDependency) { - if ( - dep.description.type === "GlobalType" || - moduleGraph.getModule(dep) === null - ) { - continue; - } +const validateSchema = (schema, options, validationConfiguration) => { + validate( + schema, + options, + validationConfiguration || { + name: "Webpack", + postFormatter: (formattedError, error) => { + const children = error.children; + if ( + children && + children.some( + child => + child.keyword === "absolutePath" && + child.dataPath === ".output.filename" + ) + ) { + return `${formattedError}\nPlease use output.path to specify absolute path and output.filename for the file name.`; + } - const exportName = dep.name; - // TODO add the following 3 lines when removing of ModuleExport is possible - // const importedModule = moduleGraph.getModule(dep); - // const usedName = importedModule && moduleGraph.getExportsInfo(importedModule).getUsedName(exportName, runtime); - // if (usedName !== false) { - if (mangle) { - array.push({ - dependency: dep, - name: Template.numberToIdentifier(importIndex++), - module: MANGLED_MODULE - }); - } else { - array.push({ - dependency: dep, - name: exportName, - module: dep.request - }); + if ( + children && + children.some( + child => + child.keyword === "pattern" && child.dataPath === ".devtool" + ) + ) { + return ( + `${formattedError}\n` + + "BREAKING CHANGE since webpack 5: The devtool option is more strict.\n" + + "Please strictly follow the order of the keywords in the pattern." + ); + } + + if (error.keyword === "additionalProperties") { + const params = + /** @type {import("ajv").AdditionalPropertiesParams} */ ( + error.params + ); + if ( + Object.prototype.hasOwnProperty.call( + DID_YOU_MEAN, + params.additionalProperty + ) + ) { + return `${formattedError}\nDid you mean ${ + DID_YOU_MEAN[params.additionalProperty] + }?`; + } + + if ( + Object.prototype.hasOwnProperty.call( + REMOVED, + params.additionalProperty + ) + ) { + return `${formattedError}\n${REMOVED[params.additionalProperty]}?`; + } + + if (!error.dataPath) { + if (params.additionalProperty === "debug") { + return ( + `${formattedError}\n` + + "The 'debug' property was removed in webpack 2.0.0.\n" + + "Loaders should be updated to allow passing this option via loader options in module.rules.\n" + + "Until loaders are updated one can use the LoaderOptionsPlugin to switch loaders into debug mode:\n" + + "plugins: [\n" + + " new webpack.LoaderOptionsPlugin({\n" + + " debug: true\n" + + " })\n" + + "]" + ); + } + + if (params.additionalProperty) { + return ( + `${formattedError}\n` + + "For typos: please correct them.\n" + + "For loader options: webpack >= v2.0.0 no longer allows custom properties in configuration.\n" + + " Loaders should be updated to allow passing options via loader options in module.rules.\n" + + " Until loaders are updated one can use the LoaderOptionsPlugin to pass these options to the loader:\n" + + " plugins: [\n" + + " new webpack.LoaderOptionsPlugin({\n" + + " // test: /\\.xxx$/, // may apply this only for some modules\n" + + " options: {\n" + + ` ${params.additionalProperty}: …\n` + + " }\n" + + " })\n" + + " ]" + ); + } + } + } + + return formattedError; } } - } - return array; + ); }; - -exports.getUsedDependencies = getUsedDependencies; -exports.MANGLED_MODULE = MANGLED_MODULE; +module.exports = validateSchema; /***/ }), -/***/ 93943: +/***/ 84465: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; @@ -133270,122 +132722,82 @@ exports.MANGLED_MODULE = MANGLED_MODULE; -/** @typedef {import("../../declarations/WebpackOptions").LibraryOptions} LibraryOptions */ -/** @typedef {import("../../declarations/WebpackOptions").WasmLoadingType} WasmLoadingType */ -/** @typedef {import("../Compiler")} Compiler */ - -/** @type {WeakMap>} */ -const enabledTypes = new WeakMap(); - -const getEnabledTypes = compiler => { - let set = enabledTypes.get(compiler); - if (set === undefined) { - set = new Set(); - enabledTypes.set(compiler, set); - } - return set; -}; - -class EnableWasmLoadingPlugin { - /** - * @param {WasmLoadingType} type library type that should be available - */ - constructor(type) { - this.type = type; - } - - /** - * @param {Compiler} compiler the compiler instance - * @param {WasmLoadingType} type type of library - * @returns {void} - */ - static setEnabled(compiler, type) { - getEnabledTypes(compiler).add(type); - } +const RuntimeGlobals = __webpack_require__(49404); +const RuntimeModule = __webpack_require__(61439); +const Template = __webpack_require__(92066); - /** - * @param {Compiler} compiler the compiler instance - * @param {WasmLoadingType} type type of library - * @returns {void} - */ - static checkEnabled(compiler, type) { - if (!getEnabledTypes(compiler).has(type)) { - throw new Error( - `Library type "${type}" is not enabled. ` + - "EnableWasmLoadingPlugin need to be used to enable this type of wasm loading. " + - 'This usually happens through the "output.enabledWasmLoadingTypes" option. ' + - 'If you are using a function as entry which sets "wasmLoading", you need to add all potential library types to "output.enabledWasmLoadingTypes". ' + - "These types are enabled: " + - Array.from(getEnabledTypes(compiler)).join(", ") - ); - } +class AsyncWasmLoadingRuntimeModule extends RuntimeModule { + constructor({ generateLoadBinaryCode, supportsStreaming }) { + super("wasm loading", RuntimeModule.STAGE_NORMAL); + this.generateLoadBinaryCode = generateLoadBinaryCode; + this.supportsStreaming = supportsStreaming; } /** - * Apply the plugin - * @param {Compiler} compiler the compiler instance - * @returns {void} + * @returns {string} runtime code */ - apply(compiler) { - const { type } = this; - - // Only enable once - const enabled = getEnabledTypes(compiler); - if (enabled.has(type)) return; - enabled.add(type); - - if (typeof type === "string") { - switch (type) { - case "fetch": { - // TODO webpack 6 remove FetchCompileWasmPlugin - const FetchCompileWasmPlugin = __webpack_require__(89728); - const FetchCompileAsyncWasmPlugin = __webpack_require__(37118); - new FetchCompileWasmPlugin({ - mangleImports: compiler.options.optimization.mangleWasmImports - }).apply(compiler); - new FetchCompileAsyncWasmPlugin().apply(compiler); - break; - } - case "async-node": { - // TODO webpack 6 remove ReadFileCompileWasmPlugin - const ReadFileCompileWasmPlugin = __webpack_require__(98724); - // @ts-expect-error typescript bug for duplicate require - const ReadFileCompileAsyncWasmPlugin = __webpack_require__(82138); - new ReadFileCompileWasmPlugin({ - mangleImports: compiler.options.optimization.mangleWasmImports - }).apply(compiler); - new ReadFileCompileAsyncWasmPlugin({ type }).apply(compiler); - break; - } - case "async-node-module": { - // @ts-expect-error typescript bug for duplicate require - const ReadFileCompileAsyncWasmPlugin = __webpack_require__(82138); - new ReadFileCompileAsyncWasmPlugin({ type, import: true }).apply( - compiler - ); - break; - } - case "universal": - throw new Error( - "Universal WebAssembly Loading is not implemented yet" - ); - default: - throw new Error(`Unsupported wasm loading type ${type}. -Plugins which provide custom wasm loading types must call EnableWasmLoadingPlugin.setEnabled(compiler, type) to disable this error.`); + generate() { + const { compilation, chunk } = this; + const { outputOptions, runtimeTemplate } = compilation; + const fn = RuntimeGlobals.instantiateWasm; + const wasmModuleSrcPath = compilation.getPath( + JSON.stringify(outputOptions.webassemblyModuleFilename), + { + hash: `" + ${RuntimeGlobals.getFullHash}() + "`, + hashWithLength: length => + `" + ${RuntimeGlobals.getFullHash}}().slice(0, ${length}) + "`, + module: { + id: '" + wasmModuleId + "', + hash: `" + wasmModuleHash + "`, + hashWithLength(length) { + return `" + wasmModuleHash.slice(0, ${length}) + "`; + } + }, + runtime: chunk.runtime } - } else { - // TODO support plugin instances here - // apply them to the compiler - } + ); + return `${fn} = ${runtimeTemplate.basicFunction( + "exports, wasmModuleId, wasmModuleHash, importsObj", + [ + `var req = ${this.generateLoadBinaryCode(wasmModuleSrcPath)};`, + this.supportsStreaming + ? Template.asString([ + "if (typeof WebAssembly.instantiateStreaming === 'function') {", + Template.indent([ + "return WebAssembly.instantiateStreaming(req, importsObj)", + Template.indent([ + `.then(${runtimeTemplate.returningFunction( + "Object.assign(exports, res.instance.exports)", + "res" + )});` + ]) + ]), + "}" + ]) + : "// no support for streaming compilation", + "return req", + Template.indent([ + `.then(${runtimeTemplate.returningFunction("x.arrayBuffer()", "x")})`, + `.then(${runtimeTemplate.returningFunction( + "WebAssembly.instantiate(bytes, importsObj)", + "bytes" + )})`, + `.then(${runtimeTemplate.returningFunction( + "Object.assign(exports, res.instance.exports)", + "res" + )});` + ]) + ] + )};`; } } -module.exports = EnableWasmLoadingPlugin; +module.exports = AsyncWasmLoadingRuntimeModule; /***/ }), -/***/ 37118: +/***/ 60072: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; @@ -133396,66 +132808,57 @@ module.exports = EnableWasmLoadingPlugin; -const RuntimeGlobals = __webpack_require__(49404); -const AsyncWasmLoadingRuntimeModule = __webpack_require__(84465); +const Generator = __webpack_require__(1826); + +/** @typedef {import("webpack-sources").Source} Source */ +/** @typedef {import("../Generator").GenerateContext} GenerateContext */ +/** @typedef {import("../NormalModule")} NormalModule */ + +const TYPES = new Set(["webassembly"]); -/** @typedef {import("../Compiler")} Compiler */ +class AsyncWebAssemblyGenerator extends Generator { + constructor(options) { + super(); + this.options = options; + } -class FetchCompileAsyncWasmPlugin { /** - * Apply the plugin - * @param {Compiler} compiler the compiler instance - * @returns {void} + * @param {NormalModule} module fresh module + * @returns {Set} available types (do not mutate) */ - apply(compiler) { - compiler.hooks.thisCompilation.tap( - "FetchCompileAsyncWasmPlugin", - compilation => { - const globalWasmLoading = compilation.outputOptions.wasmLoading; - const isEnabledForChunk = chunk => { - const options = chunk.getEntryOptions(); - const wasmLoading = - options && options.wasmLoading !== undefined - ? options.wasmLoading - : globalWasmLoading; - return wasmLoading === "fetch"; - }; - const generateLoadBinaryCode = path => - `fetch(${RuntimeGlobals.publicPath} + ${path})`; + getTypes(module) { + return TYPES; + } - compilation.hooks.runtimeRequirementInTree - .for(RuntimeGlobals.instantiateWasm) - .tap("FetchCompileAsyncWasmPlugin", (chunk, set) => { - if (!isEnabledForChunk(chunk)) return; - const chunkGraph = compilation.chunkGraph; - if ( - !chunkGraph.hasModuleInGraph( - chunk, - m => m.type === "webassembly/async" - ) - ) { - return; - } - set.add(RuntimeGlobals.publicPath); - compilation.addRuntimeModule( - chunk, - new AsyncWasmLoadingRuntimeModule({ - generateLoadBinaryCode, - supportsStreaming: true - }) - ); - }); - } - ); + /** + * @param {NormalModule} module the module + * @param {string=} type source type + * @returns {number} estimate size of the module + */ + getSize(module, type) { + const originalSource = module.originalSource(); + if (!originalSource) { + return 0; + } + return originalSource.size(); + } + + /** + * @param {NormalModule} module module for which the code should be generated + * @param {GenerateContext} generateContext context for generate + * @returns {Source} generated code + */ + generate(module, generateContext) { + return module.originalSource(); } } -module.exports = FetchCompileAsyncWasmPlugin; +module.exports = AsyncWebAssemblyGenerator; /***/ }), -/***/ 89728: +/***/ 33838: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; @@ -133466,75 +132869,192 @@ module.exports = FetchCompileAsyncWasmPlugin; +const { RawSource } = __webpack_require__(96192); +const Generator = __webpack_require__(1826); +const InitFragment = __webpack_require__(51739); const RuntimeGlobals = __webpack_require__(49404); -const WasmChunkLoadingRuntimeModule = __webpack_require__(92153); +const Template = __webpack_require__(92066); +const WebAssemblyImportDependency = __webpack_require__(97093); -/** @typedef {import("../Compiler")} Compiler */ +/** @typedef {import("webpack-sources").Source} Source */ +/** @typedef {import("../DependencyTemplates")} DependencyTemplates */ +/** @typedef {import("../Generator").GenerateContext} GenerateContext */ +/** @typedef {import("../Module")} Module */ +/** @typedef {import("../NormalModule")} NormalModule */ +/** @typedef {import("../RuntimeTemplate")} RuntimeTemplate */ -// TODO webpack 6 remove +const TYPES = new Set(["webassembly"]); -class FetchCompileWasmPlugin { - constructor(options) { - this.options = options || {}; +class AsyncWebAssemblyJavascriptGenerator extends Generator { + constructor(filenameTemplate) { + super(); + this.filenameTemplate = filenameTemplate; } /** - * Apply the plugin - * @param {Compiler} compiler the compiler instance - * @returns {void} + * @param {NormalModule} module fresh module + * @returns {Set} available types (do not mutate) */ - apply(compiler) { - compiler.hooks.thisCompilation.tap( - "FetchCompileWasmPlugin", - compilation => { - const globalWasmLoading = compilation.outputOptions.wasmLoading; - const isEnabledForChunk = chunk => { - const options = chunk.getEntryOptions(); - const wasmLoading = - options && options.wasmLoading !== undefined - ? options.wasmLoading - : globalWasmLoading; - return wasmLoading === "fetch"; - }; - const generateLoadBinaryCode = path => - `fetch(${RuntimeGlobals.publicPath} + ${path})`; + getTypes(module) { + return TYPES; + } - compilation.hooks.runtimeRequirementInTree - .for(RuntimeGlobals.ensureChunkHandlers) - .tap("FetchCompileWasmPlugin", (chunk, set) => { - if (!isEnabledForChunk(chunk)) return; - const chunkGraph = compilation.chunkGraph; - if ( - !chunkGraph.hasModuleInGraph( - chunk, - m => m.type === "webassembly/sync" - ) - ) { - return; - } - set.add(RuntimeGlobals.moduleCache); - set.add(RuntimeGlobals.publicPath); - compilation.addRuntimeModule( - chunk, - new WasmChunkLoadingRuntimeModule({ - generateLoadBinaryCode, - supportsStreaming: true, - mangleImports: this.options.mangleImports, - runtimeRequirements: set - }) - ); + /** + * @param {NormalModule} module the module + * @param {string=} type source type + * @returns {number} estimate size of the module + */ + getSize(module, type) { + return 40 + module.dependencies.length * 10; + } + + /** + * @param {NormalModule} module module for which the code should be generated + * @param {GenerateContext} generateContext context for generate + * @returns {Source} generated code + */ + generate(module, generateContext) { + const { + runtimeTemplate, + chunkGraph, + moduleGraph, + runtimeRequirements, + runtime + } = generateContext; + runtimeRequirements.add(RuntimeGlobals.module); + runtimeRequirements.add(RuntimeGlobals.moduleId); + runtimeRequirements.add(RuntimeGlobals.exports); + runtimeRequirements.add(RuntimeGlobals.instantiateWasm); + /** @type {InitFragment[]} */ + const initFragments = []; + /** @type {Map} */ + const depModules = new Map(); + /** @type {Map} */ + const wasmDepsByRequest = new Map(); + for (const dep of module.dependencies) { + if (dep instanceof WebAssemblyImportDependency) { + const module = moduleGraph.getModule(dep); + if (!depModules.has(module)) { + depModules.set(module, { + request: dep.request, + importVar: `WEBPACK_IMPORTED_MODULE_${depModules.size}` }); + } + let list = wasmDepsByRequest.get(dep.request); + if (list === undefined) { + list = []; + wasmDepsByRequest.set(dep.request, list); + } + list.push(dep); + } + } + + const promises = []; + + const importStatements = Array.from( + depModules, + ([importedModule, { request, importVar }]) => { + if (moduleGraph.isAsync(importedModule)) { + promises.push(importVar); + } + return runtimeTemplate.importStatement({ + update: false, + module: importedModule, + chunkGraph, + request, + originModule: module, + importVar, + runtimeRequirements + }); + } + ); + const importsCode = importStatements.map(([x]) => x).join(""); + const importsCompatCode = importStatements.map(([_, x]) => x).join(""); + + const importObjRequestItems = Array.from( + wasmDepsByRequest, + ([request, deps]) => { + const exportItems = deps.map(dep => { + const importedModule = moduleGraph.getModule(dep); + const importVar = depModules.get(importedModule).importVar; + return `${JSON.stringify( + dep.name + )}: ${runtimeTemplate.exportFromImport({ + moduleGraph, + module: importedModule, + request, + exportName: dep.name, + originModule: module, + asiSafe: true, + isCall: false, + callContext: false, + defaultInterop: true, + importVar, + initFragments, + runtime, + runtimeRequirements + })}`; + }); + return Template.asString([ + `${JSON.stringify(request)}: {`, + Template.indent(exportItems.join(",\n")), + "}" + ]); } ); + + const importsObj = + importObjRequestItems.length > 0 + ? Template.asString([ + "{", + Template.indent(importObjRequestItems.join(",\n")), + "}" + ]) + : undefined; + + const instantiateCall = + `${RuntimeGlobals.instantiateWasm}(${module.exportsArgument}, ${ + module.moduleArgument + }.id, ${JSON.stringify( + chunkGraph.getRenderedModuleHash(module, runtime) + )}` + (importsObj ? `, ${importsObj})` : `)`); + + if (promises.length > 0) + runtimeRequirements.add(RuntimeGlobals.asyncModule); + + const source = new RawSource( + promises.length > 0 + ? Template.asString([ + `var __webpack_instantiate__ = ${runtimeTemplate.basicFunction( + `[${promises.join(", ")}]`, + `${importsCompatCode}return ${instantiateCall};` + )}`, + `${RuntimeGlobals.asyncModule}(${ + module.moduleArgument + }, ${runtimeTemplate.basicFunction( + "__webpack_handle_async_dependencies__", + [ + importsCode, + `var __webpack_async_dependencies__ = __webpack_handle_async_dependencies__([${promises.join( + ", " + )}]);`, + "return __webpack_async_dependencies__.then ? __webpack_async_dependencies__.then(__webpack_instantiate__) : __webpack_instantiate__(__webpack_async_dependencies__);" + ] + )}, 1);` + ]) + : `${importsCode}${importsCompatCode}module.exports = ${instantiateCall};` + ); + + return InitFragment.addToSource(source, initFragments, generateContext); } } -module.exports = FetchCompileWasmPlugin; +module.exports = AsyncWebAssemblyJavascriptGenerator; /***/ }), -/***/ 9253: +/***/ 13804: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; @@ -133545,768 +133065,689 @@ module.exports = FetchCompileWasmPlugin; -const RuntimeGlobals = __webpack_require__(49404); -const JsonpChunkLoadingRuntimeModule = __webpack_require__(66032); +const { SyncWaterfallHook } = __webpack_require__(34718); +const Compilation = __webpack_require__(59622); +const Generator = __webpack_require__(1826); +const { tryRunOrWebpackError } = __webpack_require__(89935); +const WebAssemblyImportDependency = __webpack_require__(97093); +const { compareModulesByIdentifier } = __webpack_require__(26296); +const memoize = __webpack_require__(84297); +/** @typedef {import("webpack-sources").Source} Source */ +/** @typedef {import("../Chunk")} Chunk */ +/** @typedef {import("../ChunkGraph")} ChunkGraph */ +/** @typedef {import("../CodeGenerationResults")} CodeGenerationResults */ /** @typedef {import("../Compiler")} Compiler */ +/** @typedef {import("../DependencyTemplates")} DependencyTemplates */ +/** @typedef {import("../Module")} Module */ +/** @typedef {import("../ModuleGraph")} ModuleGraph */ +/** @typedef {import("../RuntimeTemplate")} RuntimeTemplate */ +/** @typedef {import("../Template").RenderManifestEntry} RenderManifestEntry */ +/** @typedef {import("../Template").RenderManifestOptions} RenderManifestOptions */ + +const getAsyncWebAssemblyGenerator = memoize(() => + __webpack_require__(60072) +); +const getAsyncWebAssemblyJavascriptGenerator = memoize(() => + __webpack_require__(33838) +); +const getAsyncWebAssemblyParser = memoize(() => + __webpack_require__(20595) +); + +/** + * @typedef {Object} WebAssemblyRenderContext + * @property {Chunk} chunk the chunk + * @property {DependencyTemplates} dependencyTemplates the dependency templates + * @property {RuntimeTemplate} runtimeTemplate the runtime template + * @property {ModuleGraph} moduleGraph the module graph + * @property {ChunkGraph} chunkGraph the chunk graph + * @property {CodeGenerationResults} codeGenerationResults results of code generation + */ + +/** + * @typedef {Object} CompilationHooks + * @property {SyncWaterfallHook<[Source, Module, WebAssemblyRenderContext]>} renderModuleContent + */ + +/** @type {WeakMap} */ +const compilationHooksMap = new WeakMap(); + +class AsyncWebAssemblyModulesPlugin { + /** + * @param {Compilation} compilation the compilation + * @returns {CompilationHooks} the attached hooks + */ + static getCompilationHooks(compilation) { + if (!(compilation instanceof Compilation)) { + throw new TypeError( + "The 'compilation' argument must be an instance of Compilation" + ); + } + let hooks = compilationHooksMap.get(compilation); + if (hooks === undefined) { + hooks = { + renderModuleContent: new SyncWaterfallHook([ + "source", + "module", + "renderContext" + ]) + }; + compilationHooksMap.set(compilation, hooks); + } + return hooks; + } + + constructor(options) { + this.options = options; + } -class JsonpChunkLoadingPlugin { /** * Apply the plugin * @param {Compiler} compiler the compiler instance * @returns {void} */ apply(compiler) { - compiler.hooks.thisCompilation.tap( - "JsonpChunkLoadingPlugin", - compilation => { - const globalChunkLoading = compilation.outputOptions.chunkLoading; - const isEnabledForChunk = chunk => { - const options = chunk.getEntryOptions(); - const chunkLoading = - options && options.chunkLoading !== undefined - ? options.chunkLoading - : globalChunkLoading; - return chunkLoading === "jsonp"; - }; - const onceForChunkSet = new WeakSet(); - const handler = (chunk, set) => { - if (onceForChunkSet.has(chunk)) return; - onceForChunkSet.add(chunk); - if (!isEnabledForChunk(chunk)) return; - set.add(RuntimeGlobals.moduleFactoriesAddOnly); - set.add(RuntimeGlobals.hasOwnProperty); - compilation.addRuntimeModule( - chunk, - new JsonpChunkLoadingRuntimeModule(set) - ); - }; - compilation.hooks.runtimeRequirementInTree - .for(RuntimeGlobals.ensureChunkHandlers) - .tap("JsonpChunkLoadingPlugin", handler); - compilation.hooks.runtimeRequirementInTree - .for(RuntimeGlobals.hmrDownloadUpdateHandlers) - .tap("JsonpChunkLoadingPlugin", handler); - compilation.hooks.runtimeRequirementInTree - .for(RuntimeGlobals.hmrDownloadManifest) - .tap("JsonpChunkLoadingPlugin", handler); - compilation.hooks.runtimeRequirementInTree - .for(RuntimeGlobals.baseURI) - .tap("JsonpChunkLoadingPlugin", handler); - compilation.hooks.runtimeRequirementInTree - .for(RuntimeGlobals.onChunksLoaded) - .tap("JsonpChunkLoadingPlugin", handler); + compiler.hooks.compilation.tap( + "AsyncWebAssemblyModulesPlugin", + (compilation, { normalModuleFactory }) => { + const hooks = + AsyncWebAssemblyModulesPlugin.getCompilationHooks(compilation); + compilation.dependencyFactories.set( + WebAssemblyImportDependency, + normalModuleFactory + ); - compilation.hooks.runtimeRequirementInTree - .for(RuntimeGlobals.ensureChunkHandlers) - .tap("JsonpChunkLoadingPlugin", (chunk, set) => { - if (!isEnabledForChunk(chunk)) return; - set.add(RuntimeGlobals.publicPath); - set.add(RuntimeGlobals.loadScript); - set.add(RuntimeGlobals.getChunkScriptFilename); - }); - compilation.hooks.runtimeRequirementInTree - .for(RuntimeGlobals.hmrDownloadUpdateHandlers) - .tap("JsonpChunkLoadingPlugin", (chunk, set) => { - if (!isEnabledForChunk(chunk)) return; - set.add(RuntimeGlobals.publicPath); - set.add(RuntimeGlobals.loadScript); - set.add(RuntimeGlobals.getChunkUpdateScriptFilename); - set.add(RuntimeGlobals.moduleCache); - set.add(RuntimeGlobals.hmrModuleData); - set.add(RuntimeGlobals.moduleFactoriesAddOnly); + normalModuleFactory.hooks.createParser + .for("webassembly/async") + .tap("AsyncWebAssemblyModulesPlugin", () => { + const AsyncWebAssemblyParser = getAsyncWebAssemblyParser(); + + return new AsyncWebAssemblyParser(); }); - compilation.hooks.runtimeRequirementInTree - .for(RuntimeGlobals.hmrDownloadManifest) - .tap("JsonpChunkLoadingPlugin", (chunk, set) => { - if (!isEnabledForChunk(chunk)) return; - set.add(RuntimeGlobals.publicPath); - set.add(RuntimeGlobals.getUpdateManifestFilename); + normalModuleFactory.hooks.createGenerator + .for("webassembly/async") + .tap("AsyncWebAssemblyModulesPlugin", () => { + const AsyncWebAssemblyJavascriptGenerator = + getAsyncWebAssemblyJavascriptGenerator(); + const AsyncWebAssemblyGenerator = getAsyncWebAssemblyGenerator(); + + return Generator.byType({ + javascript: new AsyncWebAssemblyJavascriptGenerator( + compilation.outputOptions.webassemblyModuleFilename + ), + webassembly: new AsyncWebAssemblyGenerator(this.options) + }); }); + + compilation.hooks.renderManifest.tap( + "WebAssemblyModulesPlugin", + (result, options) => { + const { moduleGraph, chunkGraph, runtimeTemplate } = compilation; + const { + chunk, + outputOptions, + dependencyTemplates, + codeGenerationResults + } = options; + + for (const module of chunkGraph.getOrderedChunkModulesIterable( + chunk, + compareModulesByIdentifier + )) { + if (module.type === "webassembly/async") { + const filenameTemplate = + outputOptions.webassemblyModuleFilename; + + result.push({ + render: () => + this.renderModule( + module, + { + chunk, + dependencyTemplates, + runtimeTemplate, + moduleGraph, + chunkGraph, + codeGenerationResults + }, + hooks + ), + filenameTemplate, + pathOptions: { + module, + runtime: chunk.runtime, + chunkGraph + }, + auxiliary: true, + identifier: `webassemblyAsyncModule${chunkGraph.getModuleId( + module + )}`, + hash: chunkGraph.getModuleHash(module, chunk.runtime) + }); + } + } + + return result; + } + ); } ); } + + renderModule(module, renderContext, hooks) { + const { codeGenerationResults, chunk } = renderContext; + try { + const moduleSource = codeGenerationResults.getSource( + module, + chunk.runtime, + "webassembly" + ); + return tryRunOrWebpackError( + () => + hooks.renderModuleContent.call(moduleSource, module, renderContext), + "AsyncWebAssemblyModulesPlugin.getCompilationHooks().renderModuleContent" + ); + } catch (e) { + e.module = module; + throw e; + } + } } -module.exports = JsonpChunkLoadingPlugin; +module.exports = AsyncWebAssemblyModulesPlugin; /***/ }), -/***/ 66032: +/***/ 20595: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; /* MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra */ -const { SyncWaterfallHook } = __webpack_require__(34718); -const Compilation = __webpack_require__(59622); -const RuntimeGlobals = __webpack_require__(49404); -const RuntimeModule = __webpack_require__(61439); -const Template = __webpack_require__(92066); -const chunkHasJs = __webpack_require__(76767).chunkHasJs; -const { getInitialChunkIds } = __webpack_require__(30951); -const compileBooleanMatcher = __webpack_require__(356); +const t = __webpack_require__(98688); +const { decode } = __webpack_require__(8062); +const Parser = __webpack_require__(68214); +const StaticExportsDependency = __webpack_require__(67967); +const WebAssemblyImportDependency = __webpack_require__(97093); -/** @typedef {import("../Chunk")} Chunk */ +/** @typedef {import("../Parser").ParserState} ParserState */ +/** @typedef {import("../Parser").PreparsedAst} PreparsedAst */ -/** - * @typedef {Object} JsonpCompilationPluginHooks - * @property {SyncWaterfallHook<[string, Chunk]>} linkPreload - * @property {SyncWaterfallHook<[string, Chunk]>} linkPrefetch - */ +const decoderOpts = { + ignoreCodeSection: true, + ignoreDataSection: true, -/** @type {WeakMap} */ -const compilationHooksMap = new WeakMap(); + // this will avoid having to lookup with identifiers in the ModuleContext + ignoreCustomNameSection: true +}; + +class WebAssemblyParser extends Parser { + constructor(options) { + super(); + this.hooks = Object.freeze({}); + this.options = options; + } -class JsonpChunkLoadingRuntimeModule extends RuntimeModule { /** - * @param {Compilation} compilation the compilation - * @returns {JsonpCompilationPluginHooks} hooks + * @param {string | Buffer | PreparsedAst} source the source to parse + * @param {ParserState} state the parser state + * @returns {ParserState} the parser state */ - static getCompilationHooks(compilation) { - if (!(compilation instanceof Compilation)) { - throw new TypeError( - "The 'compilation' argument must be an instance of Compilation" - ); - } - let hooks = compilationHooksMap.get(compilation); - if (hooks === undefined) { - hooks = { - linkPreload: new SyncWaterfallHook(["source", "chunk"]), - linkPrefetch: new SyncWaterfallHook(["source", "chunk"]) - }; - compilationHooksMap.set(compilation, hooks); + parse(source, state) { + if (!Buffer.isBuffer(source)) { + throw new Error("WebAssemblyParser input must be a Buffer"); } - return hooks; - } - constructor(runtimeRequirements) { - super("jsonp chunk loading", RuntimeModule.STAGE_ATTACH); - this._runtimeRequirements = runtimeRequirements; - } + // flag it as async module + state.module.buildInfo.strict = true; + state.module.buildMeta.exportsType = "namespace"; + state.module.buildMeta.async = true; - /** - * @returns {string} runtime code - */ - generate() { - const { chunkGraph, compilation, chunk } = this; - const { - runtimeTemplate, - outputOptions: { - globalObject, - chunkLoadingGlobal, - hotUpdateGlobal, - crossOriginLoading, - scriptType + // parse it + const program = decode(source, decoderOpts); + const module = program.body[0]; + + const exports = []; + t.traverse(module, { + ModuleExport({ node }) { + exports.push(node.name); + }, + + ModuleImport({ node }) { + const dep = new WebAssemblyImportDependency( + node.module, + node.name, + node.descr, + false + ); + + state.module.addDependency(dep); } - } = compilation; - const { linkPreload, linkPrefetch } = - JsonpChunkLoadingRuntimeModule.getCompilationHooks(compilation); - const fn = RuntimeGlobals.ensureChunkHandlers; - const withBaseURI = this._runtimeRequirements.has(RuntimeGlobals.baseURI); - const withLoading = this._runtimeRequirements.has( - RuntimeGlobals.ensureChunkHandlers - ); - const withCallback = this._runtimeRequirements.has( - RuntimeGlobals.chunkCallback - ); - const withOnChunkLoad = this._runtimeRequirements.has( - RuntimeGlobals.onChunksLoaded - ); - const withHmr = this._runtimeRequirements.has( - RuntimeGlobals.hmrDownloadUpdateHandlers - ); - const withHmrManifest = this._runtimeRequirements.has( - RuntimeGlobals.hmrDownloadManifest - ); - const withPrefetch = this._runtimeRequirements.has( - RuntimeGlobals.prefetchChunkHandlers - ); - const withPreload = this._runtimeRequirements.has( - RuntimeGlobals.preloadChunkHandlers - ); - const chunkLoadingGlobalExpr = `${globalObject}[${JSON.stringify( - chunkLoadingGlobal - )}]`; - const conditionMap = chunkGraph.getChunkConditionMap(chunk, chunkHasJs); - const hasJsMatcher = compileBooleanMatcher(conditionMap); - const initialChunkIds = getInitialChunkIds(chunk, chunkGraph); + }); - const stateExpression = withHmr - ? `${RuntimeGlobals.hmrRuntimeStatePrefix}_jsonp` - : undefined; + state.module.addDependency(new StaticExportsDependency(exports, false)); - return Template.asString([ - withBaseURI - ? Template.asString([ - `${RuntimeGlobals.baseURI} = document.baseURI || self.location.href;` - ]) - : "// no baseURI", - "", - "// object to store loaded and loading chunks", - "// undefined = chunk not loaded, null = chunk preloaded/prefetched", - "// [resolve, reject, Promise] = chunk loading, 0 = chunk loaded", - `var installedChunks = ${ - stateExpression ? `${stateExpression} = ${stateExpression} || ` : "" - }{`, - Template.indent( - Array.from(initialChunkIds, id => `${JSON.stringify(id)}: 0`).join( - ",\n" - ) - ), - "};", - "", - withLoading - ? Template.asString([ - `${fn}.j = ${runtimeTemplate.basicFunction( - "chunkId, promises", - hasJsMatcher !== false - ? Template.indent([ - "// JSONP chunk loading for javascript", - `var installedChunkData = ${RuntimeGlobals.hasOwnProperty}(installedChunks, chunkId) ? installedChunks[chunkId] : undefined;`, - 'if(installedChunkData !== 0) { // 0 means "already installed".', - Template.indent([ - "", - '// a Promise means "currently loading".', - "if(installedChunkData) {", - Template.indent([ - "promises.push(installedChunkData[2]);" - ]), - "} else {", - Template.indent([ - hasJsMatcher === true - ? "if(true) { // all chunks have JS" - : `if(${hasJsMatcher("chunkId")}) {`, - Template.indent([ - "// setup Promise in chunk cache", - `var promise = new Promise(${runtimeTemplate.expressionFunction( - `installedChunkData = installedChunks[chunkId] = [resolve, reject]`, - "resolve, reject" - )});`, - "promises.push(installedChunkData[2] = promise);", - "", - "// start chunk loading", - `var url = ${RuntimeGlobals.publicPath} + ${RuntimeGlobals.getChunkScriptFilename}(chunkId);`, - "// create error before stack unwound to get useful stacktrace later", - "var error = new Error();", - `var loadingEnded = ${runtimeTemplate.basicFunction( - "event", - [ - `if(${RuntimeGlobals.hasOwnProperty}(installedChunks, chunkId)) {`, - Template.indent([ - "installedChunkData = installedChunks[chunkId];", - "if(installedChunkData !== 0) installedChunks[chunkId] = undefined;", - "if(installedChunkData) {", - Template.indent([ - "var errorType = event && (event.type === 'load' ? 'missing' : event.type);", - "var realSrc = event && event.target && event.target.src;", - "error.message = 'Loading chunk ' + chunkId + ' failed.\\n(' + errorType + ': ' + realSrc + ')';", - "error.name = 'ChunkLoadError';", - "error.type = errorType;", - "error.request = realSrc;", - "installedChunkData[1](error);" - ]), - "}" - ]), - "}" - ] - )};`, - `${RuntimeGlobals.loadScript}(url, loadingEnded, "chunk-" + chunkId, chunkId);` - ]), - "} else installedChunks[chunkId] = 0;" - ]), - "}" - ]), - "}" - ]) - : Template.indent(["installedChunks[chunkId] = 0;"]) - )};` - ]) - : "// no chunk on demand loading", - "", - withPrefetch && hasJsMatcher !== false - ? `${ - RuntimeGlobals.prefetchChunkHandlers - }.j = ${runtimeTemplate.basicFunction("chunkId", [ - `if((!${ - RuntimeGlobals.hasOwnProperty - }(installedChunks, chunkId) || installedChunks[chunkId] === undefined) && ${ - hasJsMatcher === true ? "true" : hasJsMatcher("chunkId") - }) {`, - Template.indent([ - "installedChunks[chunkId] = null;", - linkPrefetch.call( - Template.asString([ - "var link = document.createElement('link');", - crossOriginLoading - ? `link.crossOrigin = ${JSON.stringify( - crossOriginLoading - )};` - : "", - `if (${RuntimeGlobals.scriptNonce}) {`, - Template.indent( - `link.setAttribute("nonce", ${RuntimeGlobals.scriptNonce});` - ), - "}", - 'link.rel = "prefetch";', - 'link.as = "script";', - `link.href = ${RuntimeGlobals.publicPath} + ${RuntimeGlobals.getChunkScriptFilename}(chunkId);` - ]), - chunk - ), - "document.head.appendChild(link);" - ]), - "}" - ])};` - : "// no prefetching", - "", - withPreload && hasJsMatcher !== false - ? `${ - RuntimeGlobals.preloadChunkHandlers - }.j = ${runtimeTemplate.basicFunction("chunkId", [ - `if((!${ - RuntimeGlobals.hasOwnProperty - }(installedChunks, chunkId) || installedChunks[chunkId] === undefined) && ${ - hasJsMatcher === true ? "true" : hasJsMatcher("chunkId") - }) {`, - Template.indent([ - "installedChunks[chunkId] = null;", - linkPreload.call( - Template.asString([ - "var link = document.createElement('link');", - scriptType - ? `link.type = ${JSON.stringify(scriptType)};` - : "", - "link.charset = 'utf-8';", - `if (${RuntimeGlobals.scriptNonce}) {`, - Template.indent( - `link.setAttribute("nonce", ${RuntimeGlobals.scriptNonce});` - ), - "}", - 'link.rel = "preload";', - 'link.as = "script";', - `link.href = ${RuntimeGlobals.publicPath} + ${RuntimeGlobals.getChunkScriptFilename}(chunkId);`, - crossOriginLoading - ? Template.asString([ - "if (link.href.indexOf(window.location.origin + '/') !== 0) {", - Template.indent( - `link.crossOrigin = ${JSON.stringify( - crossOriginLoading - )};` - ), - "}" - ]) - : "" - ]), - chunk - ), - "document.head.appendChild(link);" - ]), - "}" - ])};` - : "// no preloaded", - "", - withHmr - ? Template.asString([ - "var currentUpdatedModulesList;", - "var waitingUpdateResolves = {};", - "function loadUpdateChunk(chunkId) {", - Template.indent([ - `return new Promise(${runtimeTemplate.basicFunction( - "resolve, reject", - [ - "waitingUpdateResolves[chunkId] = resolve;", - "// start update chunk loading", - `var url = ${RuntimeGlobals.publicPath} + ${RuntimeGlobals.getChunkUpdateScriptFilename}(chunkId);`, - "// create error before stack unwound to get useful stacktrace later", - "var error = new Error();", - `var loadingEnded = ${runtimeTemplate.basicFunction("event", [ - "if(waitingUpdateResolves[chunkId]) {", - Template.indent([ - "waitingUpdateResolves[chunkId] = undefined", - "var errorType = event && (event.type === 'load' ? 'missing' : event.type);", - "var realSrc = event && event.target && event.target.src;", - "error.message = 'Loading hot update chunk ' + chunkId + ' failed.\\n(' + errorType + ': ' + realSrc + ')';", - "error.name = 'ChunkLoadError';", - "error.type = errorType;", - "error.request = realSrc;", - "reject(error);" - ]), - "}" - ])};`, - `${RuntimeGlobals.loadScript}(url, loadingEnded);` - ] - )});` - ]), - "}", - "", - `${globalObject}[${JSON.stringify( - hotUpdateGlobal - )}] = ${runtimeTemplate.basicFunction( - "chunkId, moreModules, runtime", - [ - "for(var moduleId in moreModules) {", - Template.indent([ - `if(${RuntimeGlobals.hasOwnProperty}(moreModules, moduleId)) {`, - Template.indent([ - "currentUpdate[moduleId] = moreModules[moduleId];", - "if(currentUpdatedModulesList) currentUpdatedModulesList.push(moduleId);" - ]), - "}" - ]), - "}", - "if(runtime) currentUpdateRuntime.push(runtime);", - "if(waitingUpdateResolves[chunkId]) {", - Template.indent([ - "waitingUpdateResolves[chunkId]();", - "waitingUpdateResolves[chunkId] = undefined;" - ]), - "}" - ] - )};`, - "", - Template.getFunctionContent( - require('./JavascriptHotModuleReplacement.runtime.js') - ) - .replace(/\$key\$/g, "jsonp") - .replace(/\$installedChunks\$/g, "installedChunks") - .replace(/\$loadUpdateChunk\$/g, "loadUpdateChunk") - .replace(/\$moduleCache\$/g, RuntimeGlobals.moduleCache) - .replace(/\$moduleFactories\$/g, RuntimeGlobals.moduleFactories) - .replace( - /\$ensureChunkHandlers\$/g, - RuntimeGlobals.ensureChunkHandlers - ) - .replace(/\$hasOwnProperty\$/g, RuntimeGlobals.hasOwnProperty) - .replace(/\$hmrModuleData\$/g, RuntimeGlobals.hmrModuleData) - .replace( - /\$hmrDownloadUpdateHandlers\$/g, - RuntimeGlobals.hmrDownloadUpdateHandlers - ) - .replace( - /\$hmrInvalidateModuleHandlers\$/g, - RuntimeGlobals.hmrInvalidateModuleHandlers - ) - ]) - : "// no HMR", - "", - withHmrManifest - ? Template.asString([ - `${ - RuntimeGlobals.hmrDownloadManifest - } = ${runtimeTemplate.basicFunction("", [ - 'if (typeof fetch === "undefined") throw new Error("No browser support: need fetch API");', - `return fetch(${RuntimeGlobals.publicPath} + ${ - RuntimeGlobals.getUpdateManifestFilename - }()).then(${runtimeTemplate.basicFunction("response", [ - "if(response.status === 404) return; // no update available", - 'if(!response.ok) throw new Error("Failed to fetch update manifest " + response.statusText);', - "return response.json();" - ])});` - ])};` - ]) - : "// no HMR manifest", - "", - withOnChunkLoad - ? `${ - RuntimeGlobals.onChunksLoaded - }.j = ${runtimeTemplate.returningFunction( - "installedChunks[chunkId] === 0", - "chunkId" - )};` - : "// no on chunks loaded", - "", - withCallback || withLoading - ? Template.asString([ - "// install a JSONP callback for chunk loading", - `var webpackJsonpCallback = ${runtimeTemplate.basicFunction( - "parentChunkLoadingFunction, data", - [ - runtimeTemplate.destructureArray( - ["chunkIds", "moreModules", "runtime"], - "data" - ), - '// add "moreModules" to the modules object,', - '// then flag all "chunkIds" as loaded and fire callback', - "var moduleId, chunkId, i = 0;", - `if(chunkIds.some(${runtimeTemplate.returningFunction( - "installedChunks[id] !== 0", - "id" - )})) {`, - Template.indent([ - "for(moduleId in moreModules) {", - Template.indent([ - `if(${RuntimeGlobals.hasOwnProperty}(moreModules, moduleId)) {`, - Template.indent( - `${RuntimeGlobals.moduleFactories}[moduleId] = moreModules[moduleId];` - ), - "}" - ]), - "}", - "if(runtime) var result = runtime(__webpack_require__);" - ]), - "}", - "if(parentChunkLoadingFunction) parentChunkLoadingFunction(data);", - "for(;i < chunkIds.length; i++) {", - Template.indent([ - "chunkId = chunkIds[i];", - `if(${RuntimeGlobals.hasOwnProperty}(installedChunks, chunkId) && installedChunks[chunkId]) {`, - Template.indent("installedChunks[chunkId][0]();"), - "}", - "installedChunks[chunkIds[i]] = 0;" - ]), - "}", - withOnChunkLoad - ? `return ${RuntimeGlobals.onChunksLoaded}(result);` - : "" - ] - )}`, - "", - `var chunkLoadingGlobal = ${chunkLoadingGlobalExpr} = ${chunkLoadingGlobalExpr} || [];`, - "chunkLoadingGlobal.forEach(webpackJsonpCallback.bind(null, 0));", - "chunkLoadingGlobal.push = webpackJsonpCallback.bind(null, chunkLoadingGlobal.push.bind(chunkLoadingGlobal));" - ]) - : "// no jsonp function" - ]); + return state; } } -module.exports = JsonpChunkLoadingRuntimeModule; +module.exports = WebAssemblyParser; /***/ }), -/***/ 45968: +/***/ 13475: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; /* MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ - - +*/ -const ArrayPushCallbackChunkFormatPlugin = __webpack_require__(86189); -const EnableChunkLoadingPlugin = __webpack_require__(34726); -const JsonpChunkLoadingRuntimeModule = __webpack_require__(66032); -/** @typedef {import("../Chunk")} Chunk */ -/** @typedef {import("../Compilation")} Compilation */ -/** @typedef {import("../Compiler")} Compiler */ -class JsonpTemplatePlugin { - /** - * @deprecated use JsonpChunkLoadingRuntimeModule.getCompilationHooks instead - * @param {Compilation} compilation the compilation - * @returns {JsonpChunkLoadingRuntimeModule.JsonpCompilationPluginHooks} hooks - */ - static getCompilationHooks(compilation) { - return JsonpChunkLoadingRuntimeModule.getCompilationHooks(compilation); - } +const WebpackError = __webpack_require__(68422); - /** - * Apply the plugin - * @param {Compiler} compiler the compiler instance - * @returns {void} - */ - apply(compiler) { - compiler.options.output.chunkLoading = "jsonp"; - new ArrayPushCallbackChunkFormatPlugin().apply(compiler); - new EnableChunkLoadingPlugin("jsonp").apply(compiler); +module.exports = class UnsupportedWebAssemblyFeatureError extends WebpackError { + /** @param {string} message Error message */ + constructor(message) { + super(message); + this.name = "UnsupportedWebAssemblyFeatureError"; + this.hideStack = true; } -} - -module.exports = JsonpTemplatePlugin; +}; /***/ }), -/***/ 86128: +/***/ 92153: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; /* MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra */ -const util = __webpack_require__(31669); -const webpackOptionsSchemaCheck = __webpack_require__(97220); -const webpackOptionsSchema = __webpack_require__(1863); -const Compiler = __webpack_require__(11777); -const MultiCompiler = __webpack_require__(73663); -const WebpackOptionsApply = __webpack_require__(44137); -const { - applyWebpackOptionsDefaults, - applyWebpackOptionsBaseDefaults -} = __webpack_require__(27057); -const { getNormalizedWebpackOptions } = __webpack_require__(52975); -const NodeEnvironmentPlugin = __webpack_require__(38857); -const memoize = __webpack_require__(84297); +const RuntimeGlobals = __webpack_require__(49404); +const RuntimeModule = __webpack_require__(61439); +const Template = __webpack_require__(92066); +const { compareModulesByIdentifier } = __webpack_require__(26296); +const WebAssemblyUtils = __webpack_require__(41520); -/** @typedef {import("../declarations/WebpackOptions").WebpackOptions} WebpackOptions */ -/** @typedef {import("./Compiler").WatchOptions} WatchOptions */ -/** @typedef {import("./MultiCompiler").MultiCompilerOptions} MultiCompilerOptions */ -/** @typedef {import("./MultiStats")} MultiStats */ -/** @typedef {import("./Stats")} Stats */ +/** @typedef {import("../ChunkGraph")} ChunkGraph */ +/** @typedef {import("../Compilation")} Compilation */ +/** @typedef {import("../Module")} Module */ +/** @typedef {import("../util/runtime").RuntimeSpec} RuntimeSpec */ -const getValidateSchema = memoize(() => __webpack_require__(55959)); +// TODO webpack 6 remove the whole folder -/** - * @template T - * @callback Callback - * @param {Error=} err - * @param {T=} stats - * @returns {void} - */ +// Get all wasm modules +const getAllWasmModules = (moduleGraph, chunkGraph, chunk) => { + const wasmModules = chunk.getAllAsyncChunks(); + const array = []; + for (const chunk of wasmModules) { + for (const m of chunkGraph.getOrderedChunkModulesIterable( + chunk, + compareModulesByIdentifier + )) { + if (m.type.startsWith("webassembly")) { + array.push(m); + } + } + } + + return array; +}; /** - * @param {ReadonlyArray} childOptions options array - * @param {MultiCompilerOptions} options options - * @returns {MultiCompiler} a multi-compiler + * generates the import object function for a module + * @param {ChunkGraph} chunkGraph the chunk graph + * @param {Module} module the module + * @param {boolean} mangle mangle imports + * @param {string[]} declarations array where declarations are pushed to + * @param {RuntimeSpec} runtime the runtime + * @returns {string} source code */ -const createMultiCompiler = (childOptions, options) => { - const compilers = childOptions.map(options => createCompiler(options)); - const compiler = new MultiCompiler(compilers, options); - for (const childCompiler of compilers) { - if (childCompiler.options.dependencies) { - compiler.setDependencies( - childCompiler, - childCompiler.options.dependencies +const generateImportObject = ( + chunkGraph, + module, + mangle, + declarations, + runtime +) => { + const moduleGraph = chunkGraph.moduleGraph; + const waitForInstances = new Map(); + const properties = []; + const usedWasmDependencies = WebAssemblyUtils.getUsedDependencies( + moduleGraph, + module, + mangle + ); + for (const usedDep of usedWasmDependencies) { + const dep = usedDep.dependency; + const importedModule = moduleGraph.getModule(dep); + const exportName = dep.name; + const usedName = + importedModule && + moduleGraph + .getExportsInfo(importedModule) + .getUsedName(exportName, runtime); + const description = dep.description; + const direct = dep.onlyDirectImport; + + const module = usedDep.module; + const name = usedDep.name; + + if (direct) { + const instanceVar = `m${waitForInstances.size}`; + waitForInstances.set(instanceVar, chunkGraph.getModuleId(importedModule)); + properties.push({ + module, + name, + value: `${instanceVar}[${JSON.stringify(usedName)}]` + }); + } else { + const params = description.signature.params.map( + (param, k) => "p" + k + param.valtype ); + + const mod = `${RuntimeGlobals.moduleCache}[${JSON.stringify( + chunkGraph.getModuleId(importedModule) + )}]`; + const modExports = `${mod}.exports`; + + const cache = `wasmImportedFuncCache${declarations.length}`; + declarations.push(`var ${cache};`); + + properties.push({ + module, + name, + value: Template.asString([ + (importedModule.type.startsWith("webassembly") + ? `${mod} ? ${modExports}[${JSON.stringify(usedName)}] : ` + : "") + `function(${params}) {`, + Template.indent([ + `if(${cache} === undefined) ${cache} = ${modExports};`, + `return ${cache}[${JSON.stringify(usedName)}](${params});` + ]), + "}" + ]) + }); } } - return compiler; -}; -/** - * @param {WebpackOptions} rawOptions options object - * @returns {Compiler} a compiler - */ -const createCompiler = rawOptions => { - const options = getNormalizedWebpackOptions(rawOptions); - applyWebpackOptionsBaseDefaults(options); - const compiler = new Compiler(options.context, options); - new NodeEnvironmentPlugin({ - infrastructureLogging: options.infrastructureLogging - }).apply(compiler); - if (Array.isArray(options.plugins)) { - for (const plugin of options.plugins) { - if (typeof plugin === "function") { - plugin.call(compiler, compiler); - } else { - plugin.apply(compiler); + let importObject; + if (mangle) { + importObject = [ + "return {", + Template.indent([ + properties.map(p => `${JSON.stringify(p.name)}: ${p.value}`).join(",\n") + ]), + "};" + ]; + } else { + const propertiesByModule = new Map(); + for (const p of properties) { + let list = propertiesByModule.get(p.module); + if (list === undefined) { + propertiesByModule.set(p.module, (list = [])); } + list.push(p); } + importObject = [ + "return {", + Template.indent([ + Array.from(propertiesByModule, ([module, list]) => { + return Template.asString([ + `${JSON.stringify(module)}: {`, + Template.indent([ + list.map(p => `${JSON.stringify(p.name)}: ${p.value}`).join(",\n") + ]), + "}" + ]); + }).join(",\n") + ]), + "};" + ]; } - applyWebpackOptionsDefaults(options); - compiler.hooks.environment.call(); - compiler.hooks.afterEnvironment.call(); - new WebpackOptionsApply().process(options, compiler); - compiler.hooks.initialize.call(); - return compiler; -}; - -/** - * @callback WebpackFunctionSingle - * @param {WebpackOptions} options options object - * @param {Callback=} callback callback - * @returns {Compiler} the compiler object - */ -/** - * @callback WebpackFunctionMulti - * @param {ReadonlyArray & MultiCompilerOptions} options options objects - * @param {Callback=} callback callback - * @returns {MultiCompiler} the multi compiler object - */ + const moduleIdStringified = JSON.stringify(chunkGraph.getModuleId(module)); + if (waitForInstances.size === 1) { + const moduleId = Array.from(waitForInstances.values())[0]; + const promise = `installedWasmModules[${JSON.stringify(moduleId)}]`; + const variable = Array.from(waitForInstances.keys())[0]; + return Template.asString([ + `${moduleIdStringified}: function() {`, + Template.indent([ + `return promiseResolve().then(function() { return ${promise}; }).then(function(${variable}) {`, + Template.indent(importObject), + "});" + ]), + "}," + ]); + } else if (waitForInstances.size > 0) { + const promises = Array.from( + waitForInstances.values(), + id => `installedWasmModules[${JSON.stringify(id)}]` + ).join(", "); + const variables = Array.from( + waitForInstances.keys(), + (name, i) => `${name} = array[${i}]` + ).join(", "); + return Template.asString([ + `${moduleIdStringified}: function() {`, + Template.indent([ + `return promiseResolve().then(function() { return Promise.all([${promises}]); }).then(function(array) {`, + Template.indent([`var ${variables};`, ...importObject]), + "});" + ]), + "}," + ]); + } else { + return Template.asString([ + `${moduleIdStringified}: function() {`, + Template.indent(importObject), + "}," + ]); + } +}; -const asArray = options => - Array.isArray(options) ? Array.from(options) : [options]; +class WasmChunkLoadingRuntimeModule extends RuntimeModule { + constructor({ + generateLoadBinaryCode, + supportsStreaming, + mangleImports, + runtimeRequirements + }) { + super("wasm chunk loading", RuntimeModule.STAGE_ATTACH); + this.generateLoadBinaryCode = generateLoadBinaryCode; + this.supportsStreaming = supportsStreaming; + this.mangleImports = mangleImports; + this._runtimeRequirements = runtimeRequirements; + } -const webpack = /** @type {WebpackFunctionSingle & WebpackFunctionMulti} */ ( /** - * @param {WebpackOptions | (ReadonlyArray & MultiCompilerOptions)} options options - * @param {Callback & Callback=} callback callback - * @returns {Compiler | MultiCompiler} + * @returns {string} runtime code */ - (options, callback) => { - const create = () => { - if (!asArray(options).every(webpackOptionsSchemaCheck)) { - getValidateSchema()(webpackOptionsSchema, options); - util.deprecate( - () => {}, - "webpack bug: Pre-compiled schema reports error while real schema is happy. This has performance drawbacks.", - "DEP_WEBPACK_PRE_COMPILED_SCHEMA_INVALID" - )(); - } - /** @type {MultiCompiler|Compiler} */ - let compiler; - let watch = false; - /** @type {WatchOptions|WatchOptions[]} */ - let watchOptions; - if (Array.isArray(options)) { - /** @type {MultiCompiler} */ - compiler = createMultiCompiler( - options, - /** @type {MultiCompilerOptions} */ (options) - ); - watch = options.some(options => options.watch); - watchOptions = options.map(options => options.watchOptions || {}); - } else { - const webpackOptions = /** @type {WebpackOptions} */ (options); - /** @type {Compiler} */ - compiler = createCompiler(webpackOptions); - watch = webpackOptions.watch; - watchOptions = webpackOptions.watchOptions || {}; - } - return { compiler, watch, watchOptions }; - }; - if (callback) { - try { - const { compiler, watch, watchOptions } = create(); - if (watch) { - compiler.watch(watchOptions, callback); - } else { - compiler.run((err, stats) => { - compiler.close(err2 => { - callback(err || err2, stats); - }); - }); - } - return compiler; - } catch (err) { - process.nextTick(() => callback(err)); - return null; - } - } else { - const { compiler, watch } = create(); - if (watch) { - util.deprecate( - () => {}, - "A 'callback' argument needs to be provided to the 'webpack(options, callback)' function when the 'watch' option is set. There is no way to handle the 'watch' option without a callback.", - "DEP_WEBPACK_WATCH_WITHOUT_CALLBACK" - )(); + generate() { + const { chunkGraph, compilation, chunk, mangleImports } = this; + const { moduleGraph, outputOptions } = compilation; + const fn = RuntimeGlobals.ensureChunkHandlers; + const withHmr = this._runtimeRequirements.has( + RuntimeGlobals.hmrDownloadUpdateHandlers + ); + const wasmModules = getAllWasmModules(moduleGraph, chunkGraph, chunk); + const declarations = []; + const importObjects = wasmModules.map(module => { + return generateImportObject( + chunkGraph, + module, + this.mangleImports, + declarations, + chunk.runtime + ); + }); + const chunkModuleIdMap = chunkGraph.getChunkModuleIdMap(chunk, m => + m.type.startsWith("webassembly") + ); + const createImportObject = content => + mangleImports + ? `{ ${JSON.stringify(WebAssemblyUtils.MANGLED_MODULE)}: ${content} }` + : content; + const wasmModuleSrcPath = compilation.getPath( + JSON.stringify(outputOptions.webassemblyModuleFilename), + { + hash: `" + ${RuntimeGlobals.getFullHash}() + "`, + hashWithLength: length => + `" + ${RuntimeGlobals.getFullHash}}().slice(0, ${length}) + "`, + module: { + id: '" + wasmModuleId + "', + hash: `" + ${JSON.stringify( + chunkGraph.getChunkModuleRenderedHashMap(chunk, m => + m.type.startsWith("webassembly") + ) + )}[chunkId][wasmModuleId] + "`, + hashWithLength(length) { + return `" + ${JSON.stringify( + chunkGraph.getChunkModuleRenderedHashMap( + chunk, + m => m.type.startsWith("webassembly"), + length + ) + )}[chunkId][wasmModuleId] + "`; + } + }, + runtime: chunk.runtime } - return compiler; - } + ); + + const stateExpression = withHmr + ? `${RuntimeGlobals.hmrRuntimeStatePrefix}_wasm` + : undefined; + + return Template.asString([ + "// object to store loaded and loading wasm modules", + `var installedWasmModules = ${ + stateExpression ? `${stateExpression} = ${stateExpression} || ` : "" + }{};`, + "", + // This function is used to delay reading the installed wasm module promises + // by a microtask. Sorting them doesn't help because there are edge cases where + // sorting is not possible (modules splitted into different chunks). + // So we not even trying and solve this by a microtask delay. + "function promiseResolve() { return Promise.resolve(); }", + "", + Template.asString(declarations), + "var wasmImportObjects = {", + Template.indent(importObjects), + "};", + "", + `var wasmModuleMap = ${JSON.stringify( + chunkModuleIdMap, + undefined, + "\t" + )};`, + "", + "// object with all WebAssembly.instance exports", + `${RuntimeGlobals.wasmInstances} = {};`, + "", + "// Fetch + compile chunk loading for webassembly", + `${fn}.wasm = function(chunkId, promises) {`, + Template.indent([ + "", + `var wasmModules = wasmModuleMap[chunkId] || [];`, + "", + "wasmModules.forEach(function(wasmModuleId, idx) {", + Template.indent([ + "var installedWasmModuleData = installedWasmModules[wasmModuleId];", + "", + '// a Promise means "currently loading" or "already loaded".', + "if(installedWasmModuleData)", + Template.indent(["promises.push(installedWasmModuleData);"]), + "else {", + Template.indent([ + `var importObject = wasmImportObjects[wasmModuleId]();`, + `var req = ${this.generateLoadBinaryCode(wasmModuleSrcPath)};`, + "var promise;", + this.supportsStreaming + ? Template.asString([ + "if(importObject && typeof importObject.then === 'function' && typeof WebAssembly.compileStreaming === 'function') {", + Template.indent([ + "promise = Promise.all([WebAssembly.compileStreaming(req), importObject]).then(function(items) {", + Template.indent([ + `return WebAssembly.instantiate(items[0], ${createImportObject( + "items[1]" + )});` + ]), + "});" + ]), + "} else if(typeof WebAssembly.instantiateStreaming === 'function') {", + Template.indent([ + `promise = WebAssembly.instantiateStreaming(req, ${createImportObject( + "importObject" + )});` + ]) + ]) + : Template.asString([ + "if(importObject && typeof importObject.then === 'function') {", + Template.indent([ + "var bytesPromise = req.then(function(x) { return x.arrayBuffer(); });", + "promise = Promise.all([", + Template.indent([ + "bytesPromise.then(function(bytes) { return WebAssembly.compile(bytes); }),", + "importObject" + ]), + "]).then(function(items) {", + Template.indent([ + `return WebAssembly.instantiate(items[0], ${createImportObject( + "items[1]" + )});` + ]), + "});" + ]) + ]), + "} else {", + Template.indent([ + "var bytesPromise = req.then(function(x) { return x.arrayBuffer(); });", + "promise = bytesPromise.then(function(bytes) {", + Template.indent([ + `return WebAssembly.instantiate(bytes, ${createImportObject( + "importObject" + )});` + ]), + "});" + ]), + "}", + "promises.push(installedWasmModules[wasmModuleId] = promise.then(function(res) {", + Template.indent([ + `return ${RuntimeGlobals.wasmInstances}[wasmModuleId] = (res.instance || res).exports;` + ]), + "}));" + ]), + "}" + ]), + "});" + ]), + "};" + ]); } -); +} -module.exports = webpack; +module.exports = WasmChunkLoadingRuntimeModule; /***/ }), -/***/ 56354: +/***/ 12995: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; @@ -134317,646 +133758,709 @@ module.exports = webpack; -const RuntimeGlobals = __webpack_require__(49404); -const CreateScriptUrlRuntimeModule = __webpack_require__(41690); -const StartupChunkDependenciesPlugin = __webpack_require__(23613); -const ImportScriptsChunkLoadingRuntimeModule = __webpack_require__(45936); +const formatLocation = __webpack_require__(57261); +const UnsupportedWebAssemblyFeatureError = __webpack_require__(13475); /** @typedef {import("../Compiler")} Compiler */ -class ImportScriptsChunkLoadingPlugin { +class WasmFinalizeExportsPlugin { /** * Apply the plugin * @param {Compiler} compiler the compiler instance * @returns {void} */ apply(compiler) { - new StartupChunkDependenciesPlugin({ - chunkLoading: "import-scripts", - asyncChunkLoading: true - }).apply(compiler); - compiler.hooks.thisCompilation.tap( - "ImportScriptsChunkLoadingPlugin", - compilation => { - const globalChunkLoading = compilation.outputOptions.chunkLoading; - const isEnabledForChunk = chunk => { - const options = chunk.getEntryOptions(); - const chunkLoading = - options && options.chunkLoading !== undefined - ? options.chunkLoading - : globalChunkLoading; - return chunkLoading === "import-scripts"; - }; - const onceForChunkSet = new WeakSet(); - const handler = (chunk, set) => { - if (onceForChunkSet.has(chunk)) return; - onceForChunkSet.add(chunk); - if (!isEnabledForChunk(chunk)) return; - const withCreateScriptUrl = !!compilation.outputOptions.trustedTypes; - set.add(RuntimeGlobals.moduleFactoriesAddOnly); - set.add(RuntimeGlobals.hasOwnProperty); - if (withCreateScriptUrl) set.add(RuntimeGlobals.createScriptUrl); - compilation.addRuntimeModule( - chunk, - new ImportScriptsChunkLoadingRuntimeModule(set, withCreateScriptUrl) - ); - }; - compilation.hooks.runtimeRequirementInTree - .for(RuntimeGlobals.ensureChunkHandlers) - .tap("ImportScriptsChunkLoadingPlugin", handler); - compilation.hooks.runtimeRequirementInTree - .for(RuntimeGlobals.hmrDownloadUpdateHandlers) - .tap("ImportScriptsChunkLoadingPlugin", handler); - compilation.hooks.runtimeRequirementInTree - .for(RuntimeGlobals.hmrDownloadManifest) - .tap("ImportScriptsChunkLoadingPlugin", handler); - compilation.hooks.runtimeRequirementInTree - .for(RuntimeGlobals.baseURI) - .tap("ImportScriptsChunkLoadingPlugin", handler); - compilation.hooks.runtimeRequirementInTree - .for(RuntimeGlobals.createScriptUrl) - .tap("RuntimePlugin", (chunk, set) => { - compilation.addRuntimeModule( - chunk, - new CreateScriptUrlRuntimeModule() - ); - return true; - }); + compiler.hooks.compilation.tap("WasmFinalizeExportsPlugin", compilation => { + compilation.hooks.finishModules.tap( + "WasmFinalizeExportsPlugin", + modules => { + for (const module of modules) { + // 1. if a WebAssembly module + if (module.type.startsWith("webassembly") === true) { + const jsIncompatibleExports = + module.buildMeta.jsIncompatibleExports; - compilation.hooks.runtimeRequirementInTree - .for(RuntimeGlobals.ensureChunkHandlers) - .tap("ImportScriptsChunkLoadingPlugin", (chunk, set) => { - if (!isEnabledForChunk(chunk)) return; - set.add(RuntimeGlobals.publicPath); - set.add(RuntimeGlobals.getChunkScriptFilename); - }); - compilation.hooks.runtimeRequirementInTree - .for(RuntimeGlobals.hmrDownloadUpdateHandlers) - .tap("ImportScriptsChunkLoadingPlugin", (chunk, set) => { - if (!isEnabledForChunk(chunk)) return; - set.add(RuntimeGlobals.publicPath); - set.add(RuntimeGlobals.getChunkUpdateScriptFilename); - set.add(RuntimeGlobals.moduleCache); - set.add(RuntimeGlobals.hmrModuleData); - set.add(RuntimeGlobals.moduleFactoriesAddOnly); - }); - compilation.hooks.runtimeRequirementInTree - .for(RuntimeGlobals.hmrDownloadManifest) - .tap("ImportScriptsChunkLoadingPlugin", (chunk, set) => { - if (!isEnabledForChunk(chunk)) return; - set.add(RuntimeGlobals.publicPath); - set.add(RuntimeGlobals.getUpdateManifestFilename); - }); - } - ); + if (jsIncompatibleExports === undefined) { + continue; + } + + for (const connection of compilation.moduleGraph.getIncomingConnections( + module + )) { + // 2. is active and referenced by a non-WebAssembly module + if ( + connection.isTargetActive(undefined) && + connection.originModule.type.startsWith("webassembly") === + false + ) { + const referencedExports = + compilation.getDependencyReferencedExports( + connection.dependency, + undefined + ); + + for (const info of referencedExports) { + const names = Array.isArray(info) ? info : info.name; + if (names.length === 0) continue; + const name = names[0]; + if (typeof name === "object") continue; + // 3. and uses a func with an incompatible JS signature + if ( + Object.prototype.hasOwnProperty.call( + jsIncompatibleExports, + name + ) + ) { + // 4. error + const error = new UnsupportedWebAssemblyFeatureError( + `Export "${name}" with ${jsIncompatibleExports[name]} can only be used for direct wasm to wasm dependencies\n` + + `It's used from ${connection.originModule.readableIdentifier( + compilation.requestShortener + )} at ${formatLocation(connection.dependency.loc)}.` + ); + error.module = module; + compilation.errors.push(error); + } + } + } + } + } + } + } + ); + }); } } -module.exports = ImportScriptsChunkLoadingPlugin; + +module.exports = WasmFinalizeExportsPlugin; /***/ }), -/***/ 45936: +/***/ 35303: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; /* MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra */ -const RuntimeGlobals = __webpack_require__(49404); -const RuntimeModule = __webpack_require__(61439); -const Template = __webpack_require__(92066); -const { - getChunkFilenameTemplate, - chunkHasJs -} = __webpack_require__(76767); -const { getInitialChunkIds } = __webpack_require__(30951); -const compileBooleanMatcher = __webpack_require__(356); -const { getUndoPath } = __webpack_require__(96236); +const { RawSource } = __webpack_require__(96192); +const Generator = __webpack_require__(1826); +const WebAssemblyUtils = __webpack_require__(41520); -class ImportScriptsChunkLoadingRuntimeModule extends RuntimeModule { - constructor(runtimeRequirements, withCreateScriptUrl) { - super("importScripts chunk loading", RuntimeModule.STAGE_ATTACH); - this.runtimeRequirements = runtimeRequirements; - this._withCreateScriptUrl = withCreateScriptUrl; - } +const t = __webpack_require__(98688); +const { moduleContextFromModuleAST } = __webpack_require__(98688); +const { editWithAST, addWithAST } = __webpack_require__(65584); +const { decode } = __webpack_require__(8062); - /** - * @returns {string} runtime code - */ - generate() { - const { - chunk, - chunkGraph, - compilation: { - runtimeTemplate, - outputOptions: { globalObject, chunkLoadingGlobal, hotUpdateGlobal } - }, - _withCreateScriptUrl: withCreateScriptUrl - } = this; - const fn = RuntimeGlobals.ensureChunkHandlers; - const withBaseURI = this.runtimeRequirements.has(RuntimeGlobals.baseURI); - const withLoading = this.runtimeRequirements.has( - RuntimeGlobals.ensureChunkHandlers - ); - const withHmr = this.runtimeRequirements.has( - RuntimeGlobals.hmrDownloadUpdateHandlers - ); - const withHmrManifest = this.runtimeRequirements.has( - RuntimeGlobals.hmrDownloadManifest - ); - const chunkLoadingGlobalExpr = `${globalObject}[${JSON.stringify( - chunkLoadingGlobal - )}]`; - const hasJsMatcher = compileBooleanMatcher( - chunkGraph.getChunkConditionMap(chunk, chunkHasJs) - ); - const initialChunkIds = getInitialChunkIds(chunk, chunkGraph); +const WebAssemblyExportImportedDependency = __webpack_require__(18248); - const outputName = this.compilation.getPath( - getChunkFilenameTemplate(chunk, this.compilation.outputOptions), - { - chunk, - contentHashType: "javascript" +/** @typedef {import("webpack-sources").Source} Source */ +/** @typedef {import("../DependencyTemplates")} DependencyTemplates */ +/** @typedef {import("../Generator").GenerateContext} GenerateContext */ +/** @typedef {import("../Module")} Module */ +/** @typedef {import("../ModuleGraph")} ModuleGraph */ +/** @typedef {import("../NormalModule")} NormalModule */ +/** @typedef {import("../RuntimeTemplate")} RuntimeTemplate */ +/** @typedef {import("../util/runtime").RuntimeSpec} RuntimeSpec */ +/** @typedef {import("./WebAssemblyUtils").UsedWasmDependency} UsedWasmDependency */ + +/** + * @typedef {(ArrayBuffer) => ArrayBuffer} ArrayBufferTransform + */ + +/** + * @template T + * @param {Function[]} fns transforms + * @returns {Function} composed transform + */ +const compose = (...fns) => { + return fns.reduce( + (prevFn, nextFn) => { + return value => nextFn(prevFn(value)); + }, + value => value + ); +}; + +/** + * Removes the start instruction + * + * @param {Object} state unused state + * @returns {ArrayBufferTransform} transform + */ +const removeStartFunc = state => bin => { + return editWithAST(state.ast, bin, { + Start(path) { + path.remove(); + } + }); +}; + +/** + * Get imported globals + * + * @param {Object} ast Module's AST + * @returns {Array} - nodes + */ +const getImportedGlobals = ast => { + const importedGlobals = []; + + t.traverse(ast, { + ModuleImport({ node }) { + if (t.isGlobalType(node.descr)) { + importedGlobals.push(node); } - ); - const rootOutputDir = getUndoPath( - outputName, - this.compilation.outputOptions.path, - false - ); + } + }); - const stateExpression = withHmr - ? `${RuntimeGlobals.hmrRuntimeStatePrefix}_importScripts` - : undefined; + return importedGlobals; +}; - return Template.asString([ - withBaseURI - ? Template.asString([ - `${RuntimeGlobals.baseURI} = self.location + ${JSON.stringify( - rootOutputDir ? "/../" + rootOutputDir : "" - )};` - ]) - : "// no baseURI", - "", - "// object to store loaded chunks", - '// "1" means "already loaded"', - `var installedChunks = ${ - stateExpression ? `${stateExpression} = ${stateExpression} || ` : "" - }{`, - Template.indent( - Array.from(initialChunkIds, id => `${JSON.stringify(id)}: 1`).join( - ",\n" - ) - ), - "};", - "", - withLoading - ? Template.asString([ - "// importScripts chunk loading", - `var installChunk = ${runtimeTemplate.basicFunction("data", [ - runtimeTemplate.destructureArray( - ["chunkIds", "moreModules", "runtime"], - "data" - ), - "for(var moduleId in moreModules) {", - Template.indent([ - `if(${RuntimeGlobals.hasOwnProperty}(moreModules, moduleId)) {`, - Template.indent( - `${RuntimeGlobals.moduleFactories}[moduleId] = moreModules[moduleId];` - ), - "}" - ]), - "}", - "if(runtime) runtime(__webpack_require__);", - "while(chunkIds.length)", - Template.indent("installedChunks[chunkIds.pop()] = 1;"), - "parentChunkLoadingFunction(data);" - ])};` - ]) - : "// no chunk install function needed", - withLoading - ? Template.asString([ - `${fn}.i = ${runtimeTemplate.basicFunction( - "chunkId, promises", - hasJsMatcher !== false - ? [ - '// "1" is the signal for "already loaded"', - "if(!installedChunks[chunkId]) {", - Template.indent([ - hasJsMatcher === true - ? "if(true) { // all chunks have JS" - : `if(${hasJsMatcher("chunkId")}) {`, - Template.indent( - `importScripts(${ - withCreateScriptUrl - ? `${RuntimeGlobals.createScriptUrl}(${RuntimeGlobals.publicPath} + ${RuntimeGlobals.getChunkScriptFilename}(chunkId))` - : `${RuntimeGlobals.publicPath} + ${RuntimeGlobals.getChunkScriptFilename}(chunkId)` - });` - ), - "}" - ]), - "}" - ] - : "installedChunks[chunkId] = 1;" - )};`, - "", - `var chunkLoadingGlobal = ${chunkLoadingGlobalExpr} = ${chunkLoadingGlobalExpr} || [];`, - "var parentChunkLoadingFunction = chunkLoadingGlobal.push.bind(chunkLoadingGlobal);", - "chunkLoadingGlobal.push = installChunk;" - ]) - : "// no chunk loading", - "", - withHmr - ? Template.asString([ - "function loadUpdateChunk(chunkId, updatedModulesList) {", - Template.indent([ - "var success = false;", - `${globalObject}[${JSON.stringify( - hotUpdateGlobal - )}] = ${runtimeTemplate.basicFunction("_, moreModules, runtime", [ - "for(var moduleId in moreModules) {", - Template.indent([ - `if(${RuntimeGlobals.hasOwnProperty}(moreModules, moduleId)) {`, - Template.indent([ - "currentUpdate[moduleId] = moreModules[moduleId];", - "if(updatedModulesList) updatedModulesList.push(moduleId);" - ]), - "}" - ]), - "}", - "if(runtime) currentUpdateRuntime.push(runtime);", - "success = true;" - ])};`, - "// start update chunk loading", - `importScripts(${ - withCreateScriptUrl - ? `${RuntimeGlobals.createScriptUrl}(${RuntimeGlobals.publicPath} + ${RuntimeGlobals.getChunkUpdateScriptFilename}(chunkId))` - : `${RuntimeGlobals.publicPath} + ${RuntimeGlobals.getChunkUpdateScriptFilename}(chunkId)` - });`, - 'if(!success) throw new Error("Loading update chunk failed for unknown reason");' - ]), - "}", - "", - Template.getFunctionContent( - require('./JavascriptHotModuleReplacement.runtime.js') - ) - .replace(/\$key\$/g, "importScrips") - .replace(/\$installedChunks\$/g, "installedChunks") - .replace(/\$loadUpdateChunk\$/g, "loadUpdateChunk") - .replace(/\$moduleCache\$/g, RuntimeGlobals.moduleCache) - .replace(/\$moduleFactories\$/g, RuntimeGlobals.moduleFactories) - .replace( - /\$ensureChunkHandlers\$/g, - RuntimeGlobals.ensureChunkHandlers - ) - .replace(/\$hasOwnProperty\$/g, RuntimeGlobals.hasOwnProperty) - .replace(/\$hmrModuleData\$/g, RuntimeGlobals.hmrModuleData) - .replace( - /\$hmrDownloadUpdateHandlers\$/g, - RuntimeGlobals.hmrDownloadUpdateHandlers - ) - .replace( - /\$hmrInvalidateModuleHandlers\$/g, - RuntimeGlobals.hmrInvalidateModuleHandlers - ) - ]) - : "// no HMR", - "", - withHmrManifest - ? Template.asString([ - `${ - RuntimeGlobals.hmrDownloadManifest - } = ${runtimeTemplate.basicFunction("", [ - 'if (typeof fetch === "undefined") throw new Error("No browser support: need fetch API");', - `return fetch(${RuntimeGlobals.publicPath} + ${ - RuntimeGlobals.getUpdateManifestFilename - }()).then(${runtimeTemplate.basicFunction("response", [ - "if(response.status === 404) return; // no update available", - 'if(!response.ok) throw new Error("Failed to fetch update manifest " + response.statusText);', - "return response.json();" - ])});` - ])};` - ]) - : "// no HMR manifest" +/** + * Get the count for imported func + * + * @param {Object} ast Module's AST + * @returns {Number} - count + */ +const getCountImportedFunc = ast => { + let count = 0; + + t.traverse(ast, { + ModuleImport({ node }) { + if (t.isFuncImportDescr(node.descr)) { + count++; + } + } + }); + + return count; +}; + +/** + * Get next type index + * + * @param {Object} ast Module's AST + * @returns {t.Index} - index + */ +const getNextTypeIndex = ast => { + const typeSectionMetadata = t.getSectionMetadata(ast, "type"); + + if (typeSectionMetadata === undefined) { + return t.indexLiteral(0); + } + + return t.indexLiteral(typeSectionMetadata.vectorOfSize.value); +}; + +/** + * Get next func index + * + * The Func section metadata provide informations for implemented funcs + * in order to have the correct index we shift the index by number of external + * functions. + * + * @param {Object} ast Module's AST + * @param {Number} countImportedFunc number of imported funcs + * @returns {t.Index} - index + */ +const getNextFuncIndex = (ast, countImportedFunc) => { + const funcSectionMetadata = t.getSectionMetadata(ast, "func"); + + if (funcSectionMetadata === undefined) { + return t.indexLiteral(0 + countImportedFunc); + } + + const vectorOfSize = funcSectionMetadata.vectorOfSize.value; + + return t.indexLiteral(vectorOfSize + countImportedFunc); +}; + +/** + * Creates an init instruction for a global type + * @param {t.GlobalType} globalType the global type + * @returns {t.Instruction} init expression + */ +const createDefaultInitForGlobal = globalType => { + if (globalType.valtype[0] === "i") { + // create NumberLiteral global initializer + return t.objectInstruction("const", globalType.valtype, [ + t.numberLiteralFromRaw(66) ]); + } else if (globalType.valtype[0] === "f") { + // create FloatLiteral global initializer + return t.objectInstruction("const", globalType.valtype, [ + t.floatLiteral(66, false, false, "66") + ]); + } else { + throw new Error("unknown type: " + globalType.valtype); } -} +}; -module.exports = ImportScriptsChunkLoadingRuntimeModule; +/** + * Rewrite the import globals: + * - removes the ModuleImport instruction + * - injects at the same offset a mutable global of the same type + * + * Since the imported globals are before the other global declarations, our + * indices will be preserved. + * + * Note that globals will become mutable. + * + * @param {Object} state unused state + * @returns {ArrayBufferTransform} transform + */ +const rewriteImportedGlobals = state => bin => { + const additionalInitCode = state.additionalInitCode; + const newGlobals = []; + bin = editWithAST(state.ast, bin, { + ModuleImport(path) { + if (t.isGlobalType(path.node.descr)) { + const globalType = path.node.descr; -/***/ }), + globalType.mutability = "var"; -/***/ 9460: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + const init = [ + createDefaultInitForGlobal(globalType), + t.instruction("end") + ]; -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ + newGlobals.push(t.global(globalType, init)); + path.remove(); + } + }, + // in order to preserve non-imported global's order we need to re-inject + // those as well + Global(path) { + const { node } = path; + const [init] = node.init; -const ArrayPushCallbackChunkFormatPlugin = __webpack_require__(86189); -const EnableChunkLoadingPlugin = __webpack_require__(34726); + if (init.id === "get_global") { + node.globalType.mutability = "var"; -/** @typedef {import("../Compiler")} Compiler */ + const initialGlobalIdx = init.args[0]; -class WebWorkerTemplatePlugin { - /** - * Apply the plugin - * @param {Compiler} compiler the compiler instance - * @returns {void} - */ - apply(compiler) { - compiler.options.output.chunkLoading = "import-scripts"; - new ArrayPushCallbackChunkFormatPlugin().apply(compiler); - new EnableChunkLoadingPlugin("import-scripts").apply(compiler); - } -} -module.exports = WebWorkerTemplatePlugin; + node.init = [ + createDefaultInitForGlobal(node.globalType), + t.instruction("end") + ]; + additionalInitCode.push( + /** + * get_global in global initializer only works for imported globals. + * They have the same indices as the init params, so use the + * same index. + */ + t.instruction("get_local", [initialGlobalIdx]), + t.instruction("set_global", [t.indexLiteral(newGlobals.length)]) + ); + } -/***/ }), + newGlobals.push(node); -/***/ 94469: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + path.remove(); + } + }); -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ + // Add global declaration instructions + return addWithAST(state.ast, bin, newGlobals); +}; +/** + * Rewrite the export names + * @param {Object} state state + * @param {Object} state.ast Module's ast + * @param {Module} state.module Module + * @param {ModuleGraph} state.moduleGraph module graph + * @param {Set} state.externalExports Module + * @param {RuntimeSpec} state.runtime runtime + * @returns {ArrayBufferTransform} transform + */ +const rewriteExportNames = + ({ ast, moduleGraph, module, externalExports, runtime }) => + bin => { + return editWithAST(ast, bin, { + ModuleExport(path) { + const isExternal = externalExports.has(path.node.name); + if (isExternal) { + path.remove(); + return; + } + const usedName = moduleGraph + .getExportsInfo(module) + .getUsedName(path.node.name, runtime); + if (!usedName) { + path.remove(); + return; + } + path.node.name = usedName; + } + }); + }; +/** + * Mangle import names and modules + * @param {Object} state state + * @param {Object} state.ast Module's ast + * @param {Map} state.usedDependencyMap mappings to mangle names + * @returns {ArrayBufferTransform} transform + */ +const rewriteImports = + ({ ast, usedDependencyMap }) => + bin => { + return editWithAST(ast, bin, { + ModuleImport(path) { + const result = usedDependencyMap.get( + path.node.module + ":" + path.node.name + ); -const DescriptionFileUtils = __webpack_require__(18641); -const getInnerRequest = __webpack_require__(98361); + if (result !== undefined) { + path.node.module = result.module; + path.node.name = result.name; + } + } + }); + }; -/** @typedef {import("./Resolver")} Resolver */ -/** @typedef {import("./Resolver").ResolveRequest} ResolveRequest */ -/** @typedef {import("./Resolver").ResolveStepHook} ResolveStepHook */ +/** + * Add an init function. + * + * The init function fills the globals given input arguments. + * + * @param {Object} state transformation state + * @param {Object} state.ast Module's ast + * @param {t.Identifier} state.initFuncId identifier of the init function + * @param {t.Index} state.startAtFuncOffset index of the start function + * @param {t.ModuleImport[]} state.importedGlobals list of imported globals + * @param {t.Instruction[]} state.additionalInitCode list of addition instructions for the init function + * @param {t.Index} state.nextFuncIndex index of the next function + * @param {t.Index} state.nextTypeIndex index of the next type + * @returns {ArrayBufferTransform} transform + */ +const addInitFunction = + ({ + ast, + initFuncId, + startAtFuncOffset, + importedGlobals, + additionalInitCode, + nextFuncIndex, + nextTypeIndex + }) => + bin => { + const funcParams = importedGlobals.map(importedGlobal => { + // used for debugging + const id = t.identifier( + `${importedGlobal.module}.${importedGlobal.name}` + ); -module.exports = class AliasFieldPlugin { - /** - * @param {string | ResolveStepHook} source source - * @param {string | Array} field field - * @param {string | ResolveStepHook} target target - */ - constructor(source, field, target) { - this.source = source; - this.field = field; - this.target = target; - } + return t.funcParam(importedGlobal.descr.valtype, id); + }); - /** - * @param {Resolver} resolver the resolver - * @returns {void} - */ - apply(resolver) { - const target = resolver.ensureHook(this.target); - resolver - .getHook(this.source) - .tapAsync("AliasFieldPlugin", (request, resolveContext, callback) => { - if (!request.descriptionFileData) return callback(); - const innerRequest = getInnerRequest(resolver, request); - if (!innerRequest) return callback(); - const fieldData = DescriptionFileUtils.getField( - request.descriptionFileData, - this.field - ); - if (fieldData === null || typeof fieldData !== "object") { - if (resolveContext.log) - resolveContext.log( - "Field '" + - this.field + - "' doesn't contain a valid alias configuration" - ); - return callback(); - } - const data1 = fieldData[innerRequest]; - const data2 = fieldData[innerRequest.replace(/^\.\//, "")]; - const data = typeof data1 !== "undefined" ? data1 : data2; - if (data === innerRequest) return callback(); - if (data === undefined) return callback(); - if (data === false) { - /** @type {ResolveRequest} */ - const ignoreObj = { - ...request, - path: false - }; - return callback(null, ignoreObj); - } - const obj = { - ...request, - path: request.descriptionFileRoot, - request: data, - fullySpecified: false - }; - resolver.doResolve( - target, - obj, - "aliased from description file " + - request.descriptionFilePath + - " with mapping '" + - innerRequest + - "' to '" + - data + - "'", - resolveContext, - (err, result) => { - if (err) return callback(err); + const funcBody = []; + importedGlobals.forEach((importedGlobal, index) => { + const args = [t.indexLiteral(index)]; + const body = [ + t.instruction("get_local", args), + t.instruction("set_global", args) + ]; - // Don't allow other aliasing or raw request - if (result === undefined) return callback(null, null); - callback(null, result); - } - ); - }); - } -}; + funcBody.push(...body); + }); + if (typeof startAtFuncOffset === "number") { + funcBody.push( + t.callInstruction(t.numberLiteralFromRaw(startAtFuncOffset)) + ); + } -/***/ }), + for (const instr of additionalInitCode) { + funcBody.push(instr); + } -/***/ 42673: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + funcBody.push(t.instruction("end")); -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ + const funcResults = []; + // Code section + const funcSignature = t.signature(funcParams, funcResults); + const func = t.func(initFuncId, funcSignature, funcBody); + // Type section + const functype = t.typeInstruction(undefined, funcSignature); -const forEachBail = __webpack_require__(55426); + // Func section + const funcindex = t.indexInFuncSection(nextTypeIndex); -/** @typedef {import("./Resolver")} Resolver */ -/** @typedef {import("./Resolver").ResolveStepHook} ResolveStepHook */ -/** @typedef {{alias: string|Array|false, name: string, onlyModule?: boolean}} AliasOption */ + // Export section + const moduleExport = t.moduleExport( + initFuncId.value, + t.moduleExportDescr("Func", nextFuncIndex) + ); + + return addWithAST(ast, bin, [func, moduleExport, funcindex, functype]); + }; + +/** + * Extract mangle mappings from module + * @param {ModuleGraph} moduleGraph module graph + * @param {Module} module current module + * @param {boolean} mangle mangle imports + * @returns {Map} mappings to mangled names + */ +const getUsedDependencyMap = (moduleGraph, module, mangle) => { + /** @type {Map} */ + const map = new Map(); + for (const usedDep of WebAssemblyUtils.getUsedDependencies( + moduleGraph, + module, + mangle + )) { + const dep = usedDep.dependency; + const request = dep.request; + const exportName = dep.name; + map.set(request + ":" + exportName, usedDep); + } + return map; +}; + +const TYPES = new Set(["webassembly"]); + +class WebAssemblyGenerator extends Generator { + constructor(options) { + super(); + this.options = options; + } -module.exports = class AliasPlugin { /** - * @param {string | ResolveStepHook} source source - * @param {AliasOption | Array} options options - * @param {string | ResolveStepHook} target target + * @param {NormalModule} module fresh module + * @returns {Set} available types (do not mutate) */ - constructor(source, options, target) { - this.source = source; - this.options = Array.isArray(options) ? options : [options]; - this.target = target; + getTypes(module) { + return TYPES; } /** - * @param {Resolver} resolver the resolver - * @returns {void} + * @param {NormalModule} module the module + * @param {string=} type source type + * @returns {number} estimate size of the module */ - apply(resolver) { - const target = resolver.ensureHook(this.target); - resolver - .getHook(this.source) - .tapAsync("AliasPlugin", (request, resolveContext, callback) => { - const innerRequest = request.request || request.path; - if (!innerRequest) return callback(); - forEachBail( - this.options, - (item, callback) => { - let shouldStop = false; - if ( - innerRequest === item.name || - (!item.onlyModule && innerRequest.startsWith(item.name + "/")) - ) { - const remainingRequest = innerRequest.substr(item.name.length); - const resolveWithAlias = (alias, callback) => { - if (alias === false) { - const ignoreObj = { - ...request, - path: false - }; - return callback(null, ignoreObj); - } - if ( - innerRequest !== alias && - !innerRequest.startsWith(alias + "/") - ) { - shouldStop = true; - const newRequestStr = alias + remainingRequest; - const obj = { - ...request, - request: newRequestStr, - fullySpecified: false - }; - return resolver.doResolve( - target, - obj, - "aliased with mapping '" + - item.name + - "': '" + - alias + - "' to '" + - newRequestStr + - "'", - resolveContext, - (err, result) => { - if (err) return callback(err); - if (result) return callback(null, result); - return callback(); - } - ); - } - return callback(); - }; - const stoppingCallback = (err, result) => { - if (err) return callback(err); + getSize(module, type) { + const originalSource = module.originalSource(); + if (!originalSource) { + return 0; + } + return originalSource.size(); + } - if (result) return callback(null, result); - // Don't allow other aliasing or raw request - if (shouldStop) return callback(null, null); - return callback(); - }; - if (Array.isArray(item.alias)) { - return forEachBail( - item.alias, - resolveWithAlias, - stoppingCallback - ); - } else { - return resolveWithAlias(item.alias, stoppingCallback); - } - } - return callback(); - }, - callback - ); - }); + /** + * @param {NormalModule} module module for which the code should be generated + * @param {GenerateContext} generateContext context for generate + * @returns {Source} generated code + */ + generate(module, { moduleGraph, runtime }) { + const bin = module.originalSource().source(); + + const initFuncId = t.identifier(""); + + // parse it + const ast = decode(bin, { + ignoreDataSection: true, + ignoreCodeSection: true, + ignoreCustomNameSection: true + }); + + const moduleContext = moduleContextFromModuleAST(ast.body[0]); + + const importedGlobals = getImportedGlobals(ast); + const countImportedFunc = getCountImportedFunc(ast); + const startAtFuncOffset = moduleContext.getStart(); + const nextFuncIndex = getNextFuncIndex(ast, countImportedFunc); + const nextTypeIndex = getNextTypeIndex(ast); + + const usedDependencyMap = getUsedDependencyMap( + moduleGraph, + module, + this.options.mangleImports + ); + const externalExports = new Set( + module.dependencies + .filter(d => d instanceof WebAssemblyExportImportedDependency) + .map(d => { + const wasmDep = /** @type {WebAssemblyExportImportedDependency} */ ( + d + ); + return wasmDep.exportName; + }) + ); + + /** @type {t.Instruction[]} */ + const additionalInitCode = []; + + const transform = compose( + rewriteExportNames({ + ast, + moduleGraph, + module, + externalExports, + runtime + }), + + removeStartFunc({ ast }), + + rewriteImportedGlobals({ ast, additionalInitCode }), + + rewriteImports({ + ast, + usedDependencyMap + }), + + addInitFunction({ + ast, + initFuncId, + importedGlobals, + additionalInitCode, + startAtFuncOffset, + nextFuncIndex, + nextTypeIndex + }) + ); + + const newBin = transform(bin); + + const newBuf = Buffer.from(newBin); + + return new RawSource(newBuf); } -}; +} + +module.exports = WebAssemblyGenerator; /***/ }), -/***/ 72405: -/***/ (function(module) { +/***/ 14073: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; /* MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra */ -/** @typedef {import("./Resolver")} Resolver */ -/** @typedef {import("./Resolver").ResolveStepHook} ResolveStepHook */ +const WebpackError = __webpack_require__(68422); -module.exports = class AppendPlugin { - /** - * @param {string | ResolveStepHook} source source - * @param {string} appending appending - * @param {string | ResolveStepHook} target target - */ - constructor(source, appending, target) { - this.source = source; - this.appending = appending; - this.target = target; +/** @typedef {import("../ChunkGraph")} ChunkGraph */ +/** @typedef {import("../Module")} Module */ +/** @typedef {import("../ModuleGraph")} ModuleGraph */ +/** @typedef {import("../RequestShortener")} RequestShortener */ + +/** + * @param {Module} module module to get chains from + * @param {ModuleGraph} moduleGraph the module graph + * @param {ChunkGraph} chunkGraph the chunk graph + * @param {RequestShortener} requestShortener to make readable identifiers + * @returns {string[]} all chains to the module + */ +const getInitialModuleChains = ( + module, + moduleGraph, + chunkGraph, + requestShortener +) => { + const queue = [ + { head: module, message: module.readableIdentifier(requestShortener) } + ]; + /** @type {Set} */ + const results = new Set(); + /** @type {Set} */ + const incompleteResults = new Set(); + /** @type {Set} */ + const visitedModules = new Set(); + + for (const chain of queue) { + const { head, message } = chain; + let final = true; + /** @type {Set} */ + const alreadyReferencedModules = new Set(); + for (const connection of moduleGraph.getIncomingConnections(head)) { + const newHead = connection.originModule; + if (newHead) { + if (!chunkGraph.getModuleChunks(newHead).some(c => c.canBeInitial())) + continue; + final = false; + if (alreadyReferencedModules.has(newHead)) continue; + alreadyReferencedModules.add(newHead); + const moduleName = newHead.readableIdentifier(requestShortener); + const detail = connection.explanation + ? ` (${connection.explanation})` + : ""; + const newMessage = `${moduleName}${detail} --> ${message}`; + if (visitedModules.has(newHead)) { + incompleteResults.add(`... --> ${newMessage}`); + continue; + } + visitedModules.add(newHead); + queue.push({ + head: newHead, + message: newMessage + }); + } else { + final = false; + const newMessage = connection.explanation + ? `(${connection.explanation}) --> ${message}` + : message; + results.add(newMessage); + } + } + if (final) { + results.add(message); + } + } + for (const result of incompleteResults) { + results.add(result); } + return Array.from(results); +}; +module.exports = class WebAssemblyInInitialChunkError extends WebpackError { /** - * @param {Resolver} resolver the resolver - * @returns {void} + * @param {Module} module WASM module + * @param {ModuleGraph} moduleGraph the module graph + * @param {ChunkGraph} chunkGraph the chunk graph + * @param {RequestShortener} requestShortener request shortener */ - apply(resolver) { - const target = resolver.ensureHook(this.target); - resolver - .getHook(this.source) - .tapAsync("AppendPlugin", (request, resolveContext, callback) => { - const obj = { - ...request, - path: request.path + this.appending, - relativePath: - request.relativePath && request.relativePath + this.appending - }; - resolver.doResolve( - target, - obj, - this.appending, - resolveContext, - callback - ); - }); + constructor(module, moduleGraph, chunkGraph, requestShortener) { + const moduleChains = getInitialModuleChains( + module, + moduleGraph, + chunkGraph, + requestShortener + ); + const message = `WebAssembly module is included in initial chunk. +This is not allowed, because WebAssembly download and compilation must happen asynchronous. +Add an async split point (i. e. import()) somewhere between your entrypoint and the WebAssembly module: +${moduleChains.map(s => `* ${s}`).join("\n")}`; + + super(message); + this.name = "WebAssemblyInInitialChunkError"; + this.hideStack = true; + this.module = module; } }; /***/ }), -/***/ 26785: +/***/ 88890: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; @@ -134967,721 +134471,370 @@ module.exports = class AppendPlugin { -const nextTick = __webpack_require__(61765).nextTick; - -/** @typedef {import("./Resolver").FileSystem} FileSystem */ -/** @typedef {import("./Resolver").SyncFileSystem} SyncFileSystem */ +const { RawSource } = __webpack_require__(96192); +const { UsageState } = __webpack_require__(4295); +const Generator = __webpack_require__(1826); +const InitFragment = __webpack_require__(51739); +const RuntimeGlobals = __webpack_require__(49404); +const Template = __webpack_require__(92066); +const ModuleDependency = __webpack_require__(80944); +const WebAssemblyExportImportedDependency = __webpack_require__(18248); +const WebAssemblyImportDependency = __webpack_require__(97093); -const dirname = path => { - let idx = path.length - 1; - while (idx >= 0) { - const c = path.charCodeAt(idx); - // slash or backslash - if (c === 47 || c === 92) break; - idx--; - } - if (idx < 0) return ""; - return path.slice(0, idx); -}; +/** @typedef {import("webpack-sources").Source} Source */ +/** @typedef {import("../Dependency")} Dependency */ +/** @typedef {import("../DependencyTemplates")} DependencyTemplates */ +/** @typedef {import("../Generator").GenerateContext} GenerateContext */ +/** @typedef {import("../NormalModule")} NormalModule */ +/** @typedef {import("../RuntimeTemplate")} RuntimeTemplate */ -const runCallbacks = (callbacks, err, result) => { - if (callbacks.length === 1) { - callbacks[0](err, result); - callbacks.length = 0; - return; - } - let error; - for (const callback of callbacks) { - try { - callback(err, result); - } catch (e) { - if (!error) error = e; - } - } - callbacks.length = 0; - if (error) throw error; -}; +const TYPES = new Set(["webassembly"]); -class OperationMergerBackend { +class WebAssemblyJavascriptGenerator extends Generator { /** - * @param {any} provider async method - * @param {any} syncProvider sync method - * @param {any} providerContext call context for the provider methods + * @param {NormalModule} module fresh module + * @returns {Set} available types (do not mutate) */ - constructor(provider, syncProvider, providerContext) { - const activeAsyncOperations = new Map(); - - this.provide = provider - ? (path, options, callback) => { - if (typeof options === "function") { - callback = options; - options = undefined; - } - if (options) { - return provider.call(providerContext, path, options, callback); - } - if (typeof path !== "string") { - callback(new TypeError("path must be a string")); - return; - } - let callbacks = activeAsyncOperations.get(path); - if (callbacks) { - callbacks.push(callback); - return; - } - activeAsyncOperations.set(path, (callbacks = [callback])); - provider.call(providerContext, path, (err, result) => { - activeAsyncOperations.delete(path); - runCallbacks(callbacks, err, result); - }); - } - : null; - this.provideSync = syncProvider - ? (path, options) => { - return syncProvider.call(providerContext, path, options); - } - : null; - - this.provideCustom = provider - ? (provider, providerContext, path, callback) => { - let callbacks = activeAsyncOperations.get(path); - if (callbacks) { - callbacks.push(callback); - return; - } - activeAsyncOperations.set(path, (callbacks = [callback])); - provider.call(providerContext, path, (err, result) => { - activeAsyncOperations.delete(path); - runCallbacks(callbacks, err, result); - }); - } - : null; - this.provideCustomSync = syncProvider - ? (syncProvider, providerContext, path) => { - return syncProvider.call(providerContext, path); - } - : null; + getTypes(module) { + return TYPES; } - purge() {} - purgeParent() {} -} - -/* - -IDLE: - insert data: goto SYNC - -SYNC: - before provide: run ticks - event loop tick: goto ASYNC_ACTIVE - -ASYNC: - timeout: run tick, goto ASYNC_PASSIVE - -ASYNC_PASSIVE: - before provide: run ticks - -IDLE --[insert data]--> SYNC --[event loop tick]--> ASYNC_ACTIVE --[interval tick]-> ASYNC_PASSIVE - ^ | - +---------[insert data]-------+ -*/ - -const STORAGE_MODE_IDLE = 0; -const STORAGE_MODE_SYNC = 1; -const STORAGE_MODE_ASYNC = 2; - -class CacheBackend { /** - * @param {number} duration max cache duration of items - * @param {any} provider async method - * @param {any} syncProvider sync method - * @param {any} providerContext call context for the provider methods + * @param {NormalModule} module the module + * @param {string=} type source type + * @returns {number} estimate size of the module */ - constructor(duration, provider, syncProvider, providerContext) { - this._duration = duration; - this._provider = provider; - this._syncProvider = syncProvider; - this._providerContext = providerContext; - /** @type {Map} */ - this._activeAsyncOperations = new Map(); - /** @type {Map }>} */ - this._data = new Map(); - /** @type {Set[]} */ - this._levels = []; - for (let i = 0; i < 10; i++) this._levels.push(new Set()); - for (let i = 5000; i < duration; i += 500) this._levels.push(new Set()); - this._currentLevel = 0; - this._tickInterval = Math.floor(duration / this._levels.length); - /** @type {STORAGE_MODE_IDLE | STORAGE_MODE_SYNC | STORAGE_MODE_ASYNC} */ - this._mode = STORAGE_MODE_IDLE; - - /** @type {NodeJS.Timeout | undefined} */ - this._timeout = undefined; - /** @type {number | undefined} */ - this._nextDecay = undefined; - - this.provide = provider ? this.provide.bind(this) : null; - this.provideSync = syncProvider ? this.provideSync.bind(this) : null; - - this.provideCustom = provider ? this.provideCustom.bind(this) : null; - this.provideCustomSync = syncProvider - ? this.provideCustomSync.bind(this) - : null; + getSize(module, type) { + return 95 + module.dependencies.length * 5; } - provide(path, options, callback) { - if (typeof options === "function") { - callback = options; - options = undefined; - } - if (typeof path !== "string") { - callback(new TypeError("path must be a string")); - return; - } - if (options) { - return this._provider.call( - this._providerContext, - path, - options, - callback - ); - } - - // When in sync mode we can move to async mode - if (this._mode === STORAGE_MODE_SYNC) { - this._enterAsyncMode(); - } - - // Check in cache - let cacheEntry = this._data.get(path); - if (cacheEntry !== undefined) { - if (cacheEntry.err) return nextTick(callback, cacheEntry.err); - return nextTick(callback, null, cacheEntry.result); - } - - // Check if there is already the same operation running - let callbacks = this._activeAsyncOperations.get(path); - if (callbacks !== undefined) { - callbacks.push(callback); - return; - } - this._activeAsyncOperations.set(path, (callbacks = [callback])); - - // Run the operation - this._provider.call(this._providerContext, path, (err, result) => { - this._activeAsyncOperations.delete(path); - this._storeResult(path, err, result); - - // Enter async mode if not yet done - this._enterAsyncMode(); - - runCallbacks(callbacks, err, result); - }); - } + /** + * @param {NormalModule} module module for which the code should be generated + * @param {GenerateContext} generateContext context for generate + * @returns {Source} generated code + */ + generate(module, generateContext) { + const { + runtimeTemplate, + moduleGraph, + chunkGraph, + runtimeRequirements, + runtime + } = generateContext; + /** @type {InitFragment[]} */ + const initFragments = []; - provideSync(path, options) { - if (typeof path !== "string") { - throw new TypeError("path must be a string"); - } - if (options) { - return this._syncProvider.call(this._providerContext, path, options); - } + const exportsInfo = moduleGraph.getExportsInfo(module); - // In sync mode we may have to decay some cache items - if (this._mode === STORAGE_MODE_SYNC) { - this._runDecays(); - } + let needExportsCopy = false; + const importedModules = new Map(); + const initParams = []; + let index = 0; + for (const dep of module.dependencies) { + const moduleDep = + dep && dep instanceof ModuleDependency ? dep : undefined; + if (moduleGraph.getModule(dep)) { + let importData = importedModules.get(moduleGraph.getModule(dep)); + if (importData === undefined) { + importedModules.set( + moduleGraph.getModule(dep), + (importData = { + importVar: `m${index}`, + index, + request: (moduleDep && moduleDep.userRequest) || undefined, + names: new Set(), + reexports: [] + }) + ); + index++; + } + if (dep instanceof WebAssemblyImportDependency) { + importData.names.add(dep.name); + if (dep.description.type === "GlobalType") { + const exportName = dep.name; + const importedModule = moduleGraph.getModule(dep); - // Check in cache - let cacheEntry = this._data.get(path); - if (cacheEntry !== undefined) { - if (cacheEntry.err) throw cacheEntry.err; - return cacheEntry.result; + if (importedModule) { + const usedName = moduleGraph + .getExportsInfo(importedModule) + .getUsedName(exportName, runtime); + if (usedName) { + initParams.push( + runtimeTemplate.exportFromImport({ + moduleGraph, + module: importedModule, + request: dep.request, + importVar: importData.importVar, + originModule: module, + exportName: dep.name, + asiSafe: true, + isCall: false, + callContext: null, + defaultInterop: true, + initFragments, + runtime, + runtimeRequirements + }) + ); + } + } + } + } + if (dep instanceof WebAssemblyExportImportedDependency) { + importData.names.add(dep.name); + const usedName = moduleGraph + .getExportsInfo(module) + .getUsedName(dep.exportName, runtime); + if (usedName) { + runtimeRequirements.add(RuntimeGlobals.exports); + const exportProp = `${module.exportsArgument}[${JSON.stringify( + usedName + )}]`; + const defineStatement = Template.asString([ + `${exportProp} = ${runtimeTemplate.exportFromImport({ + moduleGraph, + module: moduleGraph.getModule(dep), + request: dep.request, + importVar: importData.importVar, + originModule: module, + exportName: dep.name, + asiSafe: true, + isCall: false, + callContext: null, + defaultInterop: true, + initFragments, + runtime, + runtimeRequirements + })};`, + `if(WebAssembly.Global) ${exportProp} = ` + + `new WebAssembly.Global({ value: ${JSON.stringify( + dep.valueType + )} }, ${exportProp});` + ]); + importData.reexports.push(defineStatement); + needExportsCopy = true; + } + } + } } + const importsCode = Template.asString( + Array.from( + importedModules, + ([module, { importVar, request, reexports }]) => { + const importStatement = runtimeTemplate.importStatement({ + module, + chunkGraph, + request, + importVar, + originModule: module, + runtimeRequirements + }); + return importStatement[0] + importStatement[1] + reexports.join("\n"); + } + ) + ); - // Get all active async operations - // This sync operation will also complete them - const callbacks = this._activeAsyncOperations.get(path); - this._activeAsyncOperations.delete(path); + const copyAllExports = + exportsInfo.otherExportsInfo.getUsed(runtime) === UsageState.Unused && + !needExportsCopy; - // Run the operation - // When in idle mode, we will enter sync mode - let result; - try { - result = this._syncProvider.call(this._providerContext, path); - } catch (err) { - this._storeResult(path, err, undefined); - this._enterSyncModeWhenIdle(); - if (callbacks) runCallbacks(callbacks, err, undefined); - throw err; + // need these globals + runtimeRequirements.add(RuntimeGlobals.module); + runtimeRequirements.add(RuntimeGlobals.moduleId); + runtimeRequirements.add(RuntimeGlobals.wasmInstances); + if (exportsInfo.otherExportsInfo.getUsed(runtime) !== UsageState.Unused) { + runtimeRequirements.add(RuntimeGlobals.makeNamespaceObject); + runtimeRequirements.add(RuntimeGlobals.exports); } - this._storeResult(path, undefined, result); - this._enterSyncModeWhenIdle(); - if (callbacks) runCallbacks(callbacks, undefined, result); - return result; - } - - provideCustom(provider, providerContext, path, callback) { - // When in sync mode we can move to async mode - if (this._mode === STORAGE_MODE_SYNC) { - this._enterAsyncMode(); + if (!copyAllExports) { + runtimeRequirements.add(RuntimeGlobals.exports); } - // Check in cache - let cacheEntry = this._data.get(path); - if (cacheEntry !== undefined) { - if (cacheEntry.err) return nextTick(callback, cacheEntry.err); - return nextTick(callback, null, cacheEntry.result); - } + // create source + const source = new RawSource( + [ + '"use strict";', + "// Instantiate WebAssembly module", + `var wasmExports = ${RuntimeGlobals.wasmInstances}[${module.moduleArgument}.id];`, - // Check if there is already the same operation running - let callbacks = this._activeAsyncOperations.get(path); - if (callbacks !== undefined) { - callbacks.push(callback); - return; - } - this._activeAsyncOperations.set(path, (callbacks = [callback])); + exportsInfo.otherExportsInfo.getUsed(runtime) !== UsageState.Unused + ? `${RuntimeGlobals.makeNamespaceObject}(${module.exportsArgument});` + : "", - // Run the operation - provider.call(providerContext, path, (err, result) => { - this._activeAsyncOperations.delete(path); - this._storeResult(path, err, result); + // this must be before import for circular dependencies + "// export exports from WebAssembly module", + copyAllExports + ? `${module.moduleArgument}.exports = wasmExports;` + : "for(var name in wasmExports) " + + `if(name) ` + + `${module.exportsArgument}[name] = wasmExports[name];`, + "// exec imports from WebAssembly module (for esm order)", + importsCode, + "", + "// exec wasm module", + `wasmExports[""](${initParams.join(", ")})` + ].join("\n") + ); + return InitFragment.addToSource(source, initFragments, generateContext); + } +} - // Enter async mode if not yet done - this._enterAsyncMode(); +module.exports = WebAssemblyJavascriptGenerator; - runCallbacks(callbacks, err, result); - }); - } - provideCustomSync(provider, providerContext, path) { - // In sync mode we may have to decay some cache items - if (this._mode === STORAGE_MODE_SYNC) { - this._runDecays(); - } +/***/ }), - // Check in cache - let cacheEntry = this._data.get(path); - if (cacheEntry !== undefined) { - if (cacheEntry.err) throw cacheEntry.err; - return cacheEntry.result; - } +/***/ 93813: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - // Get all active async operations - // This sync operation will also complete them - const callbacks = this._activeAsyncOperations.get(path); - this._activeAsyncOperations.delete(path); +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ - // Run the operation - // When in idle mode, we will enter sync mode - let result; - try { - result = provider.call(providerContext, path); - } catch (err) { - this._storeResult(path, err, undefined); - this._enterSyncModeWhenIdle(); - if (callbacks) runCallbacks(callbacks, err, undefined); - throw err; - } - this._storeResult(path, undefined, result); - this._enterSyncModeWhenIdle(); - if (callbacks) runCallbacks(callbacks, undefined, result); - return result; - } - purge(what) { - if (!what) { - if (this._mode !== STORAGE_MODE_IDLE) { - this._data.clear(); - for (const level of this._levels) { - level.clear(); - } - this._enterIdleMode(); - } - } else if (typeof what === "string") { - for (let [key, data] of this._data) { - if (key.startsWith(what)) { - this._data.delete(key); - data.level.delete(key); - } - } - if (this._data.size === 0) { - this._enterIdleMode(); - } - } else { - for (let [key, data] of this._data) { - for (const item of what) { - if (key.startsWith(item)) { - this._data.delete(key); - data.level.delete(key); - break; - } - } - } - if (this._data.size === 0) { - this._enterIdleMode(); - } - } - } - purgeParent(what) { - if (!what) { - this.purge(); - } else if (typeof what === "string") { - this.purge(dirname(what)); - } else { - const set = new Set(); - for (const item of what) { - set.add(dirname(item)); - } - this.purge(set); - } - } +const Generator = __webpack_require__(1826); +const WebAssemblyExportImportedDependency = __webpack_require__(18248); +const WebAssemblyImportDependency = __webpack_require__(97093); +const { compareModulesByIdentifier } = __webpack_require__(26296); +const memoize = __webpack_require__(84297); +const WebAssemblyInInitialChunkError = __webpack_require__(14073); - _storeResult(path, err, result) { - if (this._data.has(path)) return; - const level = this._levels[this._currentLevel]; - this._data.set(path, { err, result, level }); - level.add(path); - } +/** @typedef {import("webpack-sources").Source} Source */ +/** @typedef {import("../Compiler")} Compiler */ +/** @typedef {import("../Module")} Module */ +/** @typedef {import("../ModuleTemplate")} ModuleTemplate */ +/** @typedef {import("../javascript/JavascriptModulesPlugin").RenderContext} RenderContext */ - _decayLevel() { - const nextLevel = (this._currentLevel + 1) % this._levels.length; - const decay = this._levels[nextLevel]; - this._currentLevel = nextLevel; - for (let item of decay) { - this._data.delete(item); - } - decay.clear(); - if (this._data.size === 0) { - this._enterIdleMode(); - } else { - // @ts-ignore _nextDecay is always a number in sync mode - this._nextDecay += this._tickInterval; - } - } +const getWebAssemblyGenerator = memoize(() => + __webpack_require__(35303) +); +const getWebAssemblyJavascriptGenerator = memoize(() => + __webpack_require__(88890) +); +const getWebAssemblyParser = memoize(() => __webpack_require__(52288)); - _runDecays() { - while ( - /** @type {number} */ (this._nextDecay) <= Date.now() && - this._mode !== STORAGE_MODE_IDLE - ) { - this._decayLevel(); - } +class WebAssemblyModulesPlugin { + constructor(options) { + this.options = options; } - _enterAsyncMode() { - let timeout = 0; - switch (this._mode) { - case STORAGE_MODE_ASYNC: - return; - case STORAGE_MODE_IDLE: - this._nextDecay = Date.now() + this._tickInterval; - timeout = this._tickInterval; - break; - case STORAGE_MODE_SYNC: - this._runDecays(); - // @ts-ignore _runDecays may change the mode - if (this._mode === STORAGE_MODE_IDLE) return; - timeout = Math.max( - 0, - /** @type {number} */ (this._nextDecay) - Date.now() + /** + * Apply the plugin + * @param {Compiler} compiler the compiler instance + * @returns {void} + */ + apply(compiler) { + compiler.hooks.compilation.tap( + "WebAssemblyModulesPlugin", + (compilation, { normalModuleFactory }) => { + compilation.dependencyFactories.set( + WebAssemblyImportDependency, + normalModuleFactory ); - break; - } - this._mode = STORAGE_MODE_ASYNC; - const ref = setTimeout(() => { - this._mode = STORAGE_MODE_SYNC; - this._runDecays(); - }, timeout); - if (ref.unref) ref.unref(); - this._timeout = ref; - } - _enterSyncModeWhenIdle() { - if (this._mode === STORAGE_MODE_IDLE) { - this._mode = STORAGE_MODE_SYNC; - this._nextDecay = Date.now() + this._tickInterval; - } - } + compilation.dependencyFactories.set( + WebAssemblyExportImportedDependency, + normalModuleFactory + ); - _enterIdleMode() { - this._mode = STORAGE_MODE_IDLE; - this._nextDecay = undefined; - if (this._timeout) clearTimeout(this._timeout); - } -} + normalModuleFactory.hooks.createParser + .for("webassembly/sync") + .tap("WebAssemblyModulesPlugin", () => { + const WebAssemblyParser = getWebAssemblyParser(); -const createBackend = (duration, provider, syncProvider, providerContext) => { - if (duration > 0) { - return new CacheBackend(duration, provider, syncProvider, providerContext); - } - return new OperationMergerBackend(provider, syncProvider, providerContext); -}; + return new WebAssemblyParser(); + }); -module.exports = class CachedInputFileSystem { - constructor(fileSystem, duration) { - this.fileSystem = fileSystem; + normalModuleFactory.hooks.createGenerator + .for("webassembly/sync") + .tap("WebAssemblyModulesPlugin", () => { + const WebAssemblyJavascriptGenerator = + getWebAssemblyJavascriptGenerator(); + const WebAssemblyGenerator = getWebAssemblyGenerator(); - this._lstatBackend = createBackend( - duration, - this.fileSystem.lstat, - this.fileSystem.lstatSync, - this.fileSystem - ); - const lstat = this._lstatBackend.provide; - this.lstat = /** @type {FileSystem["lstat"]} */ (lstat); - const lstatSync = this._lstatBackend.provideSync; - this.lstatSync = /** @type {SyncFileSystem["lstatSync"]} */ (lstatSync); + return Generator.byType({ + javascript: new WebAssemblyJavascriptGenerator(), + webassembly: new WebAssemblyGenerator(this.options) + }); + }); - this._statBackend = createBackend( - duration, - this.fileSystem.stat, - this.fileSystem.statSync, - this.fileSystem - ); - const stat = this._statBackend.provide; - const customStat = this._statBackend.provideCustom; - this.stat = /** @type {FileSystem["stat"]} */ (stat); - const statSync = this._statBackend.provideSync; - const customStatSync = this._statBackend.provideCustomSync; - this.statSync = /** @type {SyncFileSystem["statSync"]} */ (statSync); + compilation.hooks.renderManifest.tap( + "WebAssemblyModulesPlugin", + (result, options) => { + const { chunkGraph } = compilation; + const { chunk, outputOptions, codeGenerationResults } = options; - this._readdirBackend = createBackend( - duration, - this.fileSystem.readdir, - this.fileSystem.readdirSync, - this.fileSystem - ); - const readdir = this._readdirBackend.provide; - this.readdir = /** @type {FileSystem["readdir"]} */ (readdir); - const readdirSync = this._readdirBackend.provideSync; - this.readdirSync = /** @type {SyncFileSystem["readdirSync"]} */ (readdirSync); + for (const module of chunkGraph.getOrderedChunkModulesIterable( + chunk, + compareModulesByIdentifier + )) { + if (module.type === "webassembly/sync") { + const filenameTemplate = + outputOptions.webassemblyModuleFilename; - this._readFileBackend = createBackend( - duration, - this.fileSystem.readFile && - this.fileSystem.fstat && - this.fileSystem.read && - this.fileSystem.open && - this.fileSystem.close && - customStat - ? /** - * @this {{ fstat: NonNullable, readFile: NonNullable, open: NonNullable, read: NonNullable, close: NonNullable }} - */ - function (path, options, callback) { - if (typeof options === "function") { - callback = options; - options = undefined; - } - if (typeof options === "object") - return this.readFile(path, options, callback); - this.open(path, "r", (err, fd) => { - if (err) return callback(err); - if (typeof fd !== "number") - return callback(new Error("fd must be a number")); - customStat( - (path, callback) => this.fstat(fd, callback), - null, - path, - (err, stats) => { - if (err) return callback(err); - if (stats.size > 0 && stats.size < 128 * 1024) { - let remaining = stats.size + 1; - const buffer = Buffer.allocUnsafe(remaining); - const afterRead = (err, bytesRead) => { - if (err) { - return this.close(fd, () => { - callback(err); - }); - } - remaining -= bytesRead; - if (bytesRead === 0 || remaining === 1) { - this.close(fd, err => { - if (err) return callback(err); - return callback( - null, - buffer.slice(0, buffer.length - remaining) - ); - }); - } else if (remaining === 0) { - // The file size has changed from the cached info - // We keep reading until the end is found - let buf = Buffer.allocUnsafe(16 * 1024); - let bufPos = 0; - const buffers = [buffer]; - const afterUnknownRead = (err, bytesRead) => { - if (err) { - return this.close(fd, () => { - callback(err); - }); - } - bufPos += bytesRead; - if (bytesRead === 0) { - if (bufPos > 0) buffers.push(buf.slice(0, bufPos)); - this.close(fd, err => { - if (err) return callback(err); - return callback(null, Buffer.concat(buffers)); - }); - } else { - if (bufPos === buf.length) { - buffers.push(buf); - buf = Buffer.allocUnsafe(16 * 1024); - bufPos = 0; - } - this.read( - fd, - buf, - bufPos, - buf.length - bufPos, - -1, - afterUnknownRead - ); - } - }; - this.read( - fd, - buf, - bufPos, - buf.length - bufPos, - -1, - afterUnknownRead - ); - } else { - this.read( - fd, - buffer, - stats.size - remaining, - remaining + 1, - -1, - afterRead - ); - } - }; - this.read(fd, buffer, 0, remaining, -1, afterRead); - } else { - this.readFile(fd, options, (err, buffer) => { - this.close(fd, closeErr => { - if (err) return callback(err); - if (closeErr) return callback(closeErr); - callback(null, buffer); - }); - }); - } - } - ); - }); - } - : this.fileSystem.readFile, - this.fileSystem.readFileSync && - this.fileSystem.fstatSync && - this.fileSystem.readSync && - this.fileSystem.openSync && - this.fileSystem.closeSync && - customStatSync - ? /** - * @this {{ fstatSync: NonNullable, readFileSync: NonNullable, openSync: NonNullable, readSync: NonNullable, closeSync: NonNullable }} - */ - function (path, options) { - if (typeof options === "object") - return this.readFileSync(path, options); - const fd = this.openSync(path, "r"); - if (typeof fd !== "number") throw new Error("fd must be a number"); - const stats = customStatSync(() => this.fstatSync(fd), null, path); - if (stats.size > 0 && stats.size < 128 * 1024) { - let remaining = stats.size; - const buffer = Buffer.allocUnsafe(remaining); - try { - let bytesRead = this.readSync(fd, buffer, 0, remaining, -1); - remaining -= bytesRead; - while (bytesRead !== 0 && remaining !== 0) { - bytesRead = this.readSync( - fd, - buffer, - stats.size - remaining, - remaining, - -1 - ); - remaining -= bytesRead; - } - return buffer; - } finally { - this.closeSync(fd); + result.push({ + render: () => + codeGenerationResults.getSource( + module, + chunk.runtime, + "webassembly" + ), + filenameTemplate, + pathOptions: { + module, + runtime: chunk.runtime, + chunkGraph + }, + auxiliary: true, + identifier: `webassemblyModule${chunkGraph.getModuleId( + module + )}`, + hash: chunkGraph.getModuleHash(module, chunk.runtime) + }); } - } else { - const buffer = this.readFileSync(fd); - this.closeSync(fd); - return buffer; } - } - : this.fileSystem.readFileSync, - this.fileSystem - ); - const readFile = this._readFileBackend.provide; - this.readFile = /** @type {FileSystem["readFile"]} */ (readFile); - const readFileSync = this._readFileBackend.provideSync; - this.readFileSync = /** @type {SyncFileSystem["readFileSync"]} */ (readFileSync); - this._readJsonBackend = createBackend( - duration, - this.fileSystem.readJson || - (this.readFile && - ((path, callback) => { - // @ts-ignore - this.readFile(path, (err, buffer) => { - if (err) return callback(err); - if (!buffer || buffer.length === 0) - return callback(new Error("No file content")); - let data; - try { - data = JSON.parse(buffer.toString("utf-8")); - } catch (e) { - return callback(e); - } - callback(null, data); - }); - })), - this.fileSystem.readJsonSync || - (this.readFileSync && - (path => { - const buffer = this.readFileSync(path); - const data = JSON.parse(buffer.toString("utf-8")); - return data; - })), - this.fileSystem - ); - const readJson = this._readJsonBackend.provide; - this.readJson = /** @type {FileSystem["readJson"]} */ (readJson); - const readJsonSync = this._readJsonBackend.provideSync; - this.readJsonSync = /** @type {SyncFileSystem["readJsonSync"]} */ (readJsonSync); + return result; + } + ); - this._readlinkBackend = createBackend( - duration, - this.fileSystem.readlink, - this.fileSystem.readlinkSync, - this.fileSystem + compilation.hooks.afterChunks.tap("WebAssemblyModulesPlugin", () => { + const chunkGraph = compilation.chunkGraph; + const initialWasmModules = new Set(); + for (const chunk of compilation.chunks) { + if (chunk.canBeInitial()) { + for (const module of chunkGraph.getChunkModulesIterable(chunk)) { + if (module.type === "webassembly/sync") { + initialWasmModules.add(module); + } + } + } + } + for (const module of initialWasmModules) { + compilation.errors.push( + new WebAssemblyInInitialChunkError( + module, + compilation.moduleGraph, + compilation.chunkGraph, + compilation.requestShortener + ) + ); + } + }); + } ); - const readlink = this._readlinkBackend.provide; - this.readlink = /** @type {FileSystem["readlink"]} */ (readlink); - const readlinkSync = this._readlinkBackend.provideSync; - this.readlinkSync = /** @type {SyncFileSystem["readlinkSync"]} */ (readlinkSync); } +} - purge(what) { - this._statBackend.purge(what); - this._lstatBackend.purge(what); - this._readdirBackend.purgeParent(what); - this._readFileBackend.purge(what); - this._readlinkBackend.purge(what); - this._readJsonBackend.purge(what); - } -}; +module.exports = WebAssemblyModulesPlugin; /***/ }), -/***/ 36154: +/***/ 52288: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; @@ -135692,50 +134845,270 @@ module.exports = class CachedInputFileSystem { -const basename = __webpack_require__(17117).basename; +const t = __webpack_require__(98688); +const { moduleContextFromModuleAST } = __webpack_require__(98688); +const { decode } = __webpack_require__(8062); +const Parser = __webpack_require__(68214); +const StaticExportsDependency = __webpack_require__(67967); +const WebAssemblyExportImportedDependency = __webpack_require__(18248); +const WebAssemblyImportDependency = __webpack_require__(97093); -/** @typedef {import("./Resolver")} Resolver */ +/** @typedef {import("../Module")} Module */ +/** @typedef {import("../Parser").ParserState} ParserState */ +/** @typedef {import("../Parser").PreparsedAst} PreparsedAst */ -module.exports = class CloneBasenamePlugin { - constructor(source, target) { - this.source = source; - this.target = target; +const JS_COMPAT_TYPES = new Set(["i32", "f32", "f64"]); + +/** + * @param {t.Signature} signature the func signature + * @returns {null | string} the type incompatible with js types + */ +const getJsIncompatibleType = signature => { + for (const param of signature.params) { + if (!JS_COMPAT_TYPES.has(param.valtype)) { + return `${param.valtype} as parameter`; + } + } + for (const type of signature.results) { + if (!JS_COMPAT_TYPES.has(type)) return `${type} as result`; + } + return null; +}; + +/** + * TODO why are there two different Signature types? + * @param {t.FuncSignature} signature the func signature + * @returns {null | string} the type incompatible with js types + */ +const getJsIncompatibleTypeOfFuncSignature = signature => { + for (const param of signature.args) { + if (!JS_COMPAT_TYPES.has(param)) { + return `${param} as parameter`; + } + } + for (const type of signature.result) { + if (!JS_COMPAT_TYPES.has(type)) return `${type} as result`; + } + return null; +}; + +const decoderOpts = { + ignoreCodeSection: true, + ignoreDataSection: true, + + // this will avoid having to lookup with identifiers in the ModuleContext + ignoreCustomNameSection: true +}; + +class WebAssemblyParser extends Parser { + constructor(options) { + super(); + this.hooks = Object.freeze({}); + this.options = options; } /** - * @param {Resolver} resolver the resolver - * @returns {void} + * @param {string | Buffer | PreparsedAst} source the source to parse + * @param {ParserState} state the parser state + * @returns {ParserState} the parser state */ - apply(resolver) { - const target = resolver.ensureHook(this.target); - resolver - .getHook(this.source) - .tapAsync("CloneBasenamePlugin", (request, resolveContext, callback) => { - const filename = basename(request.path); - const filePath = resolver.join(request.path, filename); - const obj = { - ...request, - path: filePath, - relativePath: - request.relativePath && - resolver.join(request.relativePath, filename) - }; - resolver.doResolve( - target, - obj, - "using path: " + filePath, - resolveContext, - callback + parse(source, state) { + if (!Buffer.isBuffer(source)) { + throw new Error("WebAssemblyParser input must be a Buffer"); + } + + // flag it as ESM + state.module.buildInfo.strict = true; + state.module.buildMeta.exportsType = "namespace"; + + // parse it + const program = decode(source, decoderOpts); + const module = program.body[0]; + + const moduleContext = moduleContextFromModuleAST(module); + + // extract imports and exports + const exports = []; + let jsIncompatibleExports = (state.module.buildMeta.jsIncompatibleExports = + undefined); + + const importedGlobals = []; + t.traverse(module, { + ModuleExport({ node }) { + const descriptor = node.descr; + + if (descriptor.exportType === "Func") { + const funcIdx = descriptor.id.value; + + /** @type {t.FuncSignature} */ + const funcSignature = moduleContext.getFunction(funcIdx); + + const incompatibleType = + getJsIncompatibleTypeOfFuncSignature(funcSignature); + + if (incompatibleType) { + if (jsIncompatibleExports === undefined) { + jsIncompatibleExports = + state.module.buildMeta.jsIncompatibleExports = {}; + } + jsIncompatibleExports[node.name] = incompatibleType; + } + } + + exports.push(node.name); + + if (node.descr && node.descr.exportType === "Global") { + const refNode = importedGlobals[node.descr.id.value]; + if (refNode) { + const dep = new WebAssemblyExportImportedDependency( + node.name, + refNode.module, + refNode.name, + refNode.descr.valtype + ); + + state.module.addDependency(dep); + } + } + }, + + Global({ node }) { + const init = node.init[0]; + + let importNode = null; + + if (init.id === "get_global") { + const globalIdx = init.args[0].value; + + if (globalIdx < importedGlobals.length) { + importNode = importedGlobals[globalIdx]; + } + } + + importedGlobals.push(importNode); + }, + + ModuleImport({ node }) { + /** @type {false | string} */ + let onlyDirectImport = false; + + if (t.isMemory(node.descr) === true) { + onlyDirectImport = "Memory"; + } else if (t.isTable(node.descr) === true) { + onlyDirectImport = "Table"; + } else if (t.isFuncImportDescr(node.descr) === true) { + const incompatibleType = getJsIncompatibleType(node.descr.signature); + if (incompatibleType) { + onlyDirectImport = `Non-JS-compatible Func Signature (${incompatibleType})`; + } + } else if (t.isGlobalType(node.descr) === true) { + const type = node.descr.valtype; + if (!JS_COMPAT_TYPES.has(type)) { + onlyDirectImport = `Non-JS-compatible Global Type (${type})`; + } + } + + const dep = new WebAssemblyImportDependency( + node.module, + node.name, + node.descr, + onlyDirectImport ); - }); + + state.module.addDependency(dep); + + if (t.isGlobalType(node.descr)) { + importedGlobals.push(node); + } + } + }); + + state.module.addDependency(new StaticExportsDependency(exports, false)); + + return state; + } +} + +module.exports = WebAssemblyParser; + + +/***/ }), + +/***/ 41520: +/***/ (function(__unused_webpack_module, exports, __webpack_require__) { + +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ + + + +const Template = __webpack_require__(92066); +const WebAssemblyImportDependency = __webpack_require__(97093); + +/** @typedef {import("../Module")} Module */ +/** @typedef {import("../ModuleGraph")} ModuleGraph */ + +/** @typedef {Object} UsedWasmDependency + * @property {WebAssemblyImportDependency} dependency the dependency + * @property {string} name the export name + * @property {string} module the module name + */ + +const MANGLED_MODULE = "a"; + +/** + * @param {ModuleGraph} moduleGraph the module graph + * @param {Module} module the module + * @param {boolean} mangle mangle module and export names + * @returns {UsedWasmDependency[]} used dependencies and (mangled) name + */ +const getUsedDependencies = (moduleGraph, module, mangle) => { + /** @type {UsedWasmDependency[]} */ + const array = []; + let importIndex = 0; + for (const dep of module.dependencies) { + if (dep instanceof WebAssemblyImportDependency) { + if ( + dep.description.type === "GlobalType" || + moduleGraph.getModule(dep) === null + ) { + continue; + } + + const exportName = dep.name; + // TODO add the following 3 lines when removing of ModuleExport is possible + // const importedModule = moduleGraph.getModule(dep); + // const usedName = importedModule && moduleGraph.getExportsInfo(importedModule).getUsedName(exportName, runtime); + // if (usedName !== false) { + if (mangle) { + array.push({ + dependency: dep, + name: Template.numberToIdentifier(importIndex++), + module: MANGLED_MODULE + }); + } else { + array.push({ + dependency: dep, + name: exportName, + module: dep.request + }); + } + } } + return array; }; +exports.getUsedDependencies = getUsedDependencies; +exports.MANGLED_MODULE = MANGLED_MODULE; + /***/ }), -/***/ 13134: -/***/ (function(module) { +/***/ 93943: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; /* @@ -135745,63 +135118,122 @@ module.exports = class CloneBasenamePlugin { -/** @typedef {import("./Resolver")} Resolver */ -/** @typedef {import("./Resolver").ResolveRequest} ResolveRequest */ -/** @typedef {import("./Resolver").ResolveStepHook} ResolveStepHook */ +/** @typedef {import("../../declarations/WebpackOptions").LibraryOptions} LibraryOptions */ +/** @typedef {import("../../declarations/WebpackOptions").WasmLoadingType} WasmLoadingType */ +/** @typedef {import("../Compiler")} Compiler */ -module.exports = class ConditionalPlugin { +/** @type {WeakMap>} */ +const enabledTypes = new WeakMap(); + +const getEnabledTypes = compiler => { + let set = enabledTypes.get(compiler); + if (set === undefined) { + set = new Set(); + enabledTypes.set(compiler, set); + } + return set; +}; + +class EnableWasmLoadingPlugin { /** - * @param {string | ResolveStepHook} source source - * @param {Partial} test compare object - * @param {string | null} message log message - * @param {boolean} allowAlternatives when false, do not continue with the current step when "test" matches - * @param {string | ResolveStepHook} target target + * @param {WasmLoadingType} type library type that should be available */ - constructor(source, test, message, allowAlternatives, target) { - this.source = source; - this.test = test; - this.message = message; - this.allowAlternatives = allowAlternatives; - this.target = target; + constructor(type) { + this.type = type; } /** - * @param {Resolver} resolver the resolver + * @param {Compiler} compiler the compiler instance + * @param {WasmLoadingType} type type of library * @returns {void} */ - apply(resolver) { - const target = resolver.ensureHook(this.target); - const { test, message, allowAlternatives } = this; - const keys = Object.keys(test); - resolver - .getHook(this.source) - .tapAsync("ConditionalPlugin", (request, resolveContext, callback) => { - for (const prop of keys) { - if (request[prop] !== test[prop]) return callback(); - } - resolver.doResolve( - target, - request, - message, - resolveContext, - allowAlternatives - ? callback - : (err, result) => { - if (err) return callback(err); + static setEnabled(compiler, type) { + getEnabledTypes(compiler).add(type); + } - // Don't allow other alternatives - if (result === undefined) return callback(null, null); - callback(null, result); - } - ); - }); + /** + * @param {Compiler} compiler the compiler instance + * @param {WasmLoadingType} type type of library + * @returns {void} + */ + static checkEnabled(compiler, type) { + if (!getEnabledTypes(compiler).has(type)) { + throw new Error( + `Library type "${type}" is not enabled. ` + + "EnableWasmLoadingPlugin need to be used to enable this type of wasm loading. " + + 'This usually happens through the "output.enabledWasmLoadingTypes" option. ' + + 'If you are using a function as entry which sets "wasmLoading", you need to add all potential library types to "output.enabledWasmLoadingTypes". ' + + "These types are enabled: " + + Array.from(getEnabledTypes(compiler)).join(", ") + ); + } + } + + /** + * Apply the plugin + * @param {Compiler} compiler the compiler instance + * @returns {void} + */ + apply(compiler) { + const { type } = this; + + // Only enable once + const enabled = getEnabledTypes(compiler); + if (enabled.has(type)) return; + enabled.add(type); + + if (typeof type === "string") { + switch (type) { + case "fetch": { + // TODO webpack 6 remove FetchCompileWasmPlugin + const FetchCompileWasmPlugin = __webpack_require__(89728); + const FetchCompileAsyncWasmPlugin = __webpack_require__(37118); + new FetchCompileWasmPlugin({ + mangleImports: compiler.options.optimization.mangleWasmImports + }).apply(compiler); + new FetchCompileAsyncWasmPlugin().apply(compiler); + break; + } + case "async-node": { + // TODO webpack 6 remove ReadFileCompileWasmPlugin + const ReadFileCompileWasmPlugin = __webpack_require__(98724); + // @ts-expect-error typescript bug for duplicate require + const ReadFileCompileAsyncWasmPlugin = __webpack_require__(82138); + new ReadFileCompileWasmPlugin({ + mangleImports: compiler.options.optimization.mangleWasmImports + }).apply(compiler); + new ReadFileCompileAsyncWasmPlugin({ type }).apply(compiler); + break; + } + case "async-node-module": { + // @ts-expect-error typescript bug for duplicate require + const ReadFileCompileAsyncWasmPlugin = __webpack_require__(82138); + new ReadFileCompileAsyncWasmPlugin({ type, import: true }).apply( + compiler + ); + break; + } + case "universal": + throw new Error( + "Universal WebAssembly Loading is not implemented yet" + ); + default: + throw new Error(`Unsupported wasm loading type ${type}. +Plugins which provide custom wasm loading types must call EnableWasmLoadingPlugin.setEnabled(compiler, type) to disable this error.`); + } + } else { + // TODO support plugin instances here + // apply them to the compiler + } } -}; +} + +module.exports = EnableWasmLoadingPlugin; /***/ }), -/***/ 85774: +/***/ 37118: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; @@ -135812,279 +135244,67 @@ module.exports = class ConditionalPlugin { -const DescriptionFileUtils = __webpack_require__(18641); - -/** @typedef {import("./Resolver")} Resolver */ -/** @typedef {import("./Resolver").ResolveStepHook} ResolveStepHook */ +const RuntimeGlobals = __webpack_require__(49404); +const AsyncWasmLoadingRuntimeModule = __webpack_require__(84465); -module.exports = class DescriptionFilePlugin { - /** - * @param {string | ResolveStepHook} source source - * @param {string[]} filenames filenames - * @param {boolean} pathIsFile pathIsFile - * @param {string | ResolveStepHook} target target - */ - constructor(source, filenames, pathIsFile, target) { - this.source = source; - this.filenames = filenames; - this.pathIsFile = pathIsFile; - this.target = target; - } +/** @typedef {import("../Compiler")} Compiler */ +class FetchCompileAsyncWasmPlugin { /** - * @param {Resolver} resolver the resolver + * Apply the plugin + * @param {Compiler} compiler the compiler instance * @returns {void} */ - apply(resolver) { - const target = resolver.ensureHook(this.target); - resolver - .getHook(this.source) - .tapAsync( - "DescriptionFilePlugin", - (request, resolveContext, callback) => { - const path = request.path; - if (!path) return callback(); - const directory = this.pathIsFile - ? DescriptionFileUtils.cdUp(path) - : path; - if (!directory) return callback(); - DescriptionFileUtils.loadDescriptionFile( - resolver, - directory, - this.filenames, - request.descriptionFilePath - ? { - path: request.descriptionFilePath, - content: request.descriptionFileData, - directory: /** @type {string} */ (request.descriptionFileRoot) - } - : undefined, - resolveContext, - (err, result) => { - if (err) return callback(err); - if (!result) { - if (resolveContext.log) - resolveContext.log( - `No description file found in ${directory} or above` - ); - return callback(); - } - const relativePath = - "." + path.substr(result.directory.length).replace(/\\/g, "/"); - const obj = { - ...request, - descriptionFilePath: result.path, - descriptionFileData: result.content, - descriptionFileRoot: result.directory, - relativePath: relativePath - }; - resolver.doResolve( - target, - obj, - "using description file: " + - result.path + - " (relative path: " + - relativePath + - ")", - resolveContext, - (err, result) => { - if (err) return callback(err); - - // Don't allow other processing - if (result === undefined) return callback(null, null); - callback(null, result); - } - ); - } - ); - } - ); - } -}; - - -/***/ }), - -/***/ 18641: -/***/ (function(__unused_webpack_module, exports, __webpack_require__) { - -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ - - - -const forEachBail = __webpack_require__(55426); - -/** @typedef {import("./Resolver")} Resolver */ -/** @typedef {import("./Resolver").ResolveContext} ResolveContext */ - -/** - * @typedef {Object} DescriptionFileInfo - * @property {any=} content - * @property {string} path - * @property {string} directory - */ - -/** - * @callback ErrorFirstCallback - * @param {Error|null=} error - * @param {DescriptionFileInfo=} result - */ - -/** - * @param {Resolver} resolver resolver - * @param {string} directory directory - * @param {string[]} filenames filenames - * @param {DescriptionFileInfo|undefined} oldInfo oldInfo - * @param {ResolveContext} resolveContext resolveContext - * @param {ErrorFirstCallback} callback callback - */ -function loadDescriptionFile( - resolver, - directory, - filenames, - oldInfo, - resolveContext, - callback -) { - (function findDescriptionFile() { - if (oldInfo && oldInfo.directory === directory) { - // We already have info for this directory and can reuse it - return callback(null, oldInfo); - } - forEachBail( - filenames, - (filename, callback) => { - const descriptionFilePath = resolver.join(directory, filename); - if (resolver.fileSystem.readJson) { - resolver.fileSystem.readJson(descriptionFilePath, (err, content) => { - if (err) { - if (typeof err.code !== "undefined") { - if (resolveContext.missingDependencies) { - resolveContext.missingDependencies.add(descriptionFilePath); - } - return callback(); - } - if (resolveContext.fileDependencies) { - resolveContext.fileDependencies.add(descriptionFilePath); - } - return onJson(err); - } - if (resolveContext.fileDependencies) { - resolveContext.fileDependencies.add(descriptionFilePath); - } - onJson(null, content); - }); - } else { - resolver.fileSystem.readFile(descriptionFilePath, (err, content) => { - if (err) { - if (resolveContext.missingDependencies) { - resolveContext.missingDependencies.add(descriptionFilePath); - } - return callback(); - } - if (resolveContext.fileDependencies) { - resolveContext.fileDependencies.add(descriptionFilePath); - } - let json; + apply(compiler) { + compiler.hooks.thisCompilation.tap( + "FetchCompileAsyncWasmPlugin", + compilation => { + const globalWasmLoading = compilation.outputOptions.wasmLoading; + const isEnabledForChunk = chunk => { + const options = chunk.getEntryOptions(); + const wasmLoading = + options && options.wasmLoading !== undefined + ? options.wasmLoading + : globalWasmLoading; + return wasmLoading === "fetch"; + }; + const generateLoadBinaryCode = path => + `fetch(${RuntimeGlobals.publicPath} + ${path})`; - if (content) { - try { - json = JSON.parse(content.toString()); - } catch (e) { - return onJson(e); - } - } else { - return onJson(new Error("No content in file")); + compilation.hooks.runtimeRequirementInTree + .for(RuntimeGlobals.instantiateWasm) + .tap("FetchCompileAsyncWasmPlugin", (chunk, set) => { + if (!isEnabledForChunk(chunk)) return; + const chunkGraph = compilation.chunkGraph; + if ( + !chunkGraph.hasModuleInGraph( + chunk, + m => m.type === "webassembly/async" + ) + ) { + return; } - - onJson(null, json); - }); - } - - function onJson(err, content) { - if (err) { - if (resolveContext.log) - resolveContext.log( - descriptionFilePath + " (directory description file): " + err - ); - else - err.message = - descriptionFilePath + " (directory description file): " + err; - return callback(err); - } - callback(null, { - content, - directory, - path: descriptionFilePath + set.add(RuntimeGlobals.publicPath); + compilation.addRuntimeModule( + chunk, + new AsyncWasmLoadingRuntimeModule({ + generateLoadBinaryCode, + supportsStreaming: true + }) + ); }); - } - }, - (err, result) => { - if (err) return callback(err); - if (result) { - return callback(null, result); - } else { - const dir = cdUp(directory); - if (!dir) { - return callback(); - } else { - directory = dir; - return findDescriptionFile(); - } - } } ); - })(); -} - -/** - * @param {any} content content - * @param {string|string[]} field field - * @returns {object|string|number|boolean|undefined} field data - */ -function getField(content, field) { - if (!content) return undefined; - if (Array.isArray(field)) { - let current = content; - for (let j = 0; j < field.length; j++) { - if (current === null || typeof current !== "object") { - current = null; - break; - } - current = current[field[j]]; - } - return current; - } else { - return content[field]; } } -/** - * @param {string} directory directory - * @returns {string|null} parent directory or null - */ -function cdUp(directory) { - if (directory === "/") return null; - const i = directory.lastIndexOf("/"), - j = directory.lastIndexOf("\\"); - const p = i < 0 ? j : j < 0 ? i : i < j ? j : i; - if (p < 0) return null; - return directory.substr(0, p || 1); -} - -exports.loadDescriptionFile = loadDescriptionFile; -exports.getField = getField; -exports.cdUp = cdUp; +module.exports = FetchCompileAsyncWasmPlugin; /***/ }), -/***/ 61827: -/***/ (function(module) { +/***/ 89728: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; /* @@ -136094,225 +135314,623 @@ exports.cdUp = cdUp; -/** @typedef {import("./Resolver")} Resolver */ -/** @typedef {import("./Resolver").ResolveStepHook} ResolveStepHook */ +const RuntimeGlobals = __webpack_require__(49404); +const WasmChunkLoadingRuntimeModule = __webpack_require__(92153); -module.exports = class DirectoryExistsPlugin { - /** - * @param {string | ResolveStepHook} source source - * @param {string | ResolveStepHook} target target - */ - constructor(source, target) { - this.source = source; - this.target = target; +/** @typedef {import("../Compiler")} Compiler */ + +// TODO webpack 6 remove + +class FetchCompileWasmPlugin { + constructor(options) { + this.options = options || {}; } /** - * @param {Resolver} resolver the resolver + * Apply the plugin + * @param {Compiler} compiler the compiler instance * @returns {void} */ - apply(resolver) { - const target = resolver.ensureHook(this.target); - resolver - .getHook(this.source) - .tapAsync( - "DirectoryExistsPlugin", - (request, resolveContext, callback) => { - const fs = resolver.fileSystem; - const directory = request.path; - if (!directory) return callback(); - fs.stat(directory, (err, stat) => { - if (err || !stat) { - if (resolveContext.missingDependencies) - resolveContext.missingDependencies.add(directory); - if (resolveContext.log) - resolveContext.log(directory + " doesn't exist"); - return callback(); - } - if (!stat.isDirectory()) { - if (resolveContext.missingDependencies) - resolveContext.missingDependencies.add(directory); - if (resolveContext.log) - resolveContext.log(directory + " is not a directory"); - return callback(); + apply(compiler) { + compiler.hooks.thisCompilation.tap( + "FetchCompileWasmPlugin", + compilation => { + const globalWasmLoading = compilation.outputOptions.wasmLoading; + const isEnabledForChunk = chunk => { + const options = chunk.getEntryOptions(); + const wasmLoading = + options && options.wasmLoading !== undefined + ? options.wasmLoading + : globalWasmLoading; + return wasmLoading === "fetch"; + }; + const generateLoadBinaryCode = path => + `fetch(${RuntimeGlobals.publicPath} + ${path})`; + + compilation.hooks.runtimeRequirementInTree + .for(RuntimeGlobals.ensureChunkHandlers) + .tap("FetchCompileWasmPlugin", (chunk, set) => { + if (!isEnabledForChunk(chunk)) return; + const chunkGraph = compilation.chunkGraph; + if ( + !chunkGraph.hasModuleInGraph( + chunk, + m => m.type === "webassembly/sync" + ) + ) { + return; } - if (resolveContext.fileDependencies) - resolveContext.fileDependencies.add(directory); - resolver.doResolve( - target, - request, - `existing directory ${directory}`, - resolveContext, - callback + set.add(RuntimeGlobals.moduleCache); + set.add(RuntimeGlobals.publicPath); + compilation.addRuntimeModule( + chunk, + new WasmChunkLoadingRuntimeModule({ + generateLoadBinaryCode, + supportsStreaming: true, + mangleImports: this.options.mangleImports, + runtimeRequirements: set + }) ); }); - } - ); + } + ); } -}; +} + +module.exports = FetchCompileWasmPlugin; /***/ }), -/***/ 98169: +/***/ 9253: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; /* MIT License http://www.opensource.org/licenses/mit-license.php - Author Ivan Kopeykin @vankop + Author Tobias Koppers @sokra */ -const path = __webpack_require__(85622); -const DescriptionFileUtils = __webpack_require__(18641); -const forEachBail = __webpack_require__(55426); -const { processExportsField } = __webpack_require__(94340); -const { parseIdentifier } = __webpack_require__(98623); -const { checkExportsFieldTarget } = __webpack_require__(69821); +const RuntimeGlobals = __webpack_require__(49404); +const JsonpChunkLoadingRuntimeModule = __webpack_require__(66032); -/** @typedef {import("./Resolver")} Resolver */ -/** @typedef {import("./Resolver").ResolveStepHook} ResolveStepHook */ -/** @typedef {import("./util/entrypoints").ExportsField} ExportsField */ -/** @typedef {import("./util/entrypoints").FieldProcessor} FieldProcessor */ +/** @typedef {import("../Compiler")} Compiler */ -module.exports = class ExportsFieldPlugin { +class JsonpChunkLoadingPlugin { /** - * @param {string | ResolveStepHook} source source - * @param {Set} conditionNames condition names - * @param {string | string[]} fieldNamePath name path - * @param {string | ResolveStepHook} target target + * Apply the plugin + * @param {Compiler} compiler the compiler instance + * @returns {void} */ - constructor(source, conditionNames, fieldNamePath, target) { - this.source = source; - this.target = target; - this.conditionNames = conditionNames; - this.fieldName = fieldNamePath; - /** @type {WeakMap} */ - this.fieldProcessorCache = new WeakMap(); + apply(compiler) { + compiler.hooks.thisCompilation.tap( + "JsonpChunkLoadingPlugin", + compilation => { + const globalChunkLoading = compilation.outputOptions.chunkLoading; + const isEnabledForChunk = chunk => { + const options = chunk.getEntryOptions(); + const chunkLoading = + options && options.chunkLoading !== undefined + ? options.chunkLoading + : globalChunkLoading; + return chunkLoading === "jsonp"; + }; + const onceForChunkSet = new WeakSet(); + const handler = (chunk, set) => { + if (onceForChunkSet.has(chunk)) return; + onceForChunkSet.add(chunk); + if (!isEnabledForChunk(chunk)) return; + set.add(RuntimeGlobals.moduleFactoriesAddOnly); + set.add(RuntimeGlobals.hasOwnProperty); + compilation.addRuntimeModule( + chunk, + new JsonpChunkLoadingRuntimeModule(set) + ); + }; + compilation.hooks.runtimeRequirementInTree + .for(RuntimeGlobals.ensureChunkHandlers) + .tap("JsonpChunkLoadingPlugin", handler); + compilation.hooks.runtimeRequirementInTree + .for(RuntimeGlobals.hmrDownloadUpdateHandlers) + .tap("JsonpChunkLoadingPlugin", handler); + compilation.hooks.runtimeRequirementInTree + .for(RuntimeGlobals.hmrDownloadManifest) + .tap("JsonpChunkLoadingPlugin", handler); + compilation.hooks.runtimeRequirementInTree + .for(RuntimeGlobals.baseURI) + .tap("JsonpChunkLoadingPlugin", handler); + compilation.hooks.runtimeRequirementInTree + .for(RuntimeGlobals.onChunksLoaded) + .tap("JsonpChunkLoadingPlugin", handler); + + compilation.hooks.runtimeRequirementInTree + .for(RuntimeGlobals.ensureChunkHandlers) + .tap("JsonpChunkLoadingPlugin", (chunk, set) => { + if (!isEnabledForChunk(chunk)) return; + set.add(RuntimeGlobals.publicPath); + set.add(RuntimeGlobals.loadScript); + set.add(RuntimeGlobals.getChunkScriptFilename); + }); + compilation.hooks.runtimeRequirementInTree + .for(RuntimeGlobals.hmrDownloadUpdateHandlers) + .tap("JsonpChunkLoadingPlugin", (chunk, set) => { + if (!isEnabledForChunk(chunk)) return; + set.add(RuntimeGlobals.publicPath); + set.add(RuntimeGlobals.loadScript); + set.add(RuntimeGlobals.getChunkUpdateScriptFilename); + set.add(RuntimeGlobals.moduleCache); + set.add(RuntimeGlobals.hmrModuleData); + set.add(RuntimeGlobals.moduleFactoriesAddOnly); + }); + compilation.hooks.runtimeRequirementInTree + .for(RuntimeGlobals.hmrDownloadManifest) + .tap("JsonpChunkLoadingPlugin", (chunk, set) => { + if (!isEnabledForChunk(chunk)) return; + set.add(RuntimeGlobals.publicPath); + set.add(RuntimeGlobals.getUpdateManifestFilename); + }); + } + ); } +} + +module.exports = JsonpChunkLoadingPlugin; - /** - * @param {Resolver} resolver the resolver - * @returns {void} - */ - apply(resolver) { - const target = resolver.ensureHook(this.target); - resolver - .getHook(this.source) - .tapAsync("ExportsFieldPlugin", (request, resolveContext, callback) => { - // When there is no description file, abort - if (!request.descriptionFilePath) return callback(); - if ( - // When the description file is inherited from parent, abort - // (There is no description file inside of this package) - request.relativePath !== "." || - request.request === undefined - ) - return callback(); - const remainingRequest = - request.query || request.fragment - ? (request.request === "." ? "./" : request.request) + - request.query + - request.fragment - : request.request; - /** @type {ExportsField|null} */ - const exportsField = DescriptionFileUtils.getField( - request.descriptionFileData, - this.fieldName - ); - if (!exportsField) return callback(); +/***/ }), - if (request.directory) { - return callback( - new Error( - `Resolving to directories is not possible with the exports field (request was ${remainingRequest}/)` - ) - ); - } +/***/ 66032: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - let paths; +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php +*/ - try { - // We attach the cache to the description file instead of the exportsField value - // because we use a WeakMap and the exportsField could be a string too. - // Description file is always an object when exports field can be accessed. - let fieldProcessor = this.fieldProcessorCache.get( - request.descriptionFileData - ); - if (fieldProcessor === undefined) { - fieldProcessor = processExportsField(exportsField); - this.fieldProcessorCache.set( - request.descriptionFileData, - fieldProcessor - ); - } - paths = fieldProcessor(remainingRequest, this.conditionNames); - } catch (err) { - if (resolveContext.log) { - resolveContext.log( - `Exports field in ${request.descriptionFilePath} can't be processed: ${err}` - ); - } - return callback(err); - } - if (paths.length === 0) { - return callback( - new Error( - `Package path ${remainingRequest} is not exported from package ${request.descriptionFileRoot} (see exports field in ${request.descriptionFilePath})` - ) - ); - } - forEachBail( - paths, - (p, callback) => { - const parsedIdentifier = parseIdentifier(p); +const { SyncWaterfallHook } = __webpack_require__(34718); +const Compilation = __webpack_require__(59622); +const RuntimeGlobals = __webpack_require__(49404); +const RuntimeModule = __webpack_require__(61439); +const Template = __webpack_require__(92066); +const chunkHasJs = __webpack_require__(76767).chunkHasJs; +const { getInitialChunkIds } = __webpack_require__(30951); +const compileBooleanMatcher = __webpack_require__(356); - if (!parsedIdentifier) return callback(); +/** @typedef {import("../Chunk")} Chunk */ - const [relativePath, query, fragment] = parsedIdentifier; +/** + * @typedef {Object} JsonpCompilationPluginHooks + * @property {SyncWaterfallHook<[string, Chunk]>} linkPreload + * @property {SyncWaterfallHook<[string, Chunk]>} linkPrefetch + */ - const error = checkExportsFieldTarget(relativePath); +/** @type {WeakMap} */ +const compilationHooksMap = new WeakMap(); - if (error) { - return callback(error); - } +class JsonpChunkLoadingRuntimeModule extends RuntimeModule { + /** + * @param {Compilation} compilation the compilation + * @returns {JsonpCompilationPluginHooks} hooks + */ + static getCompilationHooks(compilation) { + if (!(compilation instanceof Compilation)) { + throw new TypeError( + "The 'compilation' argument must be an instance of Compilation" + ); + } + let hooks = compilationHooksMap.get(compilation); + if (hooks === undefined) { + hooks = { + linkPreload: new SyncWaterfallHook(["source", "chunk"]), + linkPrefetch: new SyncWaterfallHook(["source", "chunk"]) + }; + compilationHooksMap.set(compilation, hooks); + } + return hooks; + } - const obj = { - ...request, - request: undefined, - path: path.join( - /** @type {string} */ (request.descriptionFileRoot), - relativePath - ), - relativePath, - query, - fragment - }; + constructor(runtimeRequirements) { + super("jsonp chunk loading", RuntimeModule.STAGE_ATTACH); + this._runtimeRequirements = runtimeRequirements; + } - resolver.doResolve( - target, - obj, - "using exports field: " + p, - resolveContext, - callback - ); - }, - (err, result) => callback(err, result || null) - ); - }); + /** + * @returns {string} runtime code + */ + generate() { + const { chunkGraph, compilation, chunk } = this; + const { + runtimeTemplate, + outputOptions: { + globalObject, + chunkLoadingGlobal, + hotUpdateGlobal, + crossOriginLoading, + scriptType + } + } = compilation; + const { linkPreload, linkPrefetch } = + JsonpChunkLoadingRuntimeModule.getCompilationHooks(compilation); + const fn = RuntimeGlobals.ensureChunkHandlers; + const withBaseURI = this._runtimeRequirements.has(RuntimeGlobals.baseURI); + const withLoading = this._runtimeRequirements.has( + RuntimeGlobals.ensureChunkHandlers + ); + const withCallback = this._runtimeRequirements.has( + RuntimeGlobals.chunkCallback + ); + const withOnChunkLoad = this._runtimeRequirements.has( + RuntimeGlobals.onChunksLoaded + ); + const withHmr = this._runtimeRequirements.has( + RuntimeGlobals.hmrDownloadUpdateHandlers + ); + const withHmrManifest = this._runtimeRequirements.has( + RuntimeGlobals.hmrDownloadManifest + ); + const withPrefetch = this._runtimeRequirements.has( + RuntimeGlobals.prefetchChunkHandlers + ); + const withPreload = this._runtimeRequirements.has( + RuntimeGlobals.preloadChunkHandlers + ); + const chunkLoadingGlobalExpr = `${globalObject}[${JSON.stringify( + chunkLoadingGlobal + )}]`; + const conditionMap = chunkGraph.getChunkConditionMap(chunk, chunkHasJs); + const hasJsMatcher = compileBooleanMatcher(conditionMap); + const initialChunkIds = getInitialChunkIds(chunk, chunkGraph); + + const stateExpression = withHmr + ? `${RuntimeGlobals.hmrRuntimeStatePrefix}_jsonp` + : undefined; + + return Template.asString([ + withBaseURI + ? Template.asString([ + `${RuntimeGlobals.baseURI} = document.baseURI || self.location.href;` + ]) + : "// no baseURI", + "", + "// object to store loaded and loading chunks", + "// undefined = chunk not loaded, null = chunk preloaded/prefetched", + "// [resolve, reject, Promise] = chunk loading, 0 = chunk loaded", + `var installedChunks = ${ + stateExpression ? `${stateExpression} = ${stateExpression} || ` : "" + }{`, + Template.indent( + Array.from(initialChunkIds, id => `${JSON.stringify(id)}: 0`).join( + ",\n" + ) + ), + "};", + "", + withLoading + ? Template.asString([ + `${fn}.j = ${runtimeTemplate.basicFunction( + "chunkId, promises", + hasJsMatcher !== false + ? Template.indent([ + "// JSONP chunk loading for javascript", + `var installedChunkData = ${RuntimeGlobals.hasOwnProperty}(installedChunks, chunkId) ? installedChunks[chunkId] : undefined;`, + 'if(installedChunkData !== 0) { // 0 means "already installed".', + Template.indent([ + "", + '// a Promise means "currently loading".', + "if(installedChunkData) {", + Template.indent([ + "promises.push(installedChunkData[2]);" + ]), + "} else {", + Template.indent([ + hasJsMatcher === true + ? "if(true) { // all chunks have JS" + : `if(${hasJsMatcher("chunkId")}) {`, + Template.indent([ + "// setup Promise in chunk cache", + `var promise = new Promise(${runtimeTemplate.expressionFunction( + `installedChunkData = installedChunks[chunkId] = [resolve, reject]`, + "resolve, reject" + )});`, + "promises.push(installedChunkData[2] = promise);", + "", + "// start chunk loading", + `var url = ${RuntimeGlobals.publicPath} + ${RuntimeGlobals.getChunkScriptFilename}(chunkId);`, + "// create error before stack unwound to get useful stacktrace later", + "var error = new Error();", + `var loadingEnded = ${runtimeTemplate.basicFunction( + "event", + [ + `if(${RuntimeGlobals.hasOwnProperty}(installedChunks, chunkId)) {`, + Template.indent([ + "installedChunkData = installedChunks[chunkId];", + "if(installedChunkData !== 0) installedChunks[chunkId] = undefined;", + "if(installedChunkData) {", + Template.indent([ + "var errorType = event && (event.type === 'load' ? 'missing' : event.type);", + "var realSrc = event && event.target && event.target.src;", + "error.message = 'Loading chunk ' + chunkId + ' failed.\\n(' + errorType + ': ' + realSrc + ')';", + "error.name = 'ChunkLoadError';", + "error.type = errorType;", + "error.request = realSrc;", + "installedChunkData[1](error);" + ]), + "}" + ]), + "}" + ] + )};`, + `${RuntimeGlobals.loadScript}(url, loadingEnded, "chunk-" + chunkId, chunkId);` + ]), + "} else installedChunks[chunkId] = 0;" + ]), + "}" + ]), + "}" + ]) + : Template.indent(["installedChunks[chunkId] = 0;"]) + )};` + ]) + : "// no chunk on demand loading", + "", + withPrefetch && hasJsMatcher !== false + ? `${ + RuntimeGlobals.prefetchChunkHandlers + }.j = ${runtimeTemplate.basicFunction("chunkId", [ + `if((!${ + RuntimeGlobals.hasOwnProperty + }(installedChunks, chunkId) || installedChunks[chunkId] === undefined) && ${ + hasJsMatcher === true ? "true" : hasJsMatcher("chunkId") + }) {`, + Template.indent([ + "installedChunks[chunkId] = null;", + linkPrefetch.call( + Template.asString([ + "var link = document.createElement('link');", + crossOriginLoading + ? `link.crossOrigin = ${JSON.stringify( + crossOriginLoading + )};` + : "", + `if (${RuntimeGlobals.scriptNonce}) {`, + Template.indent( + `link.setAttribute("nonce", ${RuntimeGlobals.scriptNonce});` + ), + "}", + 'link.rel = "prefetch";', + 'link.as = "script";', + `link.href = ${RuntimeGlobals.publicPath} + ${RuntimeGlobals.getChunkScriptFilename}(chunkId);` + ]), + chunk + ), + "document.head.appendChild(link);" + ]), + "}" + ])};` + : "// no prefetching", + "", + withPreload && hasJsMatcher !== false + ? `${ + RuntimeGlobals.preloadChunkHandlers + }.j = ${runtimeTemplate.basicFunction("chunkId", [ + `if((!${ + RuntimeGlobals.hasOwnProperty + }(installedChunks, chunkId) || installedChunks[chunkId] === undefined) && ${ + hasJsMatcher === true ? "true" : hasJsMatcher("chunkId") + }) {`, + Template.indent([ + "installedChunks[chunkId] = null;", + linkPreload.call( + Template.asString([ + "var link = document.createElement('link');", + scriptType + ? `link.type = ${JSON.stringify(scriptType)};` + : "", + "link.charset = 'utf-8';", + `if (${RuntimeGlobals.scriptNonce}) {`, + Template.indent( + `link.setAttribute("nonce", ${RuntimeGlobals.scriptNonce});` + ), + "}", + 'link.rel = "preload";', + 'link.as = "script";', + `link.href = ${RuntimeGlobals.publicPath} + ${RuntimeGlobals.getChunkScriptFilename}(chunkId);`, + crossOriginLoading + ? Template.asString([ + "if (link.href.indexOf(window.location.origin + '/') !== 0) {", + Template.indent( + `link.crossOrigin = ${JSON.stringify( + crossOriginLoading + )};` + ), + "}" + ]) + : "" + ]), + chunk + ), + "document.head.appendChild(link);" + ]), + "}" + ])};` + : "// no preloaded", + "", + withHmr + ? Template.asString([ + "var currentUpdatedModulesList;", + "var waitingUpdateResolves = {};", + "function loadUpdateChunk(chunkId) {", + Template.indent([ + `return new Promise(${runtimeTemplate.basicFunction( + "resolve, reject", + [ + "waitingUpdateResolves[chunkId] = resolve;", + "// start update chunk loading", + `var url = ${RuntimeGlobals.publicPath} + ${RuntimeGlobals.getChunkUpdateScriptFilename}(chunkId);`, + "// create error before stack unwound to get useful stacktrace later", + "var error = new Error();", + `var loadingEnded = ${runtimeTemplate.basicFunction("event", [ + "if(waitingUpdateResolves[chunkId]) {", + Template.indent([ + "waitingUpdateResolves[chunkId] = undefined", + "var errorType = event && (event.type === 'load' ? 'missing' : event.type);", + "var realSrc = event && event.target && event.target.src;", + "error.message = 'Loading hot update chunk ' + chunkId + ' failed.\\n(' + errorType + ': ' + realSrc + ')';", + "error.name = 'ChunkLoadError';", + "error.type = errorType;", + "error.request = realSrc;", + "reject(error);" + ]), + "}" + ])};`, + `${RuntimeGlobals.loadScript}(url, loadingEnded);` + ] + )});` + ]), + "}", + "", + `${globalObject}[${JSON.stringify( + hotUpdateGlobal + )}] = ${runtimeTemplate.basicFunction( + "chunkId, moreModules, runtime", + [ + "for(var moduleId in moreModules) {", + Template.indent([ + `if(${RuntimeGlobals.hasOwnProperty}(moreModules, moduleId)) {`, + Template.indent([ + "currentUpdate[moduleId] = moreModules[moduleId];", + "if(currentUpdatedModulesList) currentUpdatedModulesList.push(moduleId);" + ]), + "}" + ]), + "}", + "if(runtime) currentUpdateRuntime.push(runtime);", + "if(waitingUpdateResolves[chunkId]) {", + Template.indent([ + "waitingUpdateResolves[chunkId]();", + "waitingUpdateResolves[chunkId] = undefined;" + ]), + "}" + ] + )};`, + "", + Template.getFunctionContent( + require('./JavascriptHotModuleReplacement.runtime.js') + ) + .replace(/\$key\$/g, "jsonp") + .replace(/\$installedChunks\$/g, "installedChunks") + .replace(/\$loadUpdateChunk\$/g, "loadUpdateChunk") + .replace(/\$moduleCache\$/g, RuntimeGlobals.moduleCache) + .replace(/\$moduleFactories\$/g, RuntimeGlobals.moduleFactories) + .replace( + /\$ensureChunkHandlers\$/g, + RuntimeGlobals.ensureChunkHandlers + ) + .replace(/\$hasOwnProperty\$/g, RuntimeGlobals.hasOwnProperty) + .replace(/\$hmrModuleData\$/g, RuntimeGlobals.hmrModuleData) + .replace( + /\$hmrDownloadUpdateHandlers\$/g, + RuntimeGlobals.hmrDownloadUpdateHandlers + ) + .replace( + /\$hmrInvalidateModuleHandlers\$/g, + RuntimeGlobals.hmrInvalidateModuleHandlers + ) + ]) + : "// no HMR", + "", + withHmrManifest + ? Template.asString([ + `${ + RuntimeGlobals.hmrDownloadManifest + } = ${runtimeTemplate.basicFunction("", [ + 'if (typeof fetch === "undefined") throw new Error("No browser support: need fetch API");', + `return fetch(${RuntimeGlobals.publicPath} + ${ + RuntimeGlobals.getUpdateManifestFilename + }()).then(${runtimeTemplate.basicFunction("response", [ + "if(response.status === 404) return; // no update available", + 'if(!response.ok) throw new Error("Failed to fetch update manifest " + response.statusText);', + "return response.json();" + ])});` + ])};` + ]) + : "// no HMR manifest", + "", + withOnChunkLoad + ? `${ + RuntimeGlobals.onChunksLoaded + }.j = ${runtimeTemplate.returningFunction( + "installedChunks[chunkId] === 0", + "chunkId" + )};` + : "// no on chunks loaded", + "", + withCallback || withLoading + ? Template.asString([ + "// install a JSONP callback for chunk loading", + `var webpackJsonpCallback = ${runtimeTemplate.basicFunction( + "parentChunkLoadingFunction, data", + [ + runtimeTemplate.destructureArray( + ["chunkIds", "moreModules", "runtime"], + "data" + ), + '// add "moreModules" to the modules object,', + '// then flag all "chunkIds" as loaded and fire callback', + "var moduleId, chunkId, i = 0;", + `if(chunkIds.some(${runtimeTemplate.returningFunction( + "installedChunks[id] !== 0", + "id" + )})) {`, + Template.indent([ + "for(moduleId in moreModules) {", + Template.indent([ + `if(${RuntimeGlobals.hasOwnProperty}(moreModules, moduleId)) {`, + Template.indent( + `${RuntimeGlobals.moduleFactories}[moduleId] = moreModules[moduleId];` + ), + "}" + ]), + "}", + "if(runtime) var result = runtime(__webpack_require__);" + ]), + "}", + "if(parentChunkLoadingFunction) parentChunkLoadingFunction(data);", + "for(;i < chunkIds.length; i++) {", + Template.indent([ + "chunkId = chunkIds[i];", + `if(${RuntimeGlobals.hasOwnProperty}(installedChunks, chunkId) && installedChunks[chunkId]) {`, + Template.indent("installedChunks[chunkId][0]();"), + "}", + "installedChunks[chunkIds[i]] = 0;" + ]), + "}", + withOnChunkLoad + ? `return ${RuntimeGlobals.onChunksLoaded}(result);` + : "" + ] + )}`, + "", + `var chunkLoadingGlobal = ${chunkLoadingGlobalExpr} = ${chunkLoadingGlobalExpr} || [];`, + "chunkLoadingGlobal.forEach(webpackJsonpCallback.bind(null, 0));", + "chunkLoadingGlobal.push = webpackJsonpCallback.bind(null, chunkLoadingGlobal.push.bind(chunkLoadingGlobal));" + ]) + : "// no jsonp function" + ]); } -}; +} + +module.exports = JsonpChunkLoadingRuntimeModule; /***/ }), -/***/ 9412: -/***/ (function(module) { +/***/ 45968: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; /* @@ -136322,242 +135940,222 @@ module.exports = class ExportsFieldPlugin { -/** @typedef {import("./Resolver")} Resolver */ -/** @typedef {import("./Resolver").ResolveStepHook} ResolveStepHook */ +const ArrayPushCallbackChunkFormatPlugin = __webpack_require__(86189); +const EnableChunkLoadingPlugin = __webpack_require__(34726); +const JsonpChunkLoadingRuntimeModule = __webpack_require__(66032); -module.exports = class FileExistsPlugin { +/** @typedef {import("../Chunk")} Chunk */ +/** @typedef {import("../Compilation")} Compilation */ +/** @typedef {import("../Compiler")} Compiler */ + +class JsonpTemplatePlugin { /** - * @param {string | ResolveStepHook} source source - * @param {string | ResolveStepHook} target target + * @deprecated use JsonpChunkLoadingRuntimeModule.getCompilationHooks instead + * @param {Compilation} compilation the compilation + * @returns {JsonpChunkLoadingRuntimeModule.JsonpCompilationPluginHooks} hooks */ - constructor(source, target) { - this.source = source; - this.target = target; + static getCompilationHooks(compilation) { + return JsonpChunkLoadingRuntimeModule.getCompilationHooks(compilation); } /** - * @param {Resolver} resolver the resolver + * Apply the plugin + * @param {Compiler} compiler the compiler instance * @returns {void} */ - apply(resolver) { - const target = resolver.ensureHook(this.target); - const fs = resolver.fileSystem; - resolver - .getHook(this.source) - .tapAsync("FileExistsPlugin", (request, resolveContext, callback) => { - const file = request.path; - if (!file) return callback(); - fs.stat(file, (err, stat) => { - if (err || !stat) { - if (resolveContext.missingDependencies) - resolveContext.missingDependencies.add(file); - if (resolveContext.log) resolveContext.log(file + " doesn't exist"); - return callback(); - } - if (!stat.isFile()) { - if (resolveContext.missingDependencies) - resolveContext.missingDependencies.add(file); - if (resolveContext.log) resolveContext.log(file + " is not a file"); - return callback(); - } - if (resolveContext.fileDependencies) - resolveContext.fileDependencies.add(file); - resolver.doResolve( - target, - request, - "existing file: " + file, - resolveContext, - callback - ); - }); - }); + apply(compiler) { + compiler.options.output.chunkLoading = "jsonp"; + new ArrayPushCallbackChunkFormatPlugin().apply(compiler); + new EnableChunkLoadingPlugin("jsonp").apply(compiler); } -}; +} + +module.exports = JsonpTemplatePlugin; /***/ }), -/***/ 41031: +/***/ 86128: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; /* MIT License http://www.opensource.org/licenses/mit-license.php - Author Ivan Kopeykin @vankop + Author Tobias Koppers @sokra */ -const path = __webpack_require__(85622); -const DescriptionFileUtils = __webpack_require__(18641); -const forEachBail = __webpack_require__(55426); -const { processImportsField } = __webpack_require__(94340); -const { parseIdentifier } = __webpack_require__(98623); - -/** @typedef {import("./Resolver")} Resolver */ -/** @typedef {import("./Resolver").ResolveStepHook} ResolveStepHook */ -/** @typedef {import("./util/entrypoints").FieldProcessor} FieldProcessor */ -/** @typedef {import("./util/entrypoints").ImportsField} ImportsField */ - -const dotCode = ".".charCodeAt(0); - -module.exports = class ImportsFieldPlugin { - /** - * @param {string | ResolveStepHook} source source - * @param {Set} conditionNames condition names - * @param {string | string[]} fieldNamePath name path - * @param {string | ResolveStepHook} targetFile target file - * @param {string | ResolveStepHook} targetPackage target package - */ - constructor( - source, - conditionNames, - fieldNamePath, - targetFile, - targetPackage - ) { - this.source = source; - this.targetFile = targetFile; - this.targetPackage = targetPackage; - this.conditionNames = conditionNames; - this.fieldName = fieldNamePath; - /** @type {WeakMap} */ - this.fieldProcessorCache = new WeakMap(); - } - - /** - * @param {Resolver} resolver the resolver - * @returns {void} - */ - apply(resolver) { - const targetFile = resolver.ensureHook(this.targetFile); - const targetPackage = resolver.ensureHook(this.targetPackage); - - resolver - .getHook(this.source) - .tapAsync("ImportsFieldPlugin", (request, resolveContext, callback) => { - // When there is no description file, abort - if (!request.descriptionFilePath || request.request === undefined) { - return callback(); - } - - const remainingRequest = - request.request + request.query + request.fragment; - /** @type {ImportsField|null} */ - const importsField = DescriptionFileUtils.getField( - request.descriptionFileData, - this.fieldName - ); - if (!importsField) return callback(); - - if (request.directory) { - return callback( - new Error( - `Resolving to directories is not possible with the imports field (request was ${remainingRequest}/)` - ) - ); - } - - let paths; +const util = __webpack_require__(31669); +const webpackOptionsSchemaCheck = __webpack_require__(97220); +const webpackOptionsSchema = __webpack_require__(1863); +const Compiler = __webpack_require__(11777); +const MultiCompiler = __webpack_require__(73663); +const WebpackOptionsApply = __webpack_require__(44137); +const { + applyWebpackOptionsDefaults, + applyWebpackOptionsBaseDefaults +} = __webpack_require__(27057); +const { getNormalizedWebpackOptions } = __webpack_require__(52975); +const NodeEnvironmentPlugin = __webpack_require__(38857); +const memoize = __webpack_require__(84297); - try { - // We attach the cache to the description file instead of the importsField value - // because we use a WeakMap and the importsField could be a string too. - // Description file is always an object when exports field can be accessed. - let fieldProcessor = this.fieldProcessorCache.get( - request.descriptionFileData - ); - if (fieldProcessor === undefined) { - fieldProcessor = processImportsField(importsField); - this.fieldProcessorCache.set( - request.descriptionFileData, - fieldProcessor - ); - } - paths = fieldProcessor(remainingRequest, this.conditionNames); - } catch (err) { - if (resolveContext.log) { - resolveContext.log( - `Imports field in ${request.descriptionFilePath} can't be processed: ${err}` - ); - } - return callback(err); - } +/** @typedef {import("../declarations/WebpackOptions").WebpackOptions} WebpackOptions */ +/** @typedef {import("./Compiler").WatchOptions} WatchOptions */ +/** @typedef {import("./MultiCompiler").MultiCompilerOptions} MultiCompilerOptions */ +/** @typedef {import("./MultiStats")} MultiStats */ +/** @typedef {import("./Stats")} Stats */ - if (paths.length === 0) { - return callback( - new Error( - `Package import ${remainingRequest} is not imported from package ${request.descriptionFileRoot} (see imports field in ${request.descriptionFilePath})` - ) - ); - } +const getValidateSchema = memoize(() => __webpack_require__(55959)); - forEachBail( - paths, - (p, callback) => { - const parsedIdentifier = parseIdentifier(p); +/** + * @template T + * @callback Callback + * @param {Error=} err + * @param {T=} stats + * @returns {void} + */ - if (!parsedIdentifier) return callback(); +/** + * @param {ReadonlyArray} childOptions options array + * @param {MultiCompilerOptions} options options + * @returns {MultiCompiler} a multi-compiler + */ +const createMultiCompiler = (childOptions, options) => { + const compilers = childOptions.map(options => createCompiler(options)); + const compiler = new MultiCompiler(compilers, options); + for (const childCompiler of compilers) { + if (childCompiler.options.dependencies) { + compiler.setDependencies( + childCompiler, + childCompiler.options.dependencies + ); + } + } + return compiler; +}; - const [path_, query, fragment] = parsedIdentifier; +/** + * @param {WebpackOptions} rawOptions options object + * @returns {Compiler} a compiler + */ +const createCompiler = rawOptions => { + const options = getNormalizedWebpackOptions(rawOptions); + applyWebpackOptionsBaseDefaults(options); + const compiler = new Compiler(options.context, options); + new NodeEnvironmentPlugin({ + infrastructureLogging: options.infrastructureLogging + }).apply(compiler); + if (Array.isArray(options.plugins)) { + for (const plugin of options.plugins) { + if (typeof plugin === "function") { + plugin.call(compiler, compiler); + } else { + plugin.apply(compiler); + } + } + } + applyWebpackOptionsDefaults(options); + compiler.hooks.environment.call(); + compiler.hooks.afterEnvironment.call(); + new WebpackOptionsApply().process(options, compiler); + compiler.hooks.initialize.call(); + return compiler; +}; - switch (path_.charCodeAt(0)) { - // should be relative - case dotCode: { - const obj = { - ...request, - request: undefined, - path: path.join( - /** @type {string} */ (request.descriptionFileRoot), - path_ - ), - relativePath: path_, - query, - fragment - }; +/** + * @callback WebpackFunctionSingle + * @param {WebpackOptions} options options object + * @param {Callback=} callback callback + * @returns {Compiler} the compiler object + */ - resolver.doResolve( - targetFile, - obj, - "using imports field: " + p, - resolveContext, - callback - ); - break; - } +/** + * @callback WebpackFunctionMulti + * @param {ReadonlyArray & MultiCompilerOptions} options options objects + * @param {Callback=} callback callback + * @returns {MultiCompiler} the multi compiler object + */ - // package resolving - default: { - const obj = { - ...request, - request: path_, - relativePath: path_, - fullySpecified: true, - query, - fragment - }; +const asArray = options => + Array.isArray(options) ? Array.from(options) : [options]; - resolver.doResolve( - targetPackage, - obj, - "using imports field: " + p, - resolveContext, - callback - ); - } - } - }, - (err, result) => callback(err, result || null) +const webpack = /** @type {WebpackFunctionSingle & WebpackFunctionMulti} */ ( + /** + * @param {WebpackOptions | (ReadonlyArray & MultiCompilerOptions)} options options + * @param {Callback & Callback=} callback callback + * @returns {Compiler | MultiCompiler} + */ + (options, callback) => { + const create = () => { + if (!asArray(options).every(webpackOptionsSchemaCheck)) { + getValidateSchema()(webpackOptionsSchema, options); + util.deprecate( + () => {}, + "webpack bug: Pre-compiled schema reports error while real schema is happy. This has performance drawbacks.", + "DEP_WEBPACK_PRE_COMPILED_SCHEMA_INVALID" + )(); + } + /** @type {MultiCompiler|Compiler} */ + let compiler; + let watch = false; + /** @type {WatchOptions|WatchOptions[]} */ + let watchOptions; + if (Array.isArray(options)) { + /** @type {MultiCompiler} */ + compiler = createMultiCompiler( + options, + /** @type {MultiCompilerOptions} */ (options) ); - }); + watch = options.some(options => options.watch); + watchOptions = options.map(options => options.watchOptions || {}); + } else { + const webpackOptions = /** @type {WebpackOptions} */ (options); + /** @type {Compiler} */ + compiler = createCompiler(webpackOptions); + watch = webpackOptions.watch; + watchOptions = webpackOptions.watchOptions || {}; + } + return { compiler, watch, watchOptions }; + }; + if (callback) { + try { + const { compiler, watch, watchOptions } = create(); + if (watch) { + compiler.watch(watchOptions, callback); + } else { + compiler.run((err, stats) => { + compiler.close(err2 => { + callback(err || err2, stats); + }); + }); + } + return compiler; + } catch (err) { + process.nextTick(() => callback(err)); + return null; + } + } else { + const { compiler, watch } = create(); + if (watch) { + util.deprecate( + () => {}, + "A 'callback' argument needs to be provided to the 'webpack(options, callback)' function when the 'watch' option is set. There is no way to handle the 'watch' option without a callback.", + "DEP_WEBPACK_WATCH_WITHOUT_CALLBACK" + )(); + } + return compiler; + } } -}; +); + +module.exports = webpack; /***/ }), -/***/ 11399: -/***/ (function(module) { +/***/ 56354: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; /* @@ -136567,118 +136165,342 @@ module.exports = class ImportsFieldPlugin { -/** @typedef {import("./Resolver")} Resolver */ -/** @typedef {import("./Resolver").ResolveStepHook} ResolveStepHook */ - -const namespaceStartCharCode = "@".charCodeAt(0); +const RuntimeGlobals = __webpack_require__(49404); +const CreateScriptUrlRuntimeModule = __webpack_require__(41690); +const StartupChunkDependenciesPlugin = __webpack_require__(23613); +const ImportScriptsChunkLoadingRuntimeModule = __webpack_require__(45936); -module.exports = class JoinRequestPartPlugin { - /** - * @param {string | ResolveStepHook} source source - * @param {string | ResolveStepHook} target target - */ - constructor(source, target) { - this.source = source; - this.target = target; - } +/** @typedef {import("../Compiler")} Compiler */ +class ImportScriptsChunkLoadingPlugin { /** - * @param {Resolver} resolver the resolver + * Apply the plugin + * @param {Compiler} compiler the compiler instance * @returns {void} */ - apply(resolver) { - const target = resolver.ensureHook(this.target); - resolver - .getHook(this.source) - .tapAsync( - "JoinRequestPartPlugin", - (request, resolveContext, callback) => { - const req = request.request || ""; - let i = req.indexOf("/", 3); - - if (i >= 0 && req.charCodeAt(2) === namespaceStartCharCode) { - i = req.indexOf("/", i + 1); - } - - let moduleName, remainingRequest, fullySpecified; - if (i < 0) { - moduleName = req; - remainingRequest = "."; - fullySpecified = false; - } else { - moduleName = req.slice(0, i); - remainingRequest = "." + req.slice(i); - fullySpecified = request.fullySpecified; - } - const obj = { - ...request, - path: resolver.join(request.path, moduleName), - relativePath: - request.relativePath && - resolver.join(request.relativePath, moduleName), - request: remainingRequest, - fullySpecified - }; - resolver.doResolve(target, obj, null, resolveContext, callback); - } - ); + apply(compiler) { + new StartupChunkDependenciesPlugin({ + chunkLoading: "import-scripts", + asyncChunkLoading: true + }).apply(compiler); + compiler.hooks.thisCompilation.tap( + "ImportScriptsChunkLoadingPlugin", + compilation => { + const globalChunkLoading = compilation.outputOptions.chunkLoading; + const isEnabledForChunk = chunk => { + const options = chunk.getEntryOptions(); + const chunkLoading = + options && options.chunkLoading !== undefined + ? options.chunkLoading + : globalChunkLoading; + return chunkLoading === "import-scripts"; + }; + const onceForChunkSet = new WeakSet(); + const handler = (chunk, set) => { + if (onceForChunkSet.has(chunk)) return; + onceForChunkSet.add(chunk); + if (!isEnabledForChunk(chunk)) return; + const withCreateScriptUrl = !!compilation.outputOptions.trustedTypes; + set.add(RuntimeGlobals.moduleFactoriesAddOnly); + set.add(RuntimeGlobals.hasOwnProperty); + if (withCreateScriptUrl) set.add(RuntimeGlobals.createScriptUrl); + compilation.addRuntimeModule( + chunk, + new ImportScriptsChunkLoadingRuntimeModule(set, withCreateScriptUrl) + ); + }; + compilation.hooks.runtimeRequirementInTree + .for(RuntimeGlobals.ensureChunkHandlers) + .tap("ImportScriptsChunkLoadingPlugin", handler); + compilation.hooks.runtimeRequirementInTree + .for(RuntimeGlobals.hmrDownloadUpdateHandlers) + .tap("ImportScriptsChunkLoadingPlugin", handler); + compilation.hooks.runtimeRequirementInTree + .for(RuntimeGlobals.hmrDownloadManifest) + .tap("ImportScriptsChunkLoadingPlugin", handler); + compilation.hooks.runtimeRequirementInTree + .for(RuntimeGlobals.baseURI) + .tap("ImportScriptsChunkLoadingPlugin", handler); + compilation.hooks.runtimeRequirementInTree + .for(RuntimeGlobals.createScriptUrl) + .tap("RuntimePlugin", (chunk, set) => { + compilation.addRuntimeModule( + chunk, + new CreateScriptUrlRuntimeModule() + ); + return true; + }); + + compilation.hooks.runtimeRequirementInTree + .for(RuntimeGlobals.ensureChunkHandlers) + .tap("ImportScriptsChunkLoadingPlugin", (chunk, set) => { + if (!isEnabledForChunk(chunk)) return; + set.add(RuntimeGlobals.publicPath); + set.add(RuntimeGlobals.getChunkScriptFilename); + }); + compilation.hooks.runtimeRequirementInTree + .for(RuntimeGlobals.hmrDownloadUpdateHandlers) + .tap("ImportScriptsChunkLoadingPlugin", (chunk, set) => { + if (!isEnabledForChunk(chunk)) return; + set.add(RuntimeGlobals.publicPath); + set.add(RuntimeGlobals.getChunkUpdateScriptFilename); + set.add(RuntimeGlobals.moduleCache); + set.add(RuntimeGlobals.hmrModuleData); + set.add(RuntimeGlobals.moduleFactoriesAddOnly); + }); + compilation.hooks.runtimeRequirementInTree + .for(RuntimeGlobals.hmrDownloadManifest) + .tap("ImportScriptsChunkLoadingPlugin", (chunk, set) => { + if (!isEnabledForChunk(chunk)) return; + set.add(RuntimeGlobals.publicPath); + set.add(RuntimeGlobals.getUpdateManifestFilename); + }); + } + ); } -}; +} +module.exports = ImportScriptsChunkLoadingPlugin; /***/ }), -/***/ 90522: -/***/ (function(module) { +/***/ 45936: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; /* MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra */ -/** @typedef {import("./Resolver")} Resolver */ -/** @typedef {import("./Resolver").ResolveStepHook} ResolveStepHook */ +const RuntimeGlobals = __webpack_require__(49404); +const RuntimeModule = __webpack_require__(61439); +const Template = __webpack_require__(92066); +const { + getChunkFilenameTemplate, + chunkHasJs +} = __webpack_require__(76767); +const { getInitialChunkIds } = __webpack_require__(30951); +const compileBooleanMatcher = __webpack_require__(356); +const { getUndoPath } = __webpack_require__(96236); -module.exports = class JoinRequestPlugin { - /** - * @param {string | ResolveStepHook} source source - * @param {string | ResolveStepHook} target target - */ - constructor(source, target) { - this.source = source; - this.target = target; +class ImportScriptsChunkLoadingRuntimeModule extends RuntimeModule { + constructor(runtimeRequirements, withCreateScriptUrl) { + super("importScripts chunk loading", RuntimeModule.STAGE_ATTACH); + this.runtimeRequirements = runtimeRequirements; + this._withCreateScriptUrl = withCreateScriptUrl; } /** - * @param {Resolver} resolver the resolver - * @returns {void} + * @returns {string} runtime code */ - apply(resolver) { - const target = resolver.ensureHook(this.target); - resolver - .getHook(this.source) - .tapAsync("JoinRequestPlugin", (request, resolveContext, callback) => { - const obj = { - ...request, - path: resolver.join(request.path, request.request), - relativePath: - request.relativePath && - resolver.join(request.relativePath, request.request), - request: undefined - }; - resolver.doResolve(target, obj, null, resolveContext, callback); - }); + generate() { + const { + chunk, + chunkGraph, + compilation: { + runtimeTemplate, + outputOptions: { globalObject, chunkLoadingGlobal, hotUpdateGlobal } + }, + _withCreateScriptUrl: withCreateScriptUrl + } = this; + const fn = RuntimeGlobals.ensureChunkHandlers; + const withBaseURI = this.runtimeRequirements.has(RuntimeGlobals.baseURI); + const withLoading = this.runtimeRequirements.has( + RuntimeGlobals.ensureChunkHandlers + ); + const withHmr = this.runtimeRequirements.has( + RuntimeGlobals.hmrDownloadUpdateHandlers + ); + const withHmrManifest = this.runtimeRequirements.has( + RuntimeGlobals.hmrDownloadManifest + ); + const chunkLoadingGlobalExpr = `${globalObject}[${JSON.stringify( + chunkLoadingGlobal + )}]`; + const hasJsMatcher = compileBooleanMatcher( + chunkGraph.getChunkConditionMap(chunk, chunkHasJs) + ); + const initialChunkIds = getInitialChunkIds(chunk, chunkGraph); + + const outputName = this.compilation.getPath( + getChunkFilenameTemplate(chunk, this.compilation.outputOptions), + { + chunk, + contentHashType: "javascript" + } + ); + const rootOutputDir = getUndoPath( + outputName, + this.compilation.outputOptions.path, + false + ); + + const stateExpression = withHmr + ? `${RuntimeGlobals.hmrRuntimeStatePrefix}_importScripts` + : undefined; + + return Template.asString([ + withBaseURI + ? Template.asString([ + `${RuntimeGlobals.baseURI} = self.location + ${JSON.stringify( + rootOutputDir ? "/../" + rootOutputDir : "" + )};` + ]) + : "// no baseURI", + "", + "// object to store loaded chunks", + '// "1" means "already loaded"', + `var installedChunks = ${ + stateExpression ? `${stateExpression} = ${stateExpression} || ` : "" + }{`, + Template.indent( + Array.from(initialChunkIds, id => `${JSON.stringify(id)}: 1`).join( + ",\n" + ) + ), + "};", + "", + withLoading + ? Template.asString([ + "// importScripts chunk loading", + `var installChunk = ${runtimeTemplate.basicFunction("data", [ + runtimeTemplate.destructureArray( + ["chunkIds", "moreModules", "runtime"], + "data" + ), + "for(var moduleId in moreModules) {", + Template.indent([ + `if(${RuntimeGlobals.hasOwnProperty}(moreModules, moduleId)) {`, + Template.indent( + `${RuntimeGlobals.moduleFactories}[moduleId] = moreModules[moduleId];` + ), + "}" + ]), + "}", + "if(runtime) runtime(__webpack_require__);", + "while(chunkIds.length)", + Template.indent("installedChunks[chunkIds.pop()] = 1;"), + "parentChunkLoadingFunction(data);" + ])};` + ]) + : "// no chunk install function needed", + withLoading + ? Template.asString([ + `${fn}.i = ${runtimeTemplate.basicFunction( + "chunkId, promises", + hasJsMatcher !== false + ? [ + '// "1" is the signal for "already loaded"', + "if(!installedChunks[chunkId]) {", + Template.indent([ + hasJsMatcher === true + ? "if(true) { // all chunks have JS" + : `if(${hasJsMatcher("chunkId")}) {`, + Template.indent( + `importScripts(${ + withCreateScriptUrl + ? `${RuntimeGlobals.createScriptUrl}(${RuntimeGlobals.publicPath} + ${RuntimeGlobals.getChunkScriptFilename}(chunkId))` + : `${RuntimeGlobals.publicPath} + ${RuntimeGlobals.getChunkScriptFilename}(chunkId)` + });` + ), + "}" + ]), + "}" + ] + : "installedChunks[chunkId] = 1;" + )};`, + "", + `var chunkLoadingGlobal = ${chunkLoadingGlobalExpr} = ${chunkLoadingGlobalExpr} || [];`, + "var parentChunkLoadingFunction = chunkLoadingGlobal.push.bind(chunkLoadingGlobal);", + "chunkLoadingGlobal.push = installChunk;" + ]) + : "// no chunk loading", + "", + withHmr + ? Template.asString([ + "function loadUpdateChunk(chunkId, updatedModulesList) {", + Template.indent([ + "var success = false;", + `${globalObject}[${JSON.stringify( + hotUpdateGlobal + )}] = ${runtimeTemplate.basicFunction("_, moreModules, runtime", [ + "for(var moduleId in moreModules) {", + Template.indent([ + `if(${RuntimeGlobals.hasOwnProperty}(moreModules, moduleId)) {`, + Template.indent([ + "currentUpdate[moduleId] = moreModules[moduleId];", + "if(updatedModulesList) updatedModulesList.push(moduleId);" + ]), + "}" + ]), + "}", + "if(runtime) currentUpdateRuntime.push(runtime);", + "success = true;" + ])};`, + "// start update chunk loading", + `importScripts(${ + withCreateScriptUrl + ? `${RuntimeGlobals.createScriptUrl}(${RuntimeGlobals.publicPath} + ${RuntimeGlobals.getChunkUpdateScriptFilename}(chunkId))` + : `${RuntimeGlobals.publicPath} + ${RuntimeGlobals.getChunkUpdateScriptFilename}(chunkId)` + });`, + 'if(!success) throw new Error("Loading update chunk failed for unknown reason");' + ]), + "}", + "", + Template.getFunctionContent( + require('./JavascriptHotModuleReplacement.runtime.js') + ) + .replace(/\$key\$/g, "importScrips") + .replace(/\$installedChunks\$/g, "installedChunks") + .replace(/\$loadUpdateChunk\$/g, "loadUpdateChunk") + .replace(/\$moduleCache\$/g, RuntimeGlobals.moduleCache) + .replace(/\$moduleFactories\$/g, RuntimeGlobals.moduleFactories) + .replace( + /\$ensureChunkHandlers\$/g, + RuntimeGlobals.ensureChunkHandlers + ) + .replace(/\$hasOwnProperty\$/g, RuntimeGlobals.hasOwnProperty) + .replace(/\$hmrModuleData\$/g, RuntimeGlobals.hmrModuleData) + .replace( + /\$hmrDownloadUpdateHandlers\$/g, + RuntimeGlobals.hmrDownloadUpdateHandlers + ) + .replace( + /\$hmrInvalidateModuleHandlers\$/g, + RuntimeGlobals.hmrInvalidateModuleHandlers + ) + ]) + : "// no HMR", + "", + withHmrManifest + ? Template.asString([ + `${ + RuntimeGlobals.hmrDownloadManifest + } = ${runtimeTemplate.basicFunction("", [ + 'if (typeof fetch === "undefined") throw new Error("No browser support: need fetch API");', + `return fetch(${RuntimeGlobals.publicPath} + ${ + RuntimeGlobals.getUpdateManifestFilename + }()).then(${runtimeTemplate.basicFunction("response", [ + "if(response.status === 404) return; // no update available", + 'if(!response.ok) throw new Error("Failed to fetch update manifest " + response.statusText);', + "return response.json();" + ])});` + ])};` + ]) + : "// no HMR manifest" + ]); } -}; +} + +module.exports = ImportScriptsChunkLoadingRuntimeModule; /***/ }), -/***/ 50098: -/***/ (function(module) { +/***/ 9460: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; /* @@ -136688,54 +136510,29 @@ module.exports = class JoinRequestPlugin { -/** @typedef {import("./Resolver")} Resolver */ +const ArrayPushCallbackChunkFormatPlugin = __webpack_require__(86189); +const EnableChunkLoadingPlugin = __webpack_require__(34726); -module.exports = class LogInfoPlugin { - constructor(source) { - this.source = source; - } +/** @typedef {import("../Compiler")} Compiler */ +class WebWorkerTemplatePlugin { /** - * @param {Resolver} resolver the resolver + * Apply the plugin + * @param {Compiler} compiler the compiler instance * @returns {void} */ - apply(resolver) { - const source = this.source; - resolver - .getHook(this.source) - .tapAsync("LogInfoPlugin", (request, resolveContext, callback) => { - if (!resolveContext.log) return callback(); - const log = resolveContext.log; - const prefix = "[" + source + "] "; - if (request.path) - log(prefix + "Resolving in directory: " + request.path); - if (request.request) - log(prefix + "Resolving request: " + request.request); - if (request.module) log(prefix + "Request is an module request."); - if (request.directory) log(prefix + "Request is a directory request."); - if (request.query) - log(prefix + "Resolving request query: " + request.query); - if (request.fragment) - log(prefix + "Resolving request fragment: " + request.fragment); - if (request.descriptionFilePath) - log( - prefix + "Has description data from " + request.descriptionFilePath - ); - if (request.relativePath) - log( - prefix + - "Relative path from description file is: " + - request.relativePath - ); - callback(); - }); + apply(compiler) { + compiler.options.output.chunkLoading = "import-scripts"; + new ArrayPushCallbackChunkFormatPlugin().apply(compiler); + new EnableChunkLoadingPlugin("import-scripts").apply(compiler); } -}; +} +module.exports = WebWorkerTemplatePlugin; /***/ }), -/***/ 18425: +/***/ 94469: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; @@ -136746,24 +136543,22 @@ module.exports = class LogInfoPlugin { -const path = __webpack_require__(85622); const DescriptionFileUtils = __webpack_require__(18641); +const getInnerRequest = __webpack_require__(98361); /** @typedef {import("./Resolver")} Resolver */ +/** @typedef {import("./Resolver").ResolveRequest} ResolveRequest */ /** @typedef {import("./Resolver").ResolveStepHook} ResolveStepHook */ -/** @typedef {{name: string|Array, forceRelative: boolean}} MainFieldOptions */ - -const alreadyTriedMainField = Symbol("alreadyTriedMainField"); -module.exports = class MainFieldPlugin { +module.exports = class AliasFieldPlugin { /** * @param {string | ResolveStepHook} source source - * @param {MainFieldOptions} options options + * @param {string | Array} field field * @param {string | ResolveStepHook} target target */ - constructor(source, options, target) { + constructor(source, field, target) { this.source = source; - this.options = options; + this.field = field; this.target = target; } @@ -136775,47 +136570,60 @@ module.exports = class MainFieldPlugin { const target = resolver.ensureHook(this.target); resolver .getHook(this.source) - .tapAsync("MainFieldPlugin", (request, resolveContext, callback) => { - if ( - request.path !== request.descriptionFileRoot || - request[alreadyTriedMainField] === request.descriptionFilePath || - !request.descriptionFilePath - ) - return callback(); - const filename = path.basename(request.descriptionFilePath); - let mainModule = DescriptionFileUtils.getField( + .tapAsync("AliasFieldPlugin", (request, resolveContext, callback) => { + if (!request.descriptionFileData) return callback(); + const innerRequest = getInnerRequest(resolver, request); + if (!innerRequest) return callback(); + const fieldData = DescriptionFileUtils.getField( request.descriptionFileData, - this.options.name + this.field ); - - if ( - !mainModule || - typeof mainModule !== "string" || - mainModule === "." || - mainModule === "./" - ) { + if (fieldData === null || typeof fieldData !== "object") { + if (resolveContext.log) + resolveContext.log( + "Field '" + + this.field + + "' doesn't contain a valid alias configuration" + ); return callback(); } - if (this.options.forceRelative && !/^\.\.?\//.test(mainModule)) - mainModule = "./" + mainModule; + const data1 = fieldData[innerRequest]; + const data2 = fieldData[innerRequest.replace(/^\.\//, "")]; + const data = typeof data1 !== "undefined" ? data1 : data2; + if (data === innerRequest) return callback(); + if (data === undefined) return callback(); + if (data === false) { + /** @type {ResolveRequest} */ + const ignoreObj = { + ...request, + path: false + }; + return callback(null, ignoreObj); + } const obj = { ...request, - request: mainModule, - module: false, - directory: mainModule.endsWith("/"), - [alreadyTriedMainField]: request.descriptionFilePath + path: request.descriptionFileRoot, + request: data, + fullySpecified: false }; - return resolver.doResolve( + resolver.doResolve( target, obj, - "use " + - mainModule + - " from " + - this.options.name + - " in " + - filename, + "aliased from description file " + + request.descriptionFilePath + + " with mapping '" + + innerRequest + + "' to '" + + data + + "'", resolveContext, - callback + (err, result) => { + if (err) return callback(err); + + // Don't allow other aliasing or raw request + if (result === undefined) return callback(null, null); + callback(null, result); + } ); }); } @@ -136824,7 +136632,7 @@ module.exports = class MainFieldPlugin { /***/ }), -/***/ 44964: +/***/ 42673: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; @@ -136836,20 +136644,20 @@ module.exports = class MainFieldPlugin { const forEachBail = __webpack_require__(55426); -const getPaths = __webpack_require__(17117); /** @typedef {import("./Resolver")} Resolver */ /** @typedef {import("./Resolver").ResolveStepHook} ResolveStepHook */ +/** @typedef {{alias: string|Array|false, name: string, onlyModule?: boolean}} AliasOption */ -module.exports = class ModulesInHierachicDirectoriesPlugin { +module.exports = class AliasPlugin { /** * @param {string | ResolveStepHook} source source - * @param {string | Array} directories directories + * @param {AliasOption | Array} options options * @param {string | ResolveStepHook} target target */ - constructor(source, directories, target) { + constructor(source, options, target) { this.source = source; - this.directories = /** @type {Array} */ ([]).concat(directories); + this.options = Array.isArray(options) ? options : [options]; this.target = target; } @@ -136861,58 +136669,87 @@ module.exports = class ModulesInHierachicDirectoriesPlugin { const target = resolver.ensureHook(this.target); resolver .getHook(this.source) - .tapAsync( - "ModulesInHierachicDirectoriesPlugin", - (request, resolveContext, callback) => { - const fs = resolver.fileSystem; - const addrs = getPaths(request.path) - .paths.map(p => { - return this.directories.map(d => resolver.join(p, d)); - }) - .reduce((array, p) => { - array.push.apply(array, p); - return array; - }, []); - forEachBail( - addrs, - (addr, callback) => { - fs.stat(addr, (err, stat) => { - if (!err && stat && stat.isDirectory()) { + .tapAsync("AliasPlugin", (request, resolveContext, callback) => { + const innerRequest = request.request || request.path; + if (!innerRequest) return callback(); + forEachBail( + this.options, + (item, callback) => { + let shouldStop = false; + if ( + innerRequest === item.name || + (!item.onlyModule && innerRequest.startsWith(item.name + "/")) + ) { + const remainingRequest = innerRequest.substr(item.name.length); + const resolveWithAlias = (alias, callback) => { + if (alias === false) { + const ignoreObj = { + ...request, + path: false + }; + return callback(null, ignoreObj); + } + if ( + innerRequest !== alias && + !innerRequest.startsWith(alias + "/") + ) { + shouldStop = true; + const newRequestStr = alias + remainingRequest; const obj = { ...request, - path: addr, - request: "./" + request.request, - module: false + request: newRequestStr, + fullySpecified: false }; - const message = "looking for modules in " + addr; return resolver.doResolve( target, obj, - message, + "aliased with mapping '" + + item.name + + "': '" + + alias + + "' to '" + + newRequestStr + + "'", resolveContext, - callback + (err, result) => { + if (err) return callback(err); + if (result) return callback(null, result); + return callback(); + } ); } - if (resolveContext.log) - resolveContext.log( - addr + " doesn't exist or is not a directory" - ); - if (resolveContext.missingDependencies) - resolveContext.missingDependencies.add(addr); return callback(); - }); - }, - callback - ); - } - ); + }; + const stoppingCallback = (err, result) => { + if (err) return callback(err); + + if (result) return callback(null, result); + // Don't allow other aliasing or raw request + if (shouldStop) return callback(null, null); + return callback(); + }; + if (Array.isArray(item.alias)) { + return forEachBail( + item.alias, + resolveWithAlias, + stoppingCallback + ); + } else { + return resolveWithAlias(item.alias, stoppingCallback); + } + } + return callback(); + }, + callback + ); + }); } }; /***/ }), -/***/ 39803: +/***/ 72405: /***/ (function(module) { "use strict"; @@ -136926,15 +136763,15 @@ module.exports = class ModulesInHierachicDirectoriesPlugin { /** @typedef {import("./Resolver")} Resolver */ /** @typedef {import("./Resolver").ResolveStepHook} ResolveStepHook */ -module.exports = class ModulesInRootPlugin { +module.exports = class AppendPlugin { /** * @param {string | ResolveStepHook} source source - * @param {string} path path + * @param {string} appending appending * @param {string | ResolveStepHook} target target */ - constructor(source, path, target) { + constructor(source, appending, target) { this.source = source; - this.path = path; + this.appending = appending; this.target = target; } @@ -136946,17 +136783,17 @@ module.exports = class ModulesInRootPlugin { const target = resolver.ensureHook(this.target); resolver .getHook(this.source) - .tapAsync("ModulesInRootPlugin", (request, resolveContext, callback) => { + .tapAsync("AppendPlugin", (request, resolveContext, callback) => { const obj = { ...request, - path: this.path, - request: "./" + request.request, - module: false + path: request.path + this.appending, + relativePath: + request.relativePath && request.relativePath + this.appending }; resolver.doResolve( target, obj, - "looking for modules in " + this.path, + this.appending, resolveContext, callback ); @@ -136967,8 +136804,8 @@ module.exports = class ModulesInRootPlugin { /***/ }), -/***/ 76354: -/***/ (function(module) { +/***/ 26785: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; /* @@ -136978,145 +136815,738 @@ module.exports = class ModulesInRootPlugin { -/** @typedef {import("./Resolver")} Resolver */ -/** @typedef {import("./Resolver").ResolveStepHook} ResolveStepHook */ +const nextTick = __webpack_require__(61765).nextTick; -module.exports = class NextPlugin { +/** @typedef {import("./Resolver").FileSystem} FileSystem */ +/** @typedef {import("./Resolver").SyncFileSystem} SyncFileSystem */ + +const dirname = path => { + let idx = path.length - 1; + while (idx >= 0) { + const c = path.charCodeAt(idx); + // slash or backslash + if (c === 47 || c === 92) break; + idx--; + } + if (idx < 0) return ""; + return path.slice(0, idx); +}; + +const runCallbacks = (callbacks, err, result) => { + if (callbacks.length === 1) { + callbacks[0](err, result); + callbacks.length = 0; + return; + } + let error; + for (const callback of callbacks) { + try { + callback(err, result); + } catch (e) { + if (!error) error = e; + } + } + callbacks.length = 0; + if (error) throw error; +}; + +class OperationMergerBackend { /** - * @param {string | ResolveStepHook} source source - * @param {string | ResolveStepHook} target target + * @param {any} provider async method + * @param {any} syncProvider sync method + * @param {any} providerContext call context for the provider methods */ - constructor(source, target) { - this.source = source; - this.target = target; + constructor(provider, syncProvider, providerContext) { + const activeAsyncOperations = new Map(); + + this.provide = provider + ? (path, options, callback) => { + if (typeof options === "function") { + callback = options; + options = undefined; + } + if (options) { + return provider.call(providerContext, path, options, callback); + } + if (typeof path !== "string") { + callback(new TypeError("path must be a string")); + return; + } + let callbacks = activeAsyncOperations.get(path); + if (callbacks) { + callbacks.push(callback); + return; + } + activeAsyncOperations.set(path, (callbacks = [callback])); + provider.call(providerContext, path, (err, result) => { + activeAsyncOperations.delete(path); + runCallbacks(callbacks, err, result); + }); + } + : null; + this.provideSync = syncProvider + ? (path, options) => { + return syncProvider.call(providerContext, path, options); + } + : null; + + this.provideCustom = provider + ? (provider, providerContext, path, callback) => { + let callbacks = activeAsyncOperations.get(path); + if (callbacks) { + callbacks.push(callback); + return; + } + activeAsyncOperations.set(path, (callbacks = [callback])); + provider.call(providerContext, path, (err, result) => { + activeAsyncOperations.delete(path); + runCallbacks(callbacks, err, result); + }); + } + : null; + this.provideCustomSync = syncProvider + ? (syncProvider, providerContext, path) => { + return syncProvider.call(providerContext, path); + } + : null; } + purge() {} + purgeParent() {} +} + +/* + +IDLE: + insert data: goto SYNC + +SYNC: + before provide: run ticks + event loop tick: goto ASYNC_ACTIVE + +ASYNC: + timeout: run tick, goto ASYNC_PASSIVE + +ASYNC_PASSIVE: + before provide: run ticks + +IDLE --[insert data]--> SYNC --[event loop tick]--> ASYNC_ACTIVE --[interval tick]-> ASYNC_PASSIVE + ^ | + +---------[insert data]-------+ +*/ + +const STORAGE_MODE_IDLE = 0; +const STORAGE_MODE_SYNC = 1; +const STORAGE_MODE_ASYNC = 2; + +class CacheBackend { /** - * @param {Resolver} resolver the resolver - * @returns {void} + * @param {number} duration max cache duration of items + * @param {any} provider async method + * @param {any} syncProvider sync method + * @param {any} providerContext call context for the provider methods */ - apply(resolver) { - const target = resolver.ensureHook(this.target); - resolver - .getHook(this.source) - .tapAsync("NextPlugin", (request, resolveContext, callback) => { - resolver.doResolve(target, request, null, resolveContext, callback); - }); + constructor(duration, provider, syncProvider, providerContext) { + this._duration = duration; + this._provider = provider; + this._syncProvider = syncProvider; + this._providerContext = providerContext; + /** @type {Map} */ + this._activeAsyncOperations = new Map(); + /** @type {Map }>} */ + this._data = new Map(); + /** @type {Set[]} */ + this._levels = []; + for (let i = 0; i < 10; i++) this._levels.push(new Set()); + for (let i = 5000; i < duration; i += 500) this._levels.push(new Set()); + this._currentLevel = 0; + this._tickInterval = Math.floor(duration / this._levels.length); + /** @type {STORAGE_MODE_IDLE | STORAGE_MODE_SYNC | STORAGE_MODE_ASYNC} */ + this._mode = STORAGE_MODE_IDLE; + + /** @type {NodeJS.Timeout | undefined} */ + this._timeout = undefined; + /** @type {number | undefined} */ + this._nextDecay = undefined; + + this.provide = provider ? this.provide.bind(this) : null; + this.provideSync = syncProvider ? this.provideSync.bind(this) : null; + + this.provideCustom = provider ? this.provideCustom.bind(this) : null; + this.provideCustomSync = syncProvider + ? this.provideCustomSync.bind(this) + : null; } -}; + provide(path, options, callback) { + if (typeof options === "function") { + callback = options; + options = undefined; + } + if (typeof path !== "string") { + callback(new TypeError("path must be a string")); + return; + } + if (options) { + return this._provider.call( + this._providerContext, + path, + options, + callback + ); + } + + // When in sync mode we can move to async mode + if (this._mode === STORAGE_MODE_SYNC) { + this._enterAsyncMode(); + } + + // Check in cache + let cacheEntry = this._data.get(path); + if (cacheEntry !== undefined) { + if (cacheEntry.err) return nextTick(callback, cacheEntry.err); + return nextTick(callback, null, cacheEntry.result); + } -/***/ }), + // Check if there is already the same operation running + let callbacks = this._activeAsyncOperations.get(path); + if (callbacks !== undefined) { + callbacks.push(callback); + return; + } + this._activeAsyncOperations.set(path, (callbacks = [callback])); + + // Run the operation + this._provider.call(this._providerContext, path, (err, result) => { + this._activeAsyncOperations.delete(path); + this._storeResult(path, err, result); + + // Enter async mode if not yet done + this._enterAsyncMode(); + + runCallbacks(callbacks, err, result); + }); + } + + provideSync(path, options) { + if (typeof path !== "string") { + throw new TypeError("path must be a string"); + } + if (options) { + return this._syncProvider.call(this._providerContext, path, options); + } + + // In sync mode we may have to decay some cache items + if (this._mode === STORAGE_MODE_SYNC) { + this._runDecays(); + } + + // Check in cache + let cacheEntry = this._data.get(path); + if (cacheEntry !== undefined) { + if (cacheEntry.err) throw cacheEntry.err; + return cacheEntry.result; + } + + // Get all active async operations + // This sync operation will also complete them + const callbacks = this._activeAsyncOperations.get(path); + this._activeAsyncOperations.delete(path); + + // Run the operation + // When in idle mode, we will enter sync mode + let result; + try { + result = this._syncProvider.call(this._providerContext, path); + } catch (err) { + this._storeResult(path, err, undefined); + this._enterSyncModeWhenIdle(); + if (callbacks) runCallbacks(callbacks, err, undefined); + throw err; + } + this._storeResult(path, undefined, result); + this._enterSyncModeWhenIdle(); + if (callbacks) runCallbacks(callbacks, undefined, result); + return result; + } + + provideCustom(provider, providerContext, path, callback) { + // When in sync mode we can move to async mode + if (this._mode === STORAGE_MODE_SYNC) { + this._enterAsyncMode(); + } + + // Check in cache + let cacheEntry = this._data.get(path); + if (cacheEntry !== undefined) { + if (cacheEntry.err) return nextTick(callback, cacheEntry.err); + return nextTick(callback, null, cacheEntry.result); + } + + // Check if there is already the same operation running + let callbacks = this._activeAsyncOperations.get(path); + if (callbacks !== undefined) { + callbacks.push(callback); + return; + } + this._activeAsyncOperations.set(path, (callbacks = [callback])); + + // Run the operation + provider.call(providerContext, path, (err, result) => { + this._activeAsyncOperations.delete(path); + this._storeResult(path, err, result); + + // Enter async mode if not yet done + this._enterAsyncMode(); + + runCallbacks(callbacks, err, result); + }); + } + + provideCustomSync(provider, providerContext, path) { + // In sync mode we may have to decay some cache items + if (this._mode === STORAGE_MODE_SYNC) { + this._runDecays(); + } + + // Check in cache + let cacheEntry = this._data.get(path); + if (cacheEntry !== undefined) { + if (cacheEntry.err) throw cacheEntry.err; + return cacheEntry.result; + } + + // Get all active async operations + // This sync operation will also complete them + const callbacks = this._activeAsyncOperations.get(path); + this._activeAsyncOperations.delete(path); + + // Run the operation + // When in idle mode, we will enter sync mode + let result; + try { + result = provider.call(providerContext, path); + } catch (err) { + this._storeResult(path, err, undefined); + this._enterSyncModeWhenIdle(); + if (callbacks) runCallbacks(callbacks, err, undefined); + throw err; + } + this._storeResult(path, undefined, result); + this._enterSyncModeWhenIdle(); + if (callbacks) runCallbacks(callbacks, undefined, result); + return result; + } + + purge(what) { + if (!what) { + if (this._mode !== STORAGE_MODE_IDLE) { + this._data.clear(); + for (const level of this._levels) { + level.clear(); + } + this._enterIdleMode(); + } + } else if (typeof what === "string") { + for (let [key, data] of this._data) { + if (key.startsWith(what)) { + this._data.delete(key); + data.level.delete(key); + } + } + if (this._data.size === 0) { + this._enterIdleMode(); + } + } else { + for (let [key, data] of this._data) { + for (const item of what) { + if (key.startsWith(item)) { + this._data.delete(key); + data.level.delete(key); + break; + } + } + } + if (this._data.size === 0) { + this._enterIdleMode(); + } + } + } + + purgeParent(what) { + if (!what) { + this.purge(); + } else if (typeof what === "string") { + this.purge(dirname(what)); + } else { + const set = new Set(); + for (const item of what) { + set.add(dirname(item)); + } + this.purge(set); + } + } + + _storeResult(path, err, result) { + if (this._data.has(path)) return; + const level = this._levels[this._currentLevel]; + this._data.set(path, { err, result, level }); + level.add(path); + } + + _decayLevel() { + const nextLevel = (this._currentLevel + 1) % this._levels.length; + const decay = this._levels[nextLevel]; + this._currentLevel = nextLevel; + for (let item of decay) { + this._data.delete(item); + } + decay.clear(); + if (this._data.size === 0) { + this._enterIdleMode(); + } else { + // @ts-ignore _nextDecay is always a number in sync mode + this._nextDecay += this._tickInterval; + } + } + + _runDecays() { + while ( + /** @type {number} */ (this._nextDecay) <= Date.now() && + this._mode !== STORAGE_MODE_IDLE + ) { + this._decayLevel(); + } + } + + _enterAsyncMode() { + let timeout = 0; + switch (this._mode) { + case STORAGE_MODE_ASYNC: + return; + case STORAGE_MODE_IDLE: + this._nextDecay = Date.now() + this._tickInterval; + timeout = this._tickInterval; + break; + case STORAGE_MODE_SYNC: + this._runDecays(); + // @ts-ignore _runDecays may change the mode + if (this._mode === STORAGE_MODE_IDLE) return; + timeout = Math.max( + 0, + /** @type {number} */ (this._nextDecay) - Date.now() + ); + break; + } + this._mode = STORAGE_MODE_ASYNC; + const ref = setTimeout(() => { + this._mode = STORAGE_MODE_SYNC; + this._runDecays(); + }, timeout); + if (ref.unref) ref.unref(); + this._timeout = ref; + } + + _enterSyncModeWhenIdle() { + if (this._mode === STORAGE_MODE_IDLE) { + this._mode = STORAGE_MODE_SYNC; + this._nextDecay = Date.now() + this._tickInterval; + } + } + + _enterIdleMode() { + this._mode = STORAGE_MODE_IDLE; + this._nextDecay = undefined; + if (this._timeout) clearTimeout(this._timeout); + } +} + +const createBackend = (duration, provider, syncProvider, providerContext) => { + if (duration > 0) { + return new CacheBackend(duration, provider, syncProvider, providerContext); + } + return new OperationMergerBackend(provider, syncProvider, providerContext); +}; + +module.exports = class CachedInputFileSystem { + constructor(fileSystem, duration) { + this.fileSystem = fileSystem; -/***/ 95204: -/***/ (function(module) { + this._lstatBackend = createBackend( + duration, + this.fileSystem.lstat, + this.fileSystem.lstatSync, + this.fileSystem + ); + const lstat = this._lstatBackend.provide; + this.lstat = /** @type {FileSystem["lstat"]} */ (lstat); + const lstatSync = this._lstatBackend.provideSync; + this.lstatSync = /** @type {SyncFileSystem["lstatSync"]} */ (lstatSync); -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ + this._statBackend = createBackend( + duration, + this.fileSystem.stat, + this.fileSystem.statSync, + this.fileSystem + ); + const stat = this._statBackend.provide; + const customStat = this._statBackend.provideCustom; + this.stat = /** @type {FileSystem["stat"]} */ (stat); + const statSync = this._statBackend.provideSync; + const customStatSync = this._statBackend.provideCustomSync; + this.statSync = /** @type {SyncFileSystem["statSync"]} */ (statSync); + this._readdirBackend = createBackend( + duration, + this.fileSystem.readdir, + this.fileSystem.readdirSync, + this.fileSystem + ); + const readdir = this._readdirBackend.provide; + this.readdir = /** @type {FileSystem["readdir"]} */ (readdir); + const readdirSync = this._readdirBackend.provideSync; + this.readdirSync = /** @type {SyncFileSystem["readdirSync"]} */ (readdirSync); + this._readFileBackend = createBackend( + duration, + this.fileSystem.readFile && + this.fileSystem.fstat && + this.fileSystem.read && + this.fileSystem.open && + this.fileSystem.close && + customStat + ? /** + * @this {{ fstat: NonNullable, readFile: NonNullable, open: NonNullable, read: NonNullable, close: NonNullable }} + */ + function (path, options, callback) { + if (typeof options === "function") { + callback = options; + options = undefined; + } + if (typeof options === "object") + return this.readFile(path, options, callback); + this.open(path, "r", (err, fd) => { + if (err) return callback(err); + if (typeof fd !== "number") + return callback(new Error("fd must be a number")); + customStat( + (path, callback) => this.fstat(fd, callback), + null, + path, + (err, stats) => { + if (err) return callback(err); + if (stats.size > 0 && stats.size < 128 * 1024) { + let remaining = stats.size + 1; + const buffer = Buffer.allocUnsafe(remaining); + const afterRead = (err, bytesRead) => { + if (err) { + return this.close(fd, () => { + callback(err); + }); + } + remaining -= bytesRead; + if (bytesRead === 0 || remaining === 1) { + this.close(fd, err => { + if (err) return callback(err); + return callback( + null, + buffer.slice(0, buffer.length - remaining) + ); + }); + } else if (remaining === 0) { + // The file size has changed from the cached info + // We keep reading until the end is found + let buf = Buffer.allocUnsafe(16 * 1024); + let bufPos = 0; + const buffers = [buffer]; + const afterUnknownRead = (err, bytesRead) => { + if (err) { + return this.close(fd, () => { + callback(err); + }); + } + bufPos += bytesRead; + if (bytesRead === 0) { + if (bufPos > 0) buffers.push(buf.slice(0, bufPos)); + this.close(fd, err => { + if (err) return callback(err); + return callback(null, Buffer.concat(buffers)); + }); + } else { + if (bufPos === buf.length) { + buffers.push(buf); + buf = Buffer.allocUnsafe(16 * 1024); + bufPos = 0; + } + this.read( + fd, + buf, + bufPos, + buf.length - bufPos, + -1, + afterUnknownRead + ); + } + }; + this.read( + fd, + buf, + bufPos, + buf.length - bufPos, + -1, + afterUnknownRead + ); + } else { + this.read( + fd, + buffer, + stats.size - remaining, + remaining + 1, + -1, + afterRead + ); + } + }; + this.read(fd, buffer, 0, remaining, -1, afterRead); + } else { + this.readFile(fd, options, (err, buffer) => { + this.close(fd, closeErr => { + if (err) return callback(err); + if (closeErr) return callback(closeErr); + callback(null, buffer); + }); + }); + } + } + ); + }); + } + : this.fileSystem.readFile, + this.fileSystem.readFileSync && + this.fileSystem.fstatSync && + this.fileSystem.readSync && + this.fileSystem.openSync && + this.fileSystem.closeSync && + customStatSync + ? /** + * @this {{ fstatSync: NonNullable, readFileSync: NonNullable, openSync: NonNullable, readSync: NonNullable, closeSync: NonNullable }} + */ + function (path, options) { + if (typeof options === "object") + return this.readFileSync(path, options); + const fd = this.openSync(path, "r"); + if (typeof fd !== "number") throw new Error("fd must be a number"); + const stats = customStatSync(() => this.fstatSync(fd), null, path); + if (stats.size > 0 && stats.size < 128 * 1024) { + let remaining = stats.size; + const buffer = Buffer.allocUnsafe(remaining); + try { + let bytesRead = this.readSync(fd, buffer, 0, remaining, -1); + remaining -= bytesRead; + while (bytesRead !== 0 && remaining !== 0) { + bytesRead = this.readSync( + fd, + buffer, + stats.size - remaining, + remaining, + -1 + ); + remaining -= bytesRead; + } + return buffer; + } finally { + this.closeSync(fd); + } + } else { + const buffer = this.readFileSync(fd); + this.closeSync(fd); + return buffer; + } + } + : this.fileSystem.readFileSync, + this.fileSystem + ); + const readFile = this._readFileBackend.provide; + this.readFile = /** @type {FileSystem["readFile"]} */ (readFile); + const readFileSync = this._readFileBackend.provideSync; + this.readFileSync = /** @type {SyncFileSystem["readFileSync"]} */ (readFileSync); -/** @typedef {import("./Resolver")} Resolver */ -/** @typedef {import("./Resolver").ResolveRequest} ResolveRequest */ -/** @typedef {import("./Resolver").ResolveStepHook} ResolveStepHook */ + this._readJsonBackend = createBackend( + duration, + this.fileSystem.readJson || + (this.readFile && + ((path, callback) => { + // @ts-ignore + this.readFile(path, (err, buffer) => { + if (err) return callback(err); + if (!buffer || buffer.length === 0) + return callback(new Error("No file content")); + let data; + try { + data = JSON.parse(buffer.toString("utf-8")); + } catch (e) { + return callback(e); + } + callback(null, data); + }); + })), + this.fileSystem.readJsonSync || + (this.readFileSync && + (path => { + const buffer = this.readFileSync(path); + const data = JSON.parse(buffer.toString("utf-8")); + return data; + })), + this.fileSystem + ); + const readJson = this._readJsonBackend.provide; + this.readJson = /** @type {FileSystem["readJson"]} */ (readJson); + const readJsonSync = this._readJsonBackend.provideSync; + this.readJsonSync = /** @type {SyncFileSystem["readJsonSync"]} */ (readJsonSync); -module.exports = class ParsePlugin { - /** - * @param {string | ResolveStepHook} source source - * @param {Partial} requestOptions request options - * @param {string | ResolveStepHook} target target - */ - constructor(source, requestOptions, target) { - this.source = source; - this.requestOptions = requestOptions; - this.target = target; + this._readlinkBackend = createBackend( + duration, + this.fileSystem.readlink, + this.fileSystem.readlinkSync, + this.fileSystem + ); + const readlink = this._readlinkBackend.provide; + this.readlink = /** @type {FileSystem["readlink"]} */ (readlink); + const readlinkSync = this._readlinkBackend.provideSync; + this.readlinkSync = /** @type {SyncFileSystem["readlinkSync"]} */ (readlinkSync); } - /** - * @param {Resolver} resolver the resolver - * @returns {void} - */ - apply(resolver) { - const target = resolver.ensureHook(this.target); - resolver - .getHook(this.source) - .tapAsync("ParsePlugin", (request, resolveContext, callback) => { - const parsed = resolver.parse(/** @type {string} */ (request.request)); - const obj = { ...request, ...parsed, ...this.requestOptions }; - if (request.query && !parsed.query) { - obj.query = request.query; - } - if (request.fragment && !parsed.fragment) { - obj.fragment = request.fragment; - } - if (parsed && resolveContext.log) { - if (parsed.module) resolveContext.log("Parsed request is a module"); - if (parsed.directory) - resolveContext.log("Parsed request is a directory"); - } - // There is an edge-case where a request with # can be a path or a fragment -> try both - if (obj.request && !obj.query && obj.fragment) { - const directory = obj.fragment.endsWith("/"); - const alternative = { - ...obj, - directory, - request: - obj.request + - (obj.directory ? "/" : "") + - (directory ? obj.fragment.slice(0, -1) : obj.fragment), - fragment: "" - }; - resolver.doResolve( - target, - alternative, - null, - resolveContext, - (err, result) => { - if (err) return callback(err); - if (result) return callback(null, result); - resolver.doResolve(target, obj, null, resolveContext, callback); - } - ); - return; - } - resolver.doResolve(target, obj, null, resolveContext, callback); - }); + purge(what) { + this._statBackend.purge(what); + this._lstatBackend.purge(what); + this._readdirBackend.purgeParent(what); + this._readFileBackend.purge(what); + this._readlinkBackend.purge(what); + this._readJsonBackend.purge(what); } }; /***/ }), -/***/ 63321: -/***/ (function(module) { +/***/ 36154: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; /* MIT License http://www.opensource.org/licenses/mit-license.php - Author Maël Nison @arcanis + Author Tobias Koppers @sokra */ +const basename = __webpack_require__(17117).basename; + /** @typedef {import("./Resolver")} Resolver */ -/** @typedef {import("./Resolver").ResolveStepHook} ResolveStepHook */ -/** - * @typedef {Object} PnpApiImpl - * @property {function(string, string, object): string} resolveToUnqualified - */ -module.exports = class PnpPlugin { - /** - * @param {string | ResolveStepHook} source source - * @param {PnpApiImpl} pnpApi pnpApi - * @param {string | ResolveStepHook} target target - */ - constructor(source, pnpApi, target) { +module.exports = class CloneBasenamePlugin { + constructor(source, target) { this.source = source; - this.pnpApi = pnpApi; this.target = target; } @@ -137128,1237 +137558,859 @@ module.exports = class PnpPlugin { const target = resolver.ensureHook(this.target); resolver .getHook(this.source) - .tapAsync("PnpPlugin", (request, resolveContext, callback) => { - const req = request.request; - if (!req) return callback(); - - // The trailing slash indicates to PnP that this value is a folder rather than a file - const issuer = `${request.path}/`; - - const packageMatch = /^(@[^/]+\/)?[^/]+/.exec(req); - if (!packageMatch) return callback(); - - const packageName = packageMatch[0]; - const innerRequest = `.${req.slice(packageName.length)}`; - - let resolution; - let apiResolution; - try { - resolution = this.pnpApi.resolveToUnqualified(packageName, issuer, { - considerBuiltins: false - }); - if (resolveContext.fileDependencies) { - apiResolution = this.pnpApi.resolveToUnqualified("pnpapi", issuer, { - considerBuiltins: false - }); - } - } catch (error) { - if ( - error.code === "MODULE_NOT_FOUND" && - error.pnpCode === "UNDECLARED_DEPENDENCY" - ) { - // This is not a PnP managed dependency. - // Try to continue resolving with our alternatives - if (resolveContext.log) { - resolveContext.log(`request is not managed by the pnpapi`); - for (const line of error.message.split("\n").filter(Boolean)) - resolveContext.log(` ${line}`); - } - return callback(); - } - return callback(error); - } - - if (resolution === packageName) return callback(); - - if (apiResolution && resolveContext.fileDependencies) { - resolveContext.fileDependencies.add(apiResolution); - } - + .tapAsync("CloneBasenamePlugin", (request, resolveContext, callback) => { + const filename = basename(request.path); + const filePath = resolver.join(request.path, filename); const obj = { ...request, - path: resolution, - request: innerRequest, - ignoreSymlinks: true, - fullySpecified: request.fullySpecified && innerRequest !== "." + path: filePath, + relativePath: + request.relativePath && + resolver.join(request.relativePath, filename) }; resolver.doResolve( target, obj, - `resolved by pnp to ${resolution}`, + "using path: " + filePath, resolveContext, - (err, result) => { - if (err) return callback(err); - if (result) return callback(null, result); - // Skip alternatives - return callback(null, null); - } - ); - }); - } -}; - - -/***/ }), - -/***/ 7675: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ - - - -const { AsyncSeriesBailHook, AsyncSeriesHook, SyncHook } = __webpack_require__(34718); -const createInnerContext = __webpack_require__(710); -const { parseIdentifier } = __webpack_require__(98623); -const { - normalize, - cachedJoin: join, - getType, - PathType -} = __webpack_require__(69821); - -/** @typedef {import("./ResolverFactory").ResolveOptions} ResolveOptions */ - -/** - * @typedef {Object} FileSystemStats - * @property {function(): boolean} isDirectory - * @property {function(): boolean} isFile - */ - -/** - * @typedef {Object} FileSystemDirent - * @property {Buffer | string} name - * @property {function(): boolean} isDirectory - * @property {function(): boolean} isFile - */ - -/** - * @typedef {Object} PossibleFileSystemError - * @property {string=} code - * @property {number=} errno - * @property {string=} path - * @property {string=} syscall - */ - -/** - * @template T - * @callback FileSystemCallback - * @param {PossibleFileSystemError & Error | null | undefined} err - * @param {T=} result - */ - -/** - * @typedef {Object} FileSystem - * @property {(function(string | number, FileSystemCallback): void) & function(string | number, object, FileSystemCallback): void} readFile - * @property {(function(string, string | number, FileSystemCallback): void) & function(string, string | number, string | number, FileSystemCallback): void=} open - * @property {(function(number, FileSystemCallback): void) & function(number, object, FileSystemCallback): void=} fstat - * @property {function(number, Buffer | Uint8Array, number, number, number, function(PossibleFileSystemError & Error | null | undefined, number=): void): void=} read - * @property {function(number, function(PossibleFileSystemError & Error | null | undefined): void): void=} close - * @property {(function(string, FileSystemCallback<(Buffer | string)[] | FileSystemDirent[]>): void) & function(string, object, FileSystemCallback<(Buffer | string)[] | FileSystemDirent[]>): void} readdir - * @property {((function(string, FileSystemCallback): void) & function(string, object, FileSystemCallback): void)=} readJson - * @property {(function(string, FileSystemCallback): void) & function(string, object, FileSystemCallback): void} readlink - * @property {(function(string, FileSystemCallback): void) & function(string, object, FileSystemCallback): void=} lstat - * @property {(function(string, FileSystemCallback): void) & function(string, object, FileSystemCallback): void} stat - */ - -/** - * @typedef {Object} SyncFileSystem - * @property {function(string | number, object=): Buffer | string} readFileSync - * @property {function(string, string | number, string | number=): number=} openSync - * @property {function(number, object=): FileSystemStats=} fstatSync - * @property {function(number, Buffer | Uint8Array, number, number, number): number=} readSync - * @property {function(number): void=} closeSync - * @property {function(string, object=): (Buffer | string)[] | FileSystemDirent[]} readdirSync - * @property {(function(string, object=): object)=} readJsonSync - * @property {function(string, object=): Buffer | string} readlinkSync - * @property {function(string, object=): FileSystemStats=} lstatSync - * @property {function(string, object=): FileSystemStats} statSync - */ - -/** - * @typedef {Object} ParsedIdentifier - * @property {string} request - * @property {string} query - * @property {string} fragment - * @property {boolean} directory - * @property {boolean} module - * @property {boolean} file - * @property {boolean} internal - */ - -/** - * @typedef {Object} BaseResolveRequest - * @property {string | false} path - * @property {string=} descriptionFilePath - * @property {string=} descriptionFileRoot - * @property {object=} descriptionFileData - * @property {string=} relativePath - * @property {boolean=} ignoreSymlinks - * @property {boolean=} fullySpecified - */ + callback + ); + }); + } +}; -/** @typedef {BaseResolveRequest & Partial} ResolveRequest */ -/** - * String with special formatting - * @typedef {string} StackEntry - */ +/***/ }), -/** @template T @typedef {{ add: (T) => void }} WriteOnlySet */ +/***/ 13134: +/***/ (function(module) { -/** - * Resolve context - * @typedef {Object} ResolveContext - * @property {WriteOnlySet=} contextDependencies - * @property {WriteOnlySet=} fileDependencies files that was found on file system - * @property {WriteOnlySet=} missingDependencies dependencies that was not found on file system - * @property {Set=} stack set of hooks' calls. For instance, `resolve → parsedResolve → describedResolve`, - * @property {(function(string): void)=} log log function - */ +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ -/** @typedef {AsyncSeriesBailHook<[ResolveRequest, ResolveContext], ResolveRequest | null>} ResolveStepHook */ -/** - * @param {string} str input string - * @returns {string} in camel case - */ -function toCamelCase(str) { - return str.replace(/-([a-z])/g, str => str.substr(1).toUpperCase()); -} -class Resolver { - /** - * @param {ResolveStepHook} hook hook - * @param {ResolveRequest} request request - * @returns {StackEntry} stack entry - */ - static createStackEntry(hook, request) { - return ( - hook.name + - ": (" + - request.path + - ") " + - (request.request || "") + - (request.query || "") + - (request.fragment || "") + - (request.directory ? " directory" : "") + - (request.module ? " module" : "") - ); - } +/** @typedef {import("./Resolver")} Resolver */ +/** @typedef {import("./Resolver").ResolveRequest} ResolveRequest */ +/** @typedef {import("./Resolver").ResolveStepHook} ResolveStepHook */ +module.exports = class ConditionalPlugin { /** - * @param {FileSystem} fileSystem a filesystem - * @param {ResolveOptions} options options + * @param {string | ResolveStepHook} source source + * @param {Partial} test compare object + * @param {string | null} message log message + * @param {boolean} allowAlternatives when false, do not continue with the current step when "test" matches + * @param {string | ResolveStepHook} target target */ - constructor(fileSystem, options) { - this.fileSystem = fileSystem; - this.options = options; - this.hooks = { - /** @type {SyncHook<[ResolveStepHook, ResolveRequest], void>} */ - resolveStep: new SyncHook(["hook", "request"], "resolveStep"), - /** @type {SyncHook<[ResolveRequest, Error]>} */ - noResolve: new SyncHook(["request", "error"], "noResolve"), - /** @type {ResolveStepHook} */ - resolve: new AsyncSeriesBailHook( - ["request", "resolveContext"], - "resolve" - ), - /** @type {AsyncSeriesHook<[ResolveRequest, ResolveContext]>} */ - result: new AsyncSeriesHook(["result", "resolveContext"], "result") - }; + constructor(source, test, message, allowAlternatives, target) { + this.source = source; + this.test = test; + this.message = message; + this.allowAlternatives = allowAlternatives; + this.target = target; } /** - * @param {string | ResolveStepHook} name hook name or hook itself - * @returns {ResolveStepHook} the hook + * @param {Resolver} resolver the resolver + * @returns {void} */ - ensureHook(name) { - if (typeof name !== "string") { - return name; - } - name = toCamelCase(name); - if (/^before/.test(name)) { - return /** @type {ResolveStepHook} */ (this.ensureHook( - name[6].toLowerCase() + name.substr(7) - ).withOptions({ - stage: -10 - })); - } - if (/^after/.test(name)) { - return /** @type {ResolveStepHook} */ (this.ensureHook( - name[5].toLowerCase() + name.substr(6) - ).withOptions({ - stage: 10 - })); - } - const hook = this.hooks[name]; - if (!hook) { - return (this.hooks[name] = new AsyncSeriesBailHook( - ["request", "resolveContext"], - name - )); - } - return hook; - } + apply(resolver) { + const target = resolver.ensureHook(this.target); + const { test, message, allowAlternatives } = this; + const keys = Object.keys(test); + resolver + .getHook(this.source) + .tapAsync("ConditionalPlugin", (request, resolveContext, callback) => { + for (const prop of keys) { + if (request[prop] !== test[prop]) return callback(); + } + resolver.doResolve( + target, + request, + message, + resolveContext, + allowAlternatives + ? callback + : (err, result) => { + if (err) return callback(err); - /** - * @param {string | ResolveStepHook} name hook name or hook itself - * @returns {ResolveStepHook} the hook - */ - getHook(name) { - if (typeof name !== "string") { - return name; - } - name = toCamelCase(name); - if (/^before/.test(name)) { - return /** @type {ResolveStepHook} */ (this.getHook( - name[6].toLowerCase() + name.substr(7) - ).withOptions({ - stage: -10 - })); - } - if (/^after/.test(name)) { - return /** @type {ResolveStepHook} */ (this.getHook( - name[5].toLowerCase() + name.substr(6) - ).withOptions({ - stage: 10 - })); - } - const hook = this.hooks[name]; - if (!hook) { - throw new Error(`Hook ${name} doesn't exist`); - } - return hook; + // Don't allow other alternatives + if (result === undefined) return callback(null, null); + callback(null, result); + } + ); + }); } +}; + + +/***/ }), + +/***/ 85774: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ + + + +const DescriptionFileUtils = __webpack_require__(18641); + +/** @typedef {import("./Resolver")} Resolver */ +/** @typedef {import("./Resolver").ResolveStepHook} ResolveStepHook */ +module.exports = class DescriptionFilePlugin { /** - * @param {object} context context information object - * @param {string} path context path - * @param {string} request request string - * @returns {string | false} result + * @param {string | ResolveStepHook} source source + * @param {string[]} filenames filenames + * @param {boolean} pathIsFile pathIsFile + * @param {string | ResolveStepHook} target target */ - resolveSync(context, path, request) { - /** @type {Error | null | undefined} */ - let err = undefined; - /** @type {string | false | undefined} */ - let result = undefined; - let sync = false; - this.resolve(context, path, request, {}, (e, r) => { - err = e; - result = r; - sync = true; - }); - if (!sync) { - throw new Error( - "Cannot 'resolveSync' because the fileSystem is not sync. Use 'resolve'!" - ); - } - if (err) throw err; - if (result === undefined) throw new Error("No result"); - return result; + constructor(source, filenames, pathIsFile, target) { + this.source = source; + this.filenames = filenames; + this.pathIsFile = pathIsFile; + this.target = target; } /** - * @param {object} context context information object - * @param {string} path context path - * @param {string} request request string - * @param {ResolveContext} resolveContext resolve context - * @param {function(Error | null, (string|false)=, ResolveRequest=): void} callback callback function + * @param {Resolver} resolver the resolver * @returns {void} */ - resolve(context, path, request, resolveContext, callback) { - if (!context || typeof context !== "object") - return callback(new Error("context argument is not an object")); - if (typeof path !== "string") - return callback(new Error("path argument is not a string")); - if (typeof request !== "string") - return callback(new Error("path argument is not a string")); - if (!resolveContext) - return callback(new Error("resolveContext argument is not set")); + apply(resolver) { + const target = resolver.ensureHook(this.target); + resolver + .getHook(this.source) + .tapAsync( + "DescriptionFilePlugin", + (request, resolveContext, callback) => { + const path = request.path; + if (!path) return callback(); + const directory = this.pathIsFile + ? DescriptionFileUtils.cdUp(path) + : path; + if (!directory) return callback(); + DescriptionFileUtils.loadDescriptionFile( + resolver, + directory, + this.filenames, + request.descriptionFilePath + ? { + path: request.descriptionFilePath, + content: request.descriptionFileData, + directory: /** @type {string} */ (request.descriptionFileRoot) + } + : undefined, + resolveContext, + (err, result) => { + if (err) return callback(err); + if (!result) { + if (resolveContext.log) + resolveContext.log( + `No description file found in ${directory} or above` + ); + return callback(); + } + const relativePath = + "." + path.substr(result.directory.length).replace(/\\/g, "/"); + const obj = { + ...request, + descriptionFilePath: result.path, + descriptionFileData: result.content, + descriptionFileRoot: result.directory, + relativePath: relativePath + }; + resolver.doResolve( + target, + obj, + "using description file: " + + result.path + + " (relative path: " + + relativePath + + ")", + resolveContext, + (err, result) => { + if (err) return callback(err); - const obj = { - context: context, - path: path, - request: request - }; + // Don't allow other processing + if (result === undefined) return callback(null, null); + callback(null, result); + } + ); + } + ); + } + ); + } +}; - const message = `resolve '${request}' in '${path}'`; - const finishResolved = result => { - return callback( - null, - result.path === false - ? false - : `${result.path.replace(/#/g, "\0#")}${ - result.query ? result.query.replace(/#/g, "\0#") : "" - }${result.fragment || ""}`, - result - ); - }; +/***/ }), - const finishWithoutResolve = log => { - /** - * @type {Error & {details?: string}} - */ - const error = new Error("Can't " + message); - error.details = log.join("\n"); - this.hooks.noResolve.call(obj, error); - return callback(error); - }; +/***/ 18641: +/***/ (function(__unused_webpack_module, exports, __webpack_require__) { - if (resolveContext.log) { - // We need log anyway to capture it in case of an error - const parentLog = resolveContext.log; - const log = []; - return this.doResolve( - this.hooks.resolve, - obj, - message, - { - log: msg => { - parentLog(msg); - log.push(msg); - }, - fileDependencies: resolveContext.fileDependencies, - contextDependencies: resolveContext.contextDependencies, - missingDependencies: resolveContext.missingDependencies, - stack: resolveContext.stack - }, - (err, result) => { - if (err) return callback(err); +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ - if (result) return finishResolved(result); - return finishWithoutResolve(log); - } - ); - } else { - // Try to resolve assuming there is no error - // We don't log stuff in this case - return this.doResolve( - this.hooks.resolve, - obj, - message, - { - log: undefined, - fileDependencies: resolveContext.fileDependencies, - contextDependencies: resolveContext.contextDependencies, - missingDependencies: resolveContext.missingDependencies, - stack: resolveContext.stack - }, - (err, result) => { - if (err) return callback(err); - if (result) return finishResolved(result); +const forEachBail = __webpack_require__(55426); - // log is missing for the error details - // so we redo the resolving for the log info - // this is more expensive to the success case - // is assumed by default +/** @typedef {import("./Resolver")} Resolver */ +/** @typedef {import("./Resolver").ResolveContext} ResolveContext */ - const log = []; +/** + * @typedef {Object} DescriptionFileInfo + * @property {any=} content + * @property {string} path + * @property {string} directory + */ - return this.doResolve( - this.hooks.resolve, - obj, - message, - { - log: msg => log.push(msg), - stack: resolveContext.stack - }, - (err, result) => { - if (err) return callback(err); +/** + * @callback ErrorFirstCallback + * @param {Error|null=} error + * @param {DescriptionFileInfo=} result + */ - return finishWithoutResolve(log); - } - ); - } - ); +/** + * @param {Resolver} resolver resolver + * @param {string} directory directory + * @param {string[]} filenames filenames + * @param {DescriptionFileInfo|undefined} oldInfo oldInfo + * @param {ResolveContext} resolveContext resolveContext + * @param {ErrorFirstCallback} callback callback + */ +function loadDescriptionFile( + resolver, + directory, + filenames, + oldInfo, + resolveContext, + callback +) { + (function findDescriptionFile() { + if (oldInfo && oldInfo.directory === directory) { + // We already have info for this directory and can reuse it + return callback(null, oldInfo); } - } + forEachBail( + filenames, + (filename, callback) => { + const descriptionFilePath = resolver.join(directory, filename); + if (resolver.fileSystem.readJson) { + resolver.fileSystem.readJson(descriptionFilePath, (err, content) => { + if (err) { + if (typeof err.code !== "undefined") { + if (resolveContext.missingDependencies) { + resolveContext.missingDependencies.add(descriptionFilePath); + } + return callback(); + } + if (resolveContext.fileDependencies) { + resolveContext.fileDependencies.add(descriptionFilePath); + } + return onJson(err); + } + if (resolveContext.fileDependencies) { + resolveContext.fileDependencies.add(descriptionFilePath); + } + onJson(null, content); + }); + } else { + resolver.fileSystem.readFile(descriptionFilePath, (err, content) => { + if (err) { + if (resolveContext.missingDependencies) { + resolveContext.missingDependencies.add(descriptionFilePath); + } + return callback(); + } + if (resolveContext.fileDependencies) { + resolveContext.fileDependencies.add(descriptionFilePath); + } + let json; - doResolve(hook, request, message, resolveContext, callback) { - const stackEntry = Resolver.createStackEntry(hook, request); + if (content) { + try { + json = JSON.parse(content.toString()); + } catch (e) { + return onJson(e); + } + } else { + return onJson(new Error("No content in file")); + } - let newStack; - if (resolveContext.stack) { - newStack = new Set(resolveContext.stack); - if (resolveContext.stack.has(stackEntry)) { - /** - * Prevent recursion - * @type {Error & {recursion?: boolean}} - */ - const recursionError = new Error( - "Recursion in resolving\nStack:\n " + - Array.from(newStack).join("\n ") - ); - recursionError.recursion = true; - if (resolveContext.log) - resolveContext.log("abort resolving because of recursion"); - return callback(recursionError); + onJson(null, json); + }); + } + + function onJson(err, content) { + if (err) { + if (resolveContext.log) + resolveContext.log( + descriptionFilePath + " (directory description file): " + err + ); + else + err.message = + descriptionFilePath + " (directory description file): " + err; + return callback(err); + } + callback(null, { + content, + directory, + path: descriptionFilePath + }); + } + }, + (err, result) => { + if (err) return callback(err); + if (result) { + return callback(null, result); + } else { + const dir = cdUp(directory); + if (!dir) { + return callback(); + } else { + directory = dir; + return findDescriptionFile(); + } + } } - newStack.add(stackEntry); - } else { - newStack = new Set([stackEntry]); - } - this.hooks.resolveStep.call(hook, request); + ); + })(); +} - if (hook.isUsed()) { - const innerContext = createInnerContext( - { - log: resolveContext.log, - fileDependencies: resolveContext.fileDependencies, - contextDependencies: resolveContext.contextDependencies, - missingDependencies: resolveContext.missingDependencies, - stack: newStack - }, - message - ); - return hook.callAsync(request, innerContext, (err, result) => { - if (err) return callback(err); - if (result) return callback(null, result); - callback(); - }); - } else { - callback(); +/** + * @param {any} content content + * @param {string|string[]} field field + * @returns {object|string|number|boolean|undefined} field data + */ +function getField(content, field) { + if (!content) return undefined; + if (Array.isArray(field)) { + let current = content; + for (let j = 0; j < field.length; j++) { + if (current === null || typeof current !== "object") { + current = null; + break; + } + current = current[field[j]]; } + return current; + } else { + return content[field]; } +} - /** - * @param {string} identifier identifier - * @returns {ParsedIdentifier} parsed identifier - */ - parse(identifier) { - const part = { - request: "", - query: "", - fragment: "", - module: false, - directory: false, - file: false, - internal: false - }; +/** + * @param {string} directory directory + * @returns {string|null} parent directory or null + */ +function cdUp(directory) { + if (directory === "/") return null; + const i = directory.lastIndexOf("/"), + j = directory.lastIndexOf("\\"); + const p = i < 0 ? j : j < 0 ? i : i < j ? j : i; + if (p < 0) return null; + return directory.substr(0, p || 1); +} - const parsedIdentifier = parseIdentifier(identifier); +exports.loadDescriptionFile = loadDescriptionFile; +exports.getField = getField; +exports.cdUp = cdUp; - if (!parsedIdentifier) return part; - [part.request, part.query, part.fragment] = parsedIdentifier; +/***/ }), - if (part.request.length > 0) { - part.internal = this.isPrivate(identifier); - part.module = this.isModule(part.request); - part.directory = this.isDirectory(part.request); - if (part.directory) { - part.request = part.request.substr(0, part.request.length - 1); - } - } +/***/ 61827: +/***/ (function(module) { - return part; - } +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ - isModule(path) { - return getType(path) === PathType.Normal; - } - isPrivate(path) { - return getType(path) === PathType.Internal; - } +/** @typedef {import("./Resolver")} Resolver */ +/** @typedef {import("./Resolver").ResolveStepHook} ResolveStepHook */ + +module.exports = class DirectoryExistsPlugin { /** - * @param {string} path a path - * @returns {boolean} true, if the path is a directory path + * @param {string | ResolveStepHook} source source + * @param {string | ResolveStepHook} target target */ - isDirectory(path) { - return path.endsWith("/"); - } - - join(path, request) { - return join(path, request); + constructor(source, target) { + this.source = source; + this.target = target; } - normalize(path) { - return normalize(path); + /** + * @param {Resolver} resolver the resolver + * @returns {void} + */ + apply(resolver) { + const target = resolver.ensureHook(this.target); + resolver + .getHook(this.source) + .tapAsync( + "DirectoryExistsPlugin", + (request, resolveContext, callback) => { + const fs = resolver.fileSystem; + const directory = request.path; + if (!directory) return callback(); + fs.stat(directory, (err, stat) => { + if (err || !stat) { + if (resolveContext.missingDependencies) + resolveContext.missingDependencies.add(directory); + if (resolveContext.log) + resolveContext.log(directory + " doesn't exist"); + return callback(); + } + if (!stat.isDirectory()) { + if (resolveContext.missingDependencies) + resolveContext.missingDependencies.add(directory); + if (resolveContext.log) + resolveContext.log(directory + " is not a directory"); + return callback(); + } + if (resolveContext.fileDependencies) + resolveContext.fileDependencies.add(directory); + resolver.doResolve( + target, + request, + `existing directory ${directory}`, + resolveContext, + callback + ); + }); + } + ); } -} - -module.exports = Resolver; +}; /***/ }), -/***/ 1453: -/***/ (function(__unused_webpack_module, exports, __webpack_require__) { +/***/ 98169: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; /* MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra + Author Ivan Kopeykin @vankop */ -const versions = __webpack_require__(61765).versions; -const Resolver = __webpack_require__(7675); -const { getType, PathType } = __webpack_require__(69821); +const path = __webpack_require__(85622); +const DescriptionFileUtils = __webpack_require__(18641); +const forEachBail = __webpack_require__(55426); +const { processExportsField } = __webpack_require__(94340); +const { parseIdentifier } = __webpack_require__(98623); +const { checkExportsFieldTarget } = __webpack_require__(69821); -const SyncAsyncFileSystemDecorator = __webpack_require__(83908); +/** @typedef {import("./Resolver")} Resolver */ +/** @typedef {import("./Resolver").ResolveStepHook} ResolveStepHook */ +/** @typedef {import("./util/entrypoints").ExportsField} ExportsField */ +/** @typedef {import("./util/entrypoints").FieldProcessor} FieldProcessor */ -const AliasFieldPlugin = __webpack_require__(94469); -const AliasPlugin = __webpack_require__(42673); -const AppendPlugin = __webpack_require__(72405); -const ConditionalPlugin = __webpack_require__(13134); -const DescriptionFilePlugin = __webpack_require__(85774); -const DirectoryExistsPlugin = __webpack_require__(61827); -const ExportsFieldPlugin = __webpack_require__(98169); -const FileExistsPlugin = __webpack_require__(9412); -const ImportsFieldPlugin = __webpack_require__(41031); -const JoinRequestPartPlugin = __webpack_require__(11399); -const JoinRequestPlugin = __webpack_require__(90522); -const MainFieldPlugin = __webpack_require__(18425); -const ModulesInHierachicDirectoriesPlugin = __webpack_require__(44964); -const ModulesInRootPlugin = __webpack_require__(39803); -const NextPlugin = __webpack_require__(76354); -const ParsePlugin = __webpack_require__(95204); -const PnpPlugin = __webpack_require__(63321); -const RestrictionsPlugin = __webpack_require__(94620); -const ResultPlugin = __webpack_require__(47775); -const RootsPlugin = __webpack_require__(8068); -const SelfReferencePlugin = __webpack_require__(24887); -const SymlinkPlugin = __webpack_require__(69476); -const TryNextPlugin = __webpack_require__(73771); -const UnsafeCachePlugin = __webpack_require__(57943); -const UseFilePlugin = __webpack_require__(81190); +module.exports = class ExportsFieldPlugin { + /** + * @param {string | ResolveStepHook} source source + * @param {Set} conditionNames condition names + * @param {string | string[]} fieldNamePath name path + * @param {string | ResolveStepHook} target target + */ + constructor(source, conditionNames, fieldNamePath, target) { + this.source = source; + this.target = target; + this.conditionNames = conditionNames; + this.fieldName = fieldNamePath; + /** @type {WeakMap} */ + this.fieldProcessorCache = new WeakMap(); + } -/** @typedef {import("./AliasPlugin").AliasOption} AliasOptionEntry */ -/** @typedef {import("./PnpPlugin").PnpApiImpl} PnpApi */ -/** @typedef {import("./Resolver").FileSystem} FileSystem */ -/** @typedef {import("./Resolver").ResolveRequest} ResolveRequest */ -/** @typedef {import("./Resolver").SyncFileSystem} SyncFileSystem */ + /** + * @param {Resolver} resolver the resolver + * @returns {void} + */ + apply(resolver) { + const target = resolver.ensureHook(this.target); + resolver + .getHook(this.source) + .tapAsync("ExportsFieldPlugin", (request, resolveContext, callback) => { + // When there is no description file, abort + if (!request.descriptionFilePath) return callback(); + if ( + // When the description file is inherited from parent, abort + // (There is no description file inside of this package) + request.relativePath !== "." || + request.request === undefined + ) + return callback(); -/** @typedef {string|string[]|false} AliasOptionNewRequest */ -/** @typedef {{[k: string]: AliasOptionNewRequest}} AliasOptions */ -/** @typedef {{apply: function(Resolver): void} | function(this: Resolver, Resolver): void} Plugin */ + const remainingRequest = + request.query || request.fragment + ? (request.request === "." ? "./" : request.request) + + request.query + + request.fragment + : request.request; + /** @type {ExportsField|null} */ + const exportsField = DescriptionFileUtils.getField( + request.descriptionFileData, + this.fieldName + ); + if (!exportsField) return callback(); -/** - * @typedef {Object} UserResolveOptions - * @property {(AliasOptions | AliasOptionEntry[])=} alias A list of module alias configurations or an object which maps key to value - * @property {(AliasOptions | AliasOptionEntry[])=} fallback A list of module alias configurations or an object which maps key to value, applied only after modules option - * @property {(string | string[])[]=} aliasFields A list of alias fields in description files - * @property {(function(ResolveRequest): boolean)=} cachePredicate A function which decides whether a request should be cached or not. An object is passed with at least `path` and `request` properties. - * @property {boolean=} cacheWithContext Whether or not the unsafeCache should include request context as part of the cache key. - * @property {string[]=} descriptionFiles A list of description files to read from - * @property {string[]=} conditionNames A list of exports field condition names. - * @property {boolean=} enforceExtension Enforce that a extension from extensions must be used - * @property {(string | string[])[]=} exportsFields A list of exports fields in description files - * @property {(string | string[])[]=} importsFields A list of imports fields in description files - * @property {string[]=} extensions A list of extensions which should be tried for files - * @property {FileSystem} fileSystem The file system which should be used - * @property {(object | boolean)=} unsafeCache Use this cache object to unsafely cache the successful requests - * @property {boolean=} symlinks Resolve symlinks to their symlinked location - * @property {Resolver=} resolver A prepared Resolver to which the plugins are attached - * @property {string[] | string=} modules A list of directories to resolve modules from, can be absolute path or folder name - * @property {(string | string[] | {name: string | string[], forceRelative: boolean})[]=} mainFields A list of main fields in description files - * @property {string[]=} mainFiles A list of main files in directories - * @property {Plugin[]=} plugins A list of additional resolve plugins which should be applied - * @property {PnpApi | null=} pnpApi A PnP API that should be used - null is "never", undefined is "auto" - * @property {string[]=} roots A list of root paths - * @property {boolean=} fullySpecified The request is already fully specified and no extensions or directories are resolved for it - * @property {boolean=} resolveToContext Resolve to a context instead of a file - * @property {(string|RegExp)[]=} restrictions A list of resolve restrictions - * @property {boolean=} useSyncFileSystemCalls Use only the sync constiants of the file system calls - * @property {boolean=} preferRelative Prefer to resolve module requests as relative requests before falling back to modules - * @property {boolean=} preferAbsolute Prefer to resolve server-relative urls as absolute paths before falling back to resolve in roots - */ + if (request.directory) { + return callback( + new Error( + `Resolving to directories is not possible with the exports field (request was ${remainingRequest}/)` + ) + ); + } -/** - * @typedef {Object} ResolveOptions - * @property {AliasOptionEntry[]} alias - * @property {AliasOptionEntry[]} fallback - * @property {Set} aliasFields - * @property {(function(ResolveRequest): boolean)} cachePredicate - * @property {boolean} cacheWithContext - * @property {Set} conditionNames A list of exports field condition names. - * @property {string[]} descriptionFiles - * @property {boolean} enforceExtension - * @property {Set} exportsFields - * @property {Set} importsFields - * @property {Set} extensions - * @property {FileSystem} fileSystem - * @property {object | false} unsafeCache - * @property {boolean} symlinks - * @property {Resolver=} resolver - * @property {Array} modules - * @property {{name: string[], forceRelative: boolean}[]} mainFields - * @property {Set} mainFiles - * @property {Plugin[]} plugins - * @property {PnpApi | null} pnpApi - * @property {Set} roots - * @property {boolean} fullySpecified - * @property {boolean} resolveToContext - * @property {Set} restrictions - * @property {boolean} preferRelative - * @property {boolean} preferAbsolute - */ + let paths; -/** - * @param {PnpApi | null=} option option - * @returns {PnpApi | null} processed option - */ -function processPnpApiOption(option) { - if ( - option === undefined && - /** @type {NodeJS.ProcessVersions & {pnp: string}} */ versions.pnp - ) { - // @ts-ignore - return __webpack_require__(97289); // eslint-disable-line node/no-missing-require - } + try { + // We attach the cache to the description file instead of the exportsField value + // because we use a WeakMap and the exportsField could be a string too. + // Description file is always an object when exports field can be accessed. + let fieldProcessor = this.fieldProcessorCache.get( + request.descriptionFileData + ); + if (fieldProcessor === undefined) { + fieldProcessor = processExportsField(exportsField); + this.fieldProcessorCache.set( + request.descriptionFileData, + fieldProcessor + ); + } + paths = fieldProcessor(remainingRequest, this.conditionNames); + } catch (err) { + if (resolveContext.log) { + resolveContext.log( + `Exports field in ${request.descriptionFilePath} can't be processed: ${err}` + ); + } + return callback(err); + } - return option || null; -} + if (paths.length === 0) { + return callback( + new Error( + `Package path ${remainingRequest} is not exported from package ${request.descriptionFileRoot} (see exports field in ${request.descriptionFilePath})` + ) + ); + } -/** - * @param {AliasOptions | AliasOptionEntry[] | undefined} alias alias - * @returns {AliasOptionEntry[]} normalized aliases - */ -function normalizeAlias(alias) { - return typeof alias === "object" && !Array.isArray(alias) && alias !== null - ? Object.keys(alias).map(key => { - /** @type {AliasOptionEntry} */ - const obj = { name: key, onlyModule: false, alias: alias[key] }; + forEachBail( + paths, + (p, callback) => { + const parsedIdentifier = parseIdentifier(p); - if (/\$$/.test(key)) { - obj.onlyModule = true; - obj.name = key.substr(0, key.length - 1); - } + if (!parsedIdentifier) return callback(); - return obj; - }) - : /** @type {Array} */ (alias) || []; -} + const [relativePath, query, fragment] = parsedIdentifier; -/** - * @param {UserResolveOptions} options input options - * @returns {ResolveOptions} output options - */ -function createOptions(options) { - const mainFieldsSet = new Set(options.mainFields || ["main"]); - const mainFields = []; + const error = checkExportsFieldTarget(relativePath); - for (const item of mainFieldsSet) { - if (typeof item === "string") { - mainFields.push({ - name: [item], - forceRelative: true - }); - } else if (Array.isArray(item)) { - mainFields.push({ - name: item, - forceRelative: true - }); - } else { - mainFields.push({ - name: Array.isArray(item.name) ? item.name : [item.name], - forceRelative: item.forceRelative - }); - } - } + if (error) { + return callback(error); + } - return { - alias: normalizeAlias(options.alias), - fallback: normalizeAlias(options.fallback), - aliasFields: new Set(options.aliasFields), - cachePredicate: - options.cachePredicate || - function () { - return true; - }, - cacheWithContext: - typeof options.cacheWithContext !== "undefined" - ? options.cacheWithContext - : true, - exportsFields: new Set(options.exportsFields || ["exports"]), - importsFields: new Set(options.importsFields || ["imports"]), - conditionNames: new Set(options.conditionNames), - descriptionFiles: Array.from( - new Set(options.descriptionFiles || ["package.json"]) - ), - enforceExtension: - options.enforceExtension === undefined - ? options.extensions && options.extensions.includes("") - ? true - : false - : options.enforceExtension, - extensions: new Set(options.extensions || [".js", ".json", ".node"]), - fileSystem: options.useSyncFileSystemCalls - ? new SyncAsyncFileSystemDecorator( - /** @type {SyncFileSystem} */ ( - /** @type {unknown} */ (options.fileSystem) - ) - ) - : options.fileSystem, - unsafeCache: - options.unsafeCache && typeof options.unsafeCache !== "object" - ? {} - : options.unsafeCache || false, - symlinks: typeof options.symlinks !== "undefined" ? options.symlinks : true, - resolver: options.resolver, - modules: mergeFilteredToArray( - Array.isArray(options.modules) - ? options.modules - : options.modules - ? [options.modules] - : ["node_modules"], - item => { - const type = getType(item); - return type === PathType.Normal || type === PathType.Relative; - } - ), - mainFields, - mainFiles: new Set(options.mainFiles || ["index"]), - plugins: options.plugins || [], - pnpApi: processPnpApiOption(options.pnpApi), - roots: new Set(options.roots || undefined), - fullySpecified: options.fullySpecified || false, - resolveToContext: options.resolveToContext || false, - preferRelative: options.preferRelative || false, - preferAbsolute: options.preferAbsolute || false, - restrictions: new Set(options.restrictions) - }; -} + const obj = { + ...request, + request: undefined, + path: path.join( + /** @type {string} */ (request.descriptionFileRoot), + relativePath + ), + relativePath, + query, + fragment + }; -/** - * @param {UserResolveOptions} options resolve options - * @returns {Resolver} created resolver - */ -exports.createResolver = function (options) { - const normalizedOptions = createOptions(options); + resolver.doResolve( + target, + obj, + "using exports field: " + p, + resolveContext, + callback + ); + }, + (err, result) => callback(err, result || null) + ); + }); + } +}; - const { - alias, - fallback, - aliasFields, - cachePredicate, - cacheWithContext, - conditionNames, - descriptionFiles, - enforceExtension, - exportsFields, - importsFields, - extensions, - fileSystem, - fullySpecified, - mainFields, - mainFiles, - modules, - plugins: userPlugins, - pnpApi, - resolveToContext, - preferRelative, - preferAbsolute, - symlinks, - unsafeCache, - resolver: customResolver, - restrictions, - roots - } = normalizedOptions; - const plugins = userPlugins.slice(); +/***/ }), - const resolver = customResolver - ? customResolver - : new Resolver(fileSystem, normalizedOptions); +/***/ 9412: +/***/ (function(module) { - //// pipeline //// +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ - resolver.ensureHook("resolve"); - resolver.ensureHook("internalResolve"); - resolver.ensureHook("newInteralResolve"); - resolver.ensureHook("parsedResolve"); - resolver.ensureHook("describedResolve"); - resolver.ensureHook("internal"); - resolver.ensureHook("rawModule"); - resolver.ensureHook("module"); - resolver.ensureHook("resolveAsModule"); - resolver.ensureHook("undescribedResolveInPackage"); - resolver.ensureHook("resolveInPackage"); - resolver.ensureHook("resolveInExistingDirectory"); - resolver.ensureHook("relative"); - resolver.ensureHook("describedRelative"); - resolver.ensureHook("directory"); - resolver.ensureHook("undescribedExistingDirectory"); - resolver.ensureHook("existingDirectory"); - resolver.ensureHook("undescribedRawFile"); - resolver.ensureHook("rawFile"); - resolver.ensureHook("file"); - resolver.ensureHook("finalFile"); - resolver.ensureHook("existingFile"); - resolver.ensureHook("resolved"); - // resolve - for (const { source, resolveOptions } of [ - { source: "resolve", resolveOptions: { fullySpecified } }, - { source: "internal-resolve", resolveOptions: { fullySpecified: false } } - ]) { - if (unsafeCache) { - plugins.push( - new UnsafeCachePlugin( - source, - cachePredicate, - unsafeCache, - cacheWithContext, - `new-${source}` - ) - ); - plugins.push( - new ParsePlugin(`new-${source}`, resolveOptions, "parsed-resolve") - ); - } else { - plugins.push(new ParsePlugin(source, resolveOptions, "parsed-resolve")); - } - } - // parsed-resolve - plugins.push( - new DescriptionFilePlugin( - "parsed-resolve", - descriptionFiles, - false, - "described-resolve" - ) - ); - plugins.push(new NextPlugin("after-parsed-resolve", "described-resolve")); +/** @typedef {import("./Resolver")} Resolver */ +/** @typedef {import("./Resolver").ResolveStepHook} ResolveStepHook */ - // described-resolve - plugins.push(new NextPlugin("described-resolve", "normal-resolve")); - if (fallback.length > 0) { - plugins.push( - new AliasPlugin("described-resolve", fallback, "internal-resolve") - ); +module.exports = class FileExistsPlugin { + /** + * @param {string | ResolveStepHook} source source + * @param {string | ResolveStepHook} target target + */ + constructor(source, target) { + this.source = source; + this.target = target; } - // normal-resolve - if (alias.length > 0) - plugins.push(new AliasPlugin("normal-resolve", alias, "internal-resolve")); - aliasFields.forEach(item => { - plugins.push( - new AliasFieldPlugin("normal-resolve", item, "internal-resolve") - ); - }); - if (preferRelative) { - plugins.push(new JoinRequestPlugin("after-normal-resolve", "relative")); - } - plugins.push( - new ConditionalPlugin( - "after-normal-resolve", - { module: true }, - "resolve as module", - false, - "raw-module" - ) - ); - plugins.push( - new ConditionalPlugin( - "after-normal-resolve", - { internal: true }, - "resolve as internal import", - false, - "internal" - ) - ); - if (preferAbsolute) { - plugins.push(new JoinRequestPlugin("after-normal-resolve", "relative")); - } - if (roots.size > 0) { - plugins.push(new RootsPlugin("after-normal-resolve", roots, "relative")); - } - if (!preferRelative && !preferAbsolute) { - plugins.push(new JoinRequestPlugin("after-normal-resolve", "relative")); + /** + * @param {Resolver} resolver the resolver + * @returns {void} + */ + apply(resolver) { + const target = resolver.ensureHook(this.target); + const fs = resolver.fileSystem; + resolver + .getHook(this.source) + .tapAsync("FileExistsPlugin", (request, resolveContext, callback) => { + const file = request.path; + if (!file) return callback(); + fs.stat(file, (err, stat) => { + if (err || !stat) { + if (resolveContext.missingDependencies) + resolveContext.missingDependencies.add(file); + if (resolveContext.log) resolveContext.log(file + " doesn't exist"); + return callback(); + } + if (!stat.isFile()) { + if (resolveContext.missingDependencies) + resolveContext.missingDependencies.add(file); + if (resolveContext.log) resolveContext.log(file + " is not a file"); + return callback(); + } + if (resolveContext.fileDependencies) + resolveContext.fileDependencies.add(file); + resolver.doResolve( + target, + request, + "existing file: " + file, + resolveContext, + callback + ); + }); + }); } +}; - // internal - importsFields.forEach(importsField => { - plugins.push( - new ImportsFieldPlugin( - "internal", - conditionNames, - importsField, - "relative", - "internal-resolve" - ) - ); - }); - // raw-module - exportsFields.forEach(exportsField => { - plugins.push( - new SelfReferencePlugin("raw-module", exportsField, "resolve-as-module") - ); - }); - modules.forEach(item => { - if (Array.isArray(item)) { - if (item.includes("node_modules") && pnpApi) { - plugins.push( - new ModulesInHierachicDirectoriesPlugin( - "raw-module", - item.filter(i => i !== "node_modules"), - "module" - ) - ); - plugins.push( - new PnpPlugin("raw-module", pnpApi, "undescribed-resolve-in-package") - ); - } else { - plugins.push( - new ModulesInHierachicDirectoriesPlugin("raw-module", item, "module") - ); - } - } else { - plugins.push(new ModulesInRootPlugin("raw-module", item, "module")); - } - }); +/***/ }), - // module - plugins.push(new JoinRequestPartPlugin("module", "resolve-as-module")); +/***/ 41031: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - // resolve-as-module - if (!resolveToContext) { - plugins.push( - new ConditionalPlugin( - "resolve-as-module", - { directory: false, request: "." }, - "single file module", - true, - "undescribed-raw-file" - ) - ); - } - plugins.push( - new DirectoryExistsPlugin( - "resolve-as-module", - "undescribed-resolve-in-package" - ) - ); +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Ivan Kopeykin @vankop +*/ - // undescribed-resolve-in-package - plugins.push( - new DescriptionFilePlugin( - "undescribed-resolve-in-package", - descriptionFiles, - false, - "resolve-in-package" - ) - ); - plugins.push( - new NextPlugin("after-undescribed-resolve-in-package", "resolve-in-package") - ); - // resolve-in-package - exportsFields.forEach(exportsField => { - plugins.push( - new ExportsFieldPlugin( - "resolve-in-package", - conditionNames, - exportsField, - "relative" - ) - ); - }); - plugins.push( - new NextPlugin("resolve-in-package", "resolve-in-existing-directory") - ); - // resolve-in-existing-directory - plugins.push( - new JoinRequestPlugin("resolve-in-existing-directory", "relative") - ); +const path = __webpack_require__(85622); +const DescriptionFileUtils = __webpack_require__(18641); +const forEachBail = __webpack_require__(55426); +const { processImportsField } = __webpack_require__(94340); +const { parseIdentifier } = __webpack_require__(98623); - // relative - plugins.push( - new DescriptionFilePlugin( - "relative", - descriptionFiles, - true, - "described-relative" - ) - ); - plugins.push(new NextPlugin("after-relative", "described-relative")); +/** @typedef {import("./Resolver")} Resolver */ +/** @typedef {import("./Resolver").ResolveStepHook} ResolveStepHook */ +/** @typedef {import("./util/entrypoints").FieldProcessor} FieldProcessor */ +/** @typedef {import("./util/entrypoints").ImportsField} ImportsField */ - // described-relative - if (resolveToContext) { - plugins.push(new NextPlugin("described-relative", "directory")); - } else { - plugins.push( - new ConditionalPlugin( - "described-relative", - { directory: false }, - null, - true, - "raw-file" - ) - ); - plugins.push( - new ConditionalPlugin( - "described-relative", - { fullySpecified: false }, - "as directory", - true, - "directory" - ) - ); +const dotCode = ".".charCodeAt(0); + +module.exports = class ImportsFieldPlugin { + /** + * @param {string | ResolveStepHook} source source + * @param {Set} conditionNames condition names + * @param {string | string[]} fieldNamePath name path + * @param {string | ResolveStepHook} targetFile target file + * @param {string | ResolveStepHook} targetPackage target package + */ + constructor( + source, + conditionNames, + fieldNamePath, + targetFile, + targetPackage + ) { + this.source = source; + this.targetFile = targetFile; + this.targetPackage = targetPackage; + this.conditionNames = conditionNames; + this.fieldName = fieldNamePath; + /** @type {WeakMap} */ + this.fieldProcessorCache = new WeakMap(); } - // directory - plugins.push( - new DirectoryExistsPlugin("directory", "undescribed-existing-directory") - ); + /** + * @param {Resolver} resolver the resolver + * @returns {void} + */ + apply(resolver) { + const targetFile = resolver.ensureHook(this.targetFile); + const targetPackage = resolver.ensureHook(this.targetPackage); - if (resolveToContext) { - // undescribed-existing-directory - plugins.push(new NextPlugin("undescribed-existing-directory", "resolved")); - } else { - // undescribed-existing-directory - plugins.push( - new DescriptionFilePlugin( - "undescribed-existing-directory", - descriptionFiles, - false, - "existing-directory" - ) - ); - mainFiles.forEach(item => { - plugins.push( - new UseFilePlugin( - "undescribed-existing-directory", - item, - "undescribed-raw-file" - ) - ); - }); + resolver + .getHook(this.source) + .tapAsync("ImportsFieldPlugin", (request, resolveContext, callback) => { + // When there is no description file, abort + if (!request.descriptionFilePath || request.request === undefined) { + return callback(); + } - // described-existing-directory - mainFields.forEach(item => { - plugins.push( - new MainFieldPlugin( - "existing-directory", - item, - "resolve-in-existing-directory" - ) - ); - }); - mainFiles.forEach(item => { - plugins.push( - new UseFilePlugin("existing-directory", item, "undescribed-raw-file") - ); - }); + const remainingRequest = + request.request + request.query + request.fragment; + /** @type {ImportsField|null} */ + const importsField = DescriptionFileUtils.getField( + request.descriptionFileData, + this.fieldName + ); + if (!importsField) return callback(); - // undescribed-raw-file - plugins.push( - new DescriptionFilePlugin( - "undescribed-raw-file", - descriptionFiles, - true, - "raw-file" - ) - ); - plugins.push(new NextPlugin("after-undescribed-raw-file", "raw-file")); + if (request.directory) { + return callback( + new Error( + `Resolving to directories is not possible with the imports field (request was ${remainingRequest}/)` + ) + ); + } - // raw-file - plugins.push( - new ConditionalPlugin( - "raw-file", - { fullySpecified: true }, - null, - false, - "file" - ) - ); - if (!enforceExtension) { - plugins.push(new TryNextPlugin("raw-file", "no extension", "file")); - } - extensions.forEach(item => { - plugins.push(new AppendPlugin("raw-file", item, "file")); - }); + let paths; - // file - if (alias.length > 0) - plugins.push(new AliasPlugin("file", alias, "internal-resolve")); - aliasFields.forEach(item => { - plugins.push(new AliasFieldPlugin("file", item, "internal-resolve")); - }); - plugins.push(new NextPlugin("file", "final-file")); + try { + // We attach the cache to the description file instead of the importsField value + // because we use a WeakMap and the importsField could be a string too. + // Description file is always an object when exports field can be accessed. + let fieldProcessor = this.fieldProcessorCache.get( + request.descriptionFileData + ); + if (fieldProcessor === undefined) { + fieldProcessor = processImportsField(importsField); + this.fieldProcessorCache.set( + request.descriptionFileData, + fieldProcessor + ); + } + paths = fieldProcessor(remainingRequest, this.conditionNames); + } catch (err) { + if (resolveContext.log) { + resolveContext.log( + `Imports field in ${request.descriptionFilePath} can't be processed: ${err}` + ); + } + return callback(err); + } - // final-file - plugins.push(new FileExistsPlugin("final-file", "existing-file")); + if (paths.length === 0) { + return callback( + new Error( + `Package import ${remainingRequest} is not imported from package ${request.descriptionFileRoot} (see imports field in ${request.descriptionFilePath})` + ) + ); + } - // existing-file - if (symlinks) - plugins.push(new SymlinkPlugin("existing-file", "existing-file")); - plugins.push(new NextPlugin("existing-file", "resolved")); - } + forEachBail( + paths, + (p, callback) => { + const parsedIdentifier = parseIdentifier(p); - // resolved - if (restrictions.size > 0) { - plugins.push(new RestrictionsPlugin(resolver.hooks.resolved, restrictions)); - } - plugins.push(new ResultPlugin(resolver.hooks.resolved)); + if (!parsedIdentifier) return callback(); - //// RESOLVER //// + const [path_, query, fragment] = parsedIdentifier; - for (const plugin of plugins) { - if (typeof plugin === "function") { - plugin.call(resolver, resolver); - } else { - plugin.apply(resolver); - } - } + switch (path_.charCodeAt(0)) { + // should be relative + case dotCode: { + const obj = { + ...request, + request: undefined, + path: path.join( + /** @type {string} */ (request.descriptionFileRoot), + path_ + ), + relativePath: path_, + query, + fragment + }; - return resolver; -}; + resolver.doResolve( + targetFile, + obj, + "using imports field: " + p, + resolveContext, + callback + ); + break; + } -/** - * Merging filtered elements - * @param {string[]} array source array - * @param {function(string): boolean} filter predicate - * @returns {Array} merge result - */ -function mergeFilteredToArray(array, filter) { - /** @type {Array} */ - const result = []; - const set = new Set(array); + // package resolving + default: { + const obj = { + ...request, + request: path_, + relativePath: path_, + fullySpecified: true, + query, + fragment + }; - for (const item of set) { - if (filter(item)) { - const lastElement = - result.length > 0 ? result[result.length - 1] : undefined; - if (Array.isArray(lastElement)) { - lastElement.push(item); - } else { - result.push([item]); - } - } else { - result.push(item); - } + resolver.doResolve( + targetPackage, + obj, + "using imports field: " + p, + resolveContext, + callback + ); + } + } + }, + (err, result) => callback(err, result || null) + ); + }); } - - return result; -} +}; /***/ }), -/***/ 94620: +/***/ 11399: /***/ (function(module) { "use strict"; /* MIT License http://www.opensource.org/licenses/mit-license.php - Author Ivan Kopeykin @vankop + Author Tobias Koppers @sokra */ @@ -138366,24 +138418,16 @@ function mergeFilteredToArray(array, filter) { /** @typedef {import("./Resolver")} Resolver */ /** @typedef {import("./Resolver").ResolveStepHook} ResolveStepHook */ -const slashCode = "/".charCodeAt(0); -const backslashCode = "\\".charCodeAt(0); - -const isInside = (path, parent) => { - if (!path.startsWith(parent)) return false; - if (path.length === parent.length) return true; - const charCode = path.charCodeAt(parent.length); - return charCode === slashCode || charCode === backslashCode; -}; +const namespaceStartCharCode = "@".charCodeAt(0); -module.exports = class RestrictionsPlugin { +module.exports = class JoinRequestPartPlugin { /** * @param {string | ResolveStepHook} source source - * @param {Set} restrictions restrictions + * @param {string | ResolveStepHook} target target */ - constructor(source, restrictions) { + constructor(source, target) { this.source = source; - this.restrictions = restrictions; + this.target = target; } /** @@ -138391,41 +138435,48 @@ module.exports = class RestrictionsPlugin { * @returns {void} */ apply(resolver) { + const target = resolver.ensureHook(this.target); resolver .getHook(this.source) - .tapAsync("RestrictionsPlugin", (request, resolveContext, callback) => { - if (typeof request.path === "string") { - const path = request.path; - for (const rule of this.restrictions) { - if (typeof rule === "string") { - if (!isInside(path, rule)) { - if (resolveContext.log) { - resolveContext.log( - `${path} is not inside of the restriction ${rule}` - ); - } - return callback(null, null); - } - } else if (!rule.test(path)) { - if (resolveContext.log) { - resolveContext.log( - `${path} doesn't match the restriction ${rule}` - ); - } - return callback(null, null); - } + .tapAsync( + "JoinRequestPartPlugin", + (request, resolveContext, callback) => { + const req = request.request || ""; + let i = req.indexOf("/", 3); + + if (i >= 0 && req.charCodeAt(2) === namespaceStartCharCode) { + i = req.indexOf("/", i + 1); } - } - callback(); - }); + let moduleName, remainingRequest, fullySpecified; + if (i < 0) { + moduleName = req; + remainingRequest = "."; + fullySpecified = false; + } else { + moduleName = req.slice(0, i); + remainingRequest = "." + req.slice(i); + fullySpecified = request.fullySpecified; + } + const obj = { + ...request, + path: resolver.join(request.path, moduleName), + relativePath: + request.relativePath && + resolver.join(request.relativePath, moduleName), + request: remainingRequest, + fullySpecified + }; + resolver.doResolve(target, obj, null, resolveContext, callback); + } + ); } }; /***/ }), -/***/ 47775: +/***/ 90522: /***/ (function(module) { "use strict"; @@ -138439,12 +138490,14 @@ module.exports = class RestrictionsPlugin { /** @typedef {import("./Resolver")} Resolver */ /** @typedef {import("./Resolver").ResolveStepHook} ResolveStepHook */ -module.exports = class ResultPlugin { +module.exports = class JoinRequestPlugin { /** - * @param {ResolveStepHook} source source + * @param {string | ResolveStepHook} source source + * @param {string | ResolveStepHook} target target */ - constructor(source) { + constructor(source, target) { this.source = source; + this.target = target; } /** @@ -138452,50 +138505,42 @@ module.exports = class ResultPlugin { * @returns {void} */ apply(resolver) { - this.source.tapAsync( - "ResultPlugin", - (request, resolverContext, callback) => { - const obj = { ...request }; - if (resolverContext.log) - resolverContext.log("reporting result " + obj.path); - resolver.hooks.result.callAsync(obj, resolverContext, err => { - if (err) return callback(err); - callback(null, obj); - }); - } - ); + const target = resolver.ensureHook(this.target); + resolver + .getHook(this.source) + .tapAsync("JoinRequestPlugin", (request, resolveContext, callback) => { + const obj = { + ...request, + path: resolver.join(request.path, request.request), + relativePath: + request.relativePath && + resolver.join(request.relativePath, request.request), + request: undefined + }; + resolver.doResolve(target, obj, null, resolveContext, callback); + }); } }; /***/ }), -/***/ 8068: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { +/***/ 50098: +/***/ (function(module) { "use strict"; /* MIT License http://www.opensource.org/licenses/mit-license.php - Author Ivan Kopeykin @vankop + Author Tobias Koppers @sokra */ -const forEachBail = __webpack_require__(55426); - /** @typedef {import("./Resolver")} Resolver */ -/** @typedef {import("./Resolver").ResolveStepHook} ResolveStepHook */ -class RootsPlugin { - /** - * @param {string | ResolveStepHook} source source hook - * @param {Set} roots roots - * @param {string | ResolveStepHook} target target hook - */ - constructor(source, roots, target) { - this.roots = Array.from(roots); +module.exports = class LogInfoPlugin { + constructor(source) { this.source = source; - this.target = target; } /** @@ -138503,44 +138548,42 @@ class RootsPlugin { * @returns {void} */ apply(resolver) { - const target = resolver.ensureHook(this.target); - + const source = this.source; resolver .getHook(this.source) - .tapAsync("RootsPlugin", (request, resolveContext, callback) => { - const req = request.request; - if (!req) return callback(); - if (!req.startsWith("/")) return callback(); - - forEachBail( - this.roots, - (root, callback) => { - const path = resolver.join(root, req.slice(1)); - const obj = { - ...request, - path, - relativePath: request.relativePath && path - }; - resolver.doResolve( - target, - obj, - `root path ${root}`, - resolveContext, - callback - ); - }, - callback - ); + .tapAsync("LogInfoPlugin", (request, resolveContext, callback) => { + if (!resolveContext.log) return callback(); + const log = resolveContext.log; + const prefix = "[" + source + "] "; + if (request.path) + log(prefix + "Resolving in directory: " + request.path); + if (request.request) + log(prefix + "Resolving request: " + request.request); + if (request.module) log(prefix + "Request is an module request."); + if (request.directory) log(prefix + "Request is a directory request."); + if (request.query) + log(prefix + "Resolving request query: " + request.query); + if (request.fragment) + log(prefix + "Resolving request fragment: " + request.fragment); + if (request.descriptionFilePath) + log( + prefix + "Has description data from " + request.descriptionFilePath + ); + if (request.relativePath) + log( + prefix + + "Relative path from description file is: " + + request.relativePath + ); + callback(); }); } -} - -module.exports = RootsPlugin; +}; /***/ }), -/***/ 24887: +/***/ 18425: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; @@ -138551,23 +138594,25 @@ module.exports = RootsPlugin; +const path = __webpack_require__(85622); const DescriptionFileUtils = __webpack_require__(18641); /** @typedef {import("./Resolver")} Resolver */ /** @typedef {import("./Resolver").ResolveStepHook} ResolveStepHook */ +/** @typedef {{name: string|Array, forceRelative: boolean}} MainFieldOptions */ -const slashCode = "/".charCodeAt(0); +const alreadyTriedMainField = Symbol("alreadyTriedMainField"); -module.exports = class SelfReferencePlugin { +module.exports = class MainFieldPlugin { /** * @param {string | ResolveStepHook} source source - * @param {string | string[]} fieldNamePath name path + * @param {MainFieldOptions} options options * @param {string | ResolveStepHook} target target */ - constructor(source, fieldNamePath, target) { + constructor(source, options, target) { this.source = source; + this.options = options; this.target = target; - this.fieldName = fieldNamePath; } /** @@ -138578,49 +138623,48 @@ module.exports = class SelfReferencePlugin { const target = resolver.ensureHook(this.target); resolver .getHook(this.source) - .tapAsync("SelfReferencePlugin", (request, resolveContext, callback) => { - if (!request.descriptionFilePath) return callback(); - - const req = request.request; - if (!req) return callback(); - - // Feature is only enabled when an exports field is present - const exportsField = DescriptionFileUtils.getField( - request.descriptionFileData, - this.fieldName - ); - if (!exportsField) return callback(); - - const name = DescriptionFileUtils.getField( + .tapAsync("MainFieldPlugin", (request, resolveContext, callback) => { + if ( + request.path !== request.descriptionFileRoot || + request[alreadyTriedMainField] === request.descriptionFilePath || + !request.descriptionFilePath + ) + return callback(); + const filename = path.basename(request.descriptionFilePath); + let mainModule = DescriptionFileUtils.getField( request.descriptionFileData, - "name" + this.options.name ); - if (typeof name !== "string") return callback(); if ( - req.startsWith(name) && - (req.length === name.length || - req.charCodeAt(name.length) === slashCode) + !mainModule || + typeof mainModule !== "string" || + mainModule === "." || + mainModule === "./" ) { - const remainingRequest = `.${req.slice(name.length)}`; - - const obj = { - ...request, - request: remainingRequest, - path: /** @type {string} */ (request.descriptionFileRoot), - relativePath: "." - }; - - resolver.doResolve( - target, - obj, - "self reference", - resolveContext, - callback - ); - } else { return callback(); } + if (this.options.forceRelative && !/^\.\.?\//.test(mainModule)) + mainModule = "./" + mainModule; + const obj = { + ...request, + request: mainModule, + module: false, + directory: mainModule.endsWith("/"), + [alreadyTriedMainField]: request.descriptionFilePath + }; + return resolver.doResolve( + target, + obj, + "use " + + mainModule + + " from " + + this.options.name + + " in " + + filename, + resolveContext, + callback + ); }); } }; @@ -138628,7 +138672,7 @@ module.exports = class SelfReferencePlugin { /***/ }), -/***/ 69476: +/***/ 44964: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; @@ -138641,18 +138685,19 @@ module.exports = class SelfReferencePlugin { const forEachBail = __webpack_require__(55426); const getPaths = __webpack_require__(17117); -const { getType, PathType } = __webpack_require__(69821); /** @typedef {import("./Resolver")} Resolver */ /** @typedef {import("./Resolver").ResolveStepHook} ResolveStepHook */ -module.exports = class SymlinkPlugin { +module.exports = class ModulesInHierachicDirectoriesPlugin { /** * @param {string | ResolveStepHook} source source + * @param {string | Array} directories directories * @param {string | ResolveStepHook} target target */ - constructor(source, target) { + constructor(source, directories, target) { this.source = source; + this.directories = /** @type {Array} */ ([]).concat(directories); this.target = target; } @@ -138662,60 +138707,106 @@ module.exports = class SymlinkPlugin { */ apply(resolver) { const target = resolver.ensureHook(this.target); - const fs = resolver.fileSystem; resolver .getHook(this.source) - .tapAsync("SymlinkPlugin", (request, resolveContext, callback) => { - if (request.ignoreSymlinks) return callback(); - const pathsResult = getPaths(request.path); - const pathSeqments = pathsResult.seqments; - const paths = pathsResult.paths; - - let containsSymlink = false; - let idx = -1; - forEachBail( - paths, - (path, callback) => { - idx++; - if (resolveContext.fileDependencies) - resolveContext.fileDependencies.add(path); - fs.readlink(path, (err, result) => { - if (!err && result) { - pathSeqments[idx] = result; - containsSymlink = true; - // Shortcut when absolute symlink found - const resultType = getType(result.toString()); - if ( - resultType === PathType.AbsoluteWin || - resultType === PathType.AbsolutePosix - ) { - return callback(null, idx); + .tapAsync( + "ModulesInHierachicDirectoriesPlugin", + (request, resolveContext, callback) => { + const fs = resolver.fileSystem; + const addrs = getPaths(request.path) + .paths.map(p => { + return this.directories.map(d => resolver.join(p, d)); + }) + .reduce((array, p) => { + array.push.apply(array, p); + return array; + }, []); + forEachBail( + addrs, + (addr, callback) => { + fs.stat(addr, (err, stat) => { + if (!err && stat && stat.isDirectory()) { + const obj = { + ...request, + path: addr, + request: "./" + request.request, + module: false + }; + const message = "looking for modules in " + addr; + return resolver.doResolve( + target, + obj, + message, + resolveContext, + callback + ); } - } - callback(); - }); - }, - (err, idx) => { - if (!containsSymlink) return callback(); - const resultSeqments = - typeof idx === "number" - ? pathSeqments.slice(0, idx + 1) - : pathSeqments.slice(); - const result = resultSeqments.reduceRight((a, b) => { - return resolver.join(a, b); - }); - const obj = { - ...request, - path: result - }; - resolver.doResolve( - target, - obj, - "resolved symlink to " + result, - resolveContext, - callback - ); - } + if (resolveContext.log) + resolveContext.log( + addr + " doesn't exist or is not a directory" + ); + if (resolveContext.missingDependencies) + resolveContext.missingDependencies.add(addr); + return callback(); + }); + }, + callback + ); + } + ); + } +}; + + +/***/ }), + +/***/ 39803: +/***/ (function(module) { + +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ + + + +/** @typedef {import("./Resolver")} Resolver */ +/** @typedef {import("./Resolver").ResolveStepHook} ResolveStepHook */ + +module.exports = class ModulesInRootPlugin { + /** + * @param {string | ResolveStepHook} source source + * @param {string} path path + * @param {string | ResolveStepHook} target target + */ + constructor(source, path, target) { + this.source = source; + this.path = path; + this.target = target; + } + + /** + * @param {Resolver} resolver the resolver + * @returns {void} + */ + apply(resolver) { + const target = resolver.ensureHook(this.target); + resolver + .getHook(this.source) + .tapAsync("ModulesInRootPlugin", (request, resolveContext, callback) => { + const obj = { + ...request, + path: this.path, + request: "./" + request.request, + module: false + }; + resolver.doResolve( + target, + obj, + "looking for modules in " + this.path, + resolveContext, + callback ); }); } @@ -138724,7 +138815,7 @@ module.exports = class SymlinkPlugin { /***/ }), -/***/ 83908: +/***/ 76354: /***/ (function(module) { "use strict"; @@ -138735,99 +138826,37 @@ module.exports = class SymlinkPlugin { -/** @typedef {import("./Resolver").FileSystem} FileSystem */ -/** @typedef {import("./Resolver").SyncFileSystem} SyncFileSystem */ - -/** - * @param {SyncFileSystem} fs file system implementation - * @constructor - */ -function SyncAsyncFileSystemDecorator(fs) { - this.fs = fs; +/** @typedef {import("./Resolver")} Resolver */ +/** @typedef {import("./Resolver").ResolveStepHook} ResolveStepHook */ - this.lstat = undefined; - this.lstatSync = undefined; - const lstatSync = fs.lstatSync; - if (lstatSync) { - this.lstat = (arg, options, callback) => { - let result; - try { - result = lstatSync.call(fs, arg); - } catch (e) { - return (callback || options)(e); - } - (callback || options)(null, result); - }; - this.lstatSync = (arg, options) => lstatSync.call(fs, arg, options); +module.exports = class NextPlugin { + /** + * @param {string | ResolveStepHook} source source + * @param {string | ResolveStepHook} target target + */ + constructor(source, target) { + this.source = source; + this.target = target; } - this.stat = (arg, options, callback) => { - let result; - try { - result = callback ? fs.statSync(arg, options) : fs.statSync(arg); - } catch (e) { - return (callback || options)(e); - } - (callback || options)(null, result); - }; - this.statSync = (arg, options) => fs.statSync(arg, options); - - this.readdir = (arg, options, callback) => { - let result; - try { - result = fs.readdirSync(arg); - } catch (e) { - return (callback || options)(e); - } - (callback || options)(null, result); - }; - this.readdirSync = (arg, options) => fs.readdirSync(arg, options); - - this.readFile = (arg, options, callback) => { - let result; - try { - result = fs.readFileSync(arg); - } catch (e) { - return (callback || options)(e); - } - (callback || options)(null, result); - }; - this.readFileSync = (arg, options) => fs.readFileSync(arg, options); - - this.readlink = (arg, options, callback) => { - let result; - try { - result = fs.readlinkSync(arg); - } catch (e) { - return (callback || options)(e); - } - (callback || options)(null, result); - }; - this.readlinkSync = (arg, options) => fs.readlinkSync(arg, options); - - this.readJson = undefined; - this.readJsonSync = undefined; - const readJsonSync = fs.readJsonSync; - if (readJsonSync) { - this.readJson = (arg, options, callback) => { - let result; - try { - result = readJsonSync.call(fs, arg); - } catch (e) { - return (callback || options)(e); - } - (callback || options)(null, result); - }; - - this.readJsonSync = (arg, options) => readJsonSync.call(fs, arg, options); + /** + * @param {Resolver} resolver the resolver + * @returns {void} + */ + apply(resolver) { + const target = resolver.ensureHook(this.target); + resolver + .getHook(this.source) + .tapAsync("NextPlugin", (request, resolveContext, callback) => { + resolver.doResolve(target, request, null, resolveContext, callback); + }); } -} -module.exports = SyncAsyncFileSystemDecorator; +}; /***/ }), -/***/ 73771: +/***/ 95204: /***/ (function(module) { "use strict"; @@ -138839,17 +138868,18 @@ module.exports = SyncAsyncFileSystemDecorator; /** @typedef {import("./Resolver")} Resolver */ +/** @typedef {import("./Resolver").ResolveRequest} ResolveRequest */ /** @typedef {import("./Resolver").ResolveStepHook} ResolveStepHook */ -module.exports = class TryNextPlugin { +module.exports = class ParsePlugin { /** * @param {string | ResolveStepHook} source source - * @param {string} message message + * @param {Partial} requestOptions request options * @param {string | ResolveStepHook} target target */ - constructor(source, message, target) { + constructor(source, requestOptions, target) { this.source = source; - this.message = message; + this.requestOptions = requestOptions; this.target = target; } @@ -138861,14 +138891,46 @@ module.exports = class TryNextPlugin { const target = resolver.ensureHook(this.target); resolver .getHook(this.source) - .tapAsync("TryNextPlugin", (request, resolveContext, callback) => { - resolver.doResolve( - target, - request, - this.message, - resolveContext, - callback - ); + .tapAsync("ParsePlugin", (request, resolveContext, callback) => { + const parsed = resolver.parse(/** @type {string} */ (request.request)); + const obj = { ...request, ...parsed, ...this.requestOptions }; + if (request.query && !parsed.query) { + obj.query = request.query; + } + if (request.fragment && !parsed.fragment) { + obj.fragment = request.fragment; + } + if (parsed && resolveContext.log) { + if (parsed.module) resolveContext.log("Parsed request is a module"); + if (parsed.directory) + resolveContext.log("Parsed request is a directory"); + } + // There is an edge-case where a request with # can be a path or a fragment -> try both + if (obj.request && !obj.query && obj.fragment) { + const directory = obj.fragment.endsWith("/"); + const alternative = { + ...obj, + directory, + request: + obj.request + + (obj.directory ? "/" : "") + + (directory ? obj.fragment.slice(0, -1) : obj.fragment), + fragment: "" + }; + resolver.doResolve( + target, + alternative, + null, + resolveContext, + (err, result) => { + if (err) return callback(err); + if (result) return callback(null, result); + resolver.doResolve(target, obj, null, resolveContext, callback); + } + ); + return; + } + resolver.doResolve(target, obj, null, resolveContext, callback); }); } }; @@ -138876,45 +138938,33 @@ module.exports = class TryNextPlugin { /***/ }), -/***/ 57943: +/***/ 63321: /***/ (function(module) { "use strict"; /* MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra + Author Maël Nison @arcanis */ /** @typedef {import("./Resolver")} Resolver */ -/** @typedef {import("./Resolver").ResolveRequest} ResolveRequest */ /** @typedef {import("./Resolver").ResolveStepHook} ResolveStepHook */ -/** @typedef {{[k: string]: any}} Cache */ - -function getCacheId(request, withContext) { - return JSON.stringify({ - context: withContext ? request.context : "", - path: request.path, - query: request.query, - fragment: request.fragment, - request: request.request - }); -} +/** + * @typedef {Object} PnpApiImpl + * @property {function(string, string, object): string} resolveToUnqualified + */ -module.exports = class UnsafeCachePlugin { +module.exports = class PnpPlugin { /** * @param {string | ResolveStepHook} source source - * @param {function(ResolveRequest): boolean} filterPredicate filterPredicate - * @param {Cache} cache cache - * @param {boolean} withContext withContext + * @param {PnpApiImpl} pnpApi pnpApi * @param {string | ResolveStepHook} target target */ - constructor(source, filterPredicate, cache, withContext, target) { + constructor(source, pnpApi, target) { this.source = source; - this.filterPredicate = filterPredicate; - this.withContext = withContext; - this.cache = cache; + this.pnpApi = pnpApi; this.target = target; } @@ -138926,22 +138976,70 @@ module.exports = class UnsafeCachePlugin { const target = resolver.ensureHook(this.target); resolver .getHook(this.source) - .tapAsync("UnsafeCachePlugin", (request, resolveContext, callback) => { - if (!this.filterPredicate(request)) return callback(); - const cacheId = getCacheId(request, this.withContext); - const cacheEntry = this.cache[cacheId]; - if (cacheEntry) { - return callback(null, cacheEntry); + .tapAsync("PnpPlugin", (request, resolveContext, callback) => { + const req = request.request; + if (!req) return callback(); + + // The trailing slash indicates to PnP that this value is a folder rather than a file + const issuer = `${request.path}/`; + + const packageMatch = /^(@[^/]+\/)?[^/]+/.exec(req); + if (!packageMatch) return callback(); + + const packageName = packageMatch[0]; + const innerRequest = `.${req.slice(packageName.length)}`; + + let resolution; + let apiResolution; + try { + resolution = this.pnpApi.resolveToUnqualified(packageName, issuer, { + considerBuiltins: false + }); + if (resolveContext.fileDependencies) { + apiResolution = this.pnpApi.resolveToUnqualified("pnpapi", issuer, { + considerBuiltins: false + }); + } + } catch (error) { + if ( + error.code === "MODULE_NOT_FOUND" && + error.pnpCode === "UNDECLARED_DEPENDENCY" + ) { + // This is not a PnP managed dependency. + // Try to continue resolving with our alternatives + if (resolveContext.log) { + resolveContext.log(`request is not managed by the pnpapi`); + for (const line of error.message.split("\n").filter(Boolean)) + resolveContext.log(` ${line}`); + } + return callback(); + } + return callback(error); + } + + if (resolution === packageName) return callback(); + + if (apiResolution && resolveContext.fileDependencies) { + resolveContext.fileDependencies.add(apiResolution); } + + const obj = { + ...request, + path: resolution, + request: innerRequest, + ignoreSymlinks: true, + fullySpecified: request.fullySpecified && innerRequest !== "." + }; resolver.doResolve( target, - request, - null, + obj, + `resolved by pnp to ${resolution}`, resolveContext, (err, result) => { if (err) return callback(err); - if (result) return callback(null, (this.cache[cacheId] = result)); - callback(); + if (result) return callback(null, result); + // Skip alternatives + return callback(null, null); } ); }); @@ -138951,8 +139049,8 @@ module.exports = class UnsafeCachePlugin { /***/ }), -/***/ 81190: -/***/ (function(module) { +/***/ 7675: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; /* @@ -138962,210 +139060,488 @@ module.exports = class UnsafeCachePlugin { -/** @typedef {import("./Resolver")} Resolver */ -/** @typedef {import("./Resolver").ResolveStepHook} ResolveStepHook */ +const { AsyncSeriesBailHook, AsyncSeriesHook, SyncHook } = __webpack_require__(34718); +const createInnerContext = __webpack_require__(710); +const { parseIdentifier } = __webpack_require__(98623); +const { + normalize, + cachedJoin: join, + getType, + PathType +} = __webpack_require__(69821); + +/** @typedef {import("./ResolverFactory").ResolveOptions} ResolveOptions */ + +/** + * @typedef {Object} FileSystemStats + * @property {function(): boolean} isDirectory + * @property {function(): boolean} isFile + */ + +/** + * @typedef {Object} FileSystemDirent + * @property {Buffer | string} name + * @property {function(): boolean} isDirectory + * @property {function(): boolean} isFile + */ + +/** + * @typedef {Object} PossibleFileSystemError + * @property {string=} code + * @property {number=} errno + * @property {string=} path + * @property {string=} syscall + */ + +/** + * @template T + * @callback FileSystemCallback + * @param {PossibleFileSystemError & Error | null | undefined} err + * @param {T=} result + */ + +/** + * @typedef {Object} FileSystem + * @property {(function(string | number, FileSystemCallback): void) & function(string | number, object, FileSystemCallback): void} readFile + * @property {(function(string, string | number, FileSystemCallback): void) & function(string, string | number, string | number, FileSystemCallback): void=} open + * @property {(function(number, FileSystemCallback): void) & function(number, object, FileSystemCallback): void=} fstat + * @property {function(number, Buffer | Uint8Array, number, number, number, function(PossibleFileSystemError & Error | null | undefined, number=): void): void=} read + * @property {function(number, function(PossibleFileSystemError & Error | null | undefined): void): void=} close + * @property {(function(string, FileSystemCallback<(Buffer | string)[] | FileSystemDirent[]>): void) & function(string, object, FileSystemCallback<(Buffer | string)[] | FileSystemDirent[]>): void} readdir + * @property {((function(string, FileSystemCallback): void) & function(string, object, FileSystemCallback): void)=} readJson + * @property {(function(string, FileSystemCallback): void) & function(string, object, FileSystemCallback): void} readlink + * @property {(function(string, FileSystemCallback): void) & function(string, object, FileSystemCallback): void=} lstat + * @property {(function(string, FileSystemCallback): void) & function(string, object, FileSystemCallback): void} stat + */ + +/** + * @typedef {Object} SyncFileSystem + * @property {function(string | number, object=): Buffer | string} readFileSync + * @property {function(string, string | number, string | number=): number=} openSync + * @property {function(number, object=): FileSystemStats=} fstatSync + * @property {function(number, Buffer | Uint8Array, number, number, number): number=} readSync + * @property {function(number): void=} closeSync + * @property {function(string, object=): (Buffer | string)[] | FileSystemDirent[]} readdirSync + * @property {(function(string, object=): object)=} readJsonSync + * @property {function(string, object=): Buffer | string} readlinkSync + * @property {function(string, object=): FileSystemStats=} lstatSync + * @property {function(string, object=): FileSystemStats} statSync + */ + +/** + * @typedef {Object} ParsedIdentifier + * @property {string} request + * @property {string} query + * @property {string} fragment + * @property {boolean} directory + * @property {boolean} module + * @property {boolean} file + * @property {boolean} internal + */ + +/** + * @typedef {Object} BaseResolveRequest + * @property {string | false} path + * @property {string=} descriptionFilePath + * @property {string=} descriptionFileRoot + * @property {object=} descriptionFileData + * @property {string=} relativePath + * @property {boolean=} ignoreSymlinks + * @property {boolean=} fullySpecified + */ + +/** @typedef {BaseResolveRequest & Partial} ResolveRequest */ + +/** + * String with special formatting + * @typedef {string} StackEntry + */ + +/** @template T @typedef {{ add: (T) => void }} WriteOnlySet */ + +/** + * Resolve context + * @typedef {Object} ResolveContext + * @property {WriteOnlySet=} contextDependencies + * @property {WriteOnlySet=} fileDependencies files that was found on file system + * @property {WriteOnlySet=} missingDependencies dependencies that was not found on file system + * @property {Set=} stack set of hooks' calls. For instance, `resolve → parsedResolve → describedResolve`, + * @property {(function(string): void)=} log log function + */ + +/** @typedef {AsyncSeriesBailHook<[ResolveRequest, ResolveContext], ResolveRequest | null>} ResolveStepHook */ + +/** + * @param {string} str input string + * @returns {string} in camel case + */ +function toCamelCase(str) { + return str.replace(/-([a-z])/g, str => str.substr(1).toUpperCase()); +} + +class Resolver { + /** + * @param {ResolveStepHook} hook hook + * @param {ResolveRequest} request request + * @returns {StackEntry} stack entry + */ + static createStackEntry(hook, request) { + return ( + hook.name + + ": (" + + request.path + + ") " + + (request.request || "") + + (request.query || "") + + (request.fragment || "") + + (request.directory ? " directory" : "") + + (request.module ? " module" : "") + ); + } + + /** + * @param {FileSystem} fileSystem a filesystem + * @param {ResolveOptions} options options + */ + constructor(fileSystem, options) { + this.fileSystem = fileSystem; + this.options = options; + this.hooks = { + /** @type {SyncHook<[ResolveStepHook, ResolveRequest], void>} */ + resolveStep: new SyncHook(["hook", "request"], "resolveStep"), + /** @type {SyncHook<[ResolveRequest, Error]>} */ + noResolve: new SyncHook(["request", "error"], "noResolve"), + /** @type {ResolveStepHook} */ + resolve: new AsyncSeriesBailHook( + ["request", "resolveContext"], + "resolve" + ), + /** @type {AsyncSeriesHook<[ResolveRequest, ResolveContext]>} */ + result: new AsyncSeriesHook(["result", "resolveContext"], "result") + }; + } + + /** + * @param {string | ResolveStepHook} name hook name or hook itself + * @returns {ResolveStepHook} the hook + */ + ensureHook(name) { + if (typeof name !== "string") { + return name; + } + name = toCamelCase(name); + if (/^before/.test(name)) { + return /** @type {ResolveStepHook} */ (this.ensureHook( + name[6].toLowerCase() + name.substr(7) + ).withOptions({ + stage: -10 + })); + } + if (/^after/.test(name)) { + return /** @type {ResolveStepHook} */ (this.ensureHook( + name[5].toLowerCase() + name.substr(6) + ).withOptions({ + stage: 10 + })); + } + const hook = this.hooks[name]; + if (!hook) { + return (this.hooks[name] = new AsyncSeriesBailHook( + ["request", "resolveContext"], + name + )); + } + return hook; + } + + /** + * @param {string | ResolveStepHook} name hook name or hook itself + * @returns {ResolveStepHook} the hook + */ + getHook(name) { + if (typeof name !== "string") { + return name; + } + name = toCamelCase(name); + if (/^before/.test(name)) { + return /** @type {ResolveStepHook} */ (this.getHook( + name[6].toLowerCase() + name.substr(7) + ).withOptions({ + stage: -10 + })); + } + if (/^after/.test(name)) { + return /** @type {ResolveStepHook} */ (this.getHook( + name[5].toLowerCase() + name.substr(6) + ).withOptions({ + stage: 10 + })); + } + const hook = this.hooks[name]; + if (!hook) { + throw new Error(`Hook ${name} doesn't exist`); + } + return hook; + } -module.exports = class UseFilePlugin { /** - * @param {string | ResolveStepHook} source source - * @param {string} filename filename - * @param {string | ResolveStepHook} target target + * @param {object} context context information object + * @param {string} path context path + * @param {string} request request string + * @returns {string | false} result */ - constructor(source, filename, target) { - this.source = source; - this.filename = filename; - this.target = target; + resolveSync(context, path, request) { + /** @type {Error | null | undefined} */ + let err = undefined; + /** @type {string | false | undefined} */ + let result = undefined; + let sync = false; + this.resolve(context, path, request, {}, (e, r) => { + err = e; + result = r; + sync = true; + }); + if (!sync) { + throw new Error( + "Cannot 'resolveSync' because the fileSystem is not sync. Use 'resolve'!" + ); + } + if (err) throw err; + if (result === undefined) throw new Error("No result"); + return result; } /** - * @param {Resolver} resolver the resolver + * @param {object} context context information object + * @param {string} path context path + * @param {string} request request string + * @param {ResolveContext} resolveContext resolve context + * @param {function(Error | null, (string|false)=, ResolveRequest=): void} callback callback function * @returns {void} */ - apply(resolver) { - const target = resolver.ensureHook(this.target); - resolver - .getHook(this.source) - .tapAsync("UseFilePlugin", (request, resolveContext, callback) => { - const filePath = resolver.join(request.path, this.filename); - const obj = { - ...request, - path: filePath, - relativePath: - request.relativePath && - resolver.join(request.relativePath, this.filename) - }; - resolver.doResolve( - target, - obj, - "using path: " + filePath, - resolveContext, - callback - ); - }); - } -}; + resolve(context, path, request, resolveContext, callback) { + if (!context || typeof context !== "object") + return callback(new Error("context argument is not an object")); + if (typeof path !== "string") + return callback(new Error("path argument is not a string")); + if (typeof request !== "string") + return callback(new Error("path argument is not a string")); + if (!resolveContext) + return callback(new Error("resolveContext argument is not set")); + const obj = { + context: context, + path: path, + request: request + }; -/***/ }), + const message = `resolve '${request}' in '${path}'`; -/***/ 710: -/***/ (function(module) { + const finishResolved = result => { + return callback( + null, + result.path === false + ? false + : `${result.path.replace(/#/g, "\0#")}${ + result.query ? result.query.replace(/#/g, "\0#") : "" + }${result.fragment || ""}`, + result + ); + }; -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ + const finishWithoutResolve = log => { + /** + * @type {Error & {details?: string}} + */ + const error = new Error("Can't " + message); + error.details = log.join("\n"); + this.hooks.noResolve.call(obj, error); + return callback(error); + }; + if (resolveContext.log) { + // We need log anyway to capture it in case of an error + const parentLog = resolveContext.log; + const log = []; + return this.doResolve( + this.hooks.resolve, + obj, + message, + { + log: msg => { + parentLog(msg); + log.push(msg); + }, + fileDependencies: resolveContext.fileDependencies, + contextDependencies: resolveContext.contextDependencies, + missingDependencies: resolveContext.missingDependencies, + stack: resolveContext.stack + }, + (err, result) => { + if (err) return callback(err); + if (result) return finishResolved(result); -module.exports = function createInnerContext( - options, - message, - messageOptional -) { - let messageReported = false; - let innerLog = undefined; - if (options.log) { - if (message) { - innerLog = msg => { - if (!messageReported) { - options.log(message); - messageReported = true; + return finishWithoutResolve(log); } - options.log(" " + msg); - }; + ); } else { - innerLog = options.log; - } - } - const childContext = { - log: innerLog, - fileDependencies: options.fileDependencies, - contextDependencies: options.contextDependencies, - missingDependencies: options.missingDependencies, - stack: options.stack - }; - return childContext; -}; - + // Try to resolve assuming there is no error + // We don't log stuff in this case + return this.doResolve( + this.hooks.resolve, + obj, + message, + { + log: undefined, + fileDependencies: resolveContext.fileDependencies, + contextDependencies: resolveContext.contextDependencies, + missingDependencies: resolveContext.missingDependencies, + stack: resolveContext.stack + }, + (err, result) => { + if (err) return callback(err); -/***/ }), + if (result) return finishResolved(result); -/***/ 55426: -/***/ (function(module) { + // log is missing for the error details + // so we redo the resolving for the log info + // this is more expensive to the success case + // is assumed by default -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ + const log = []; + return this.doResolve( + this.hooks.resolve, + obj, + message, + { + log: msg => log.push(msg), + stack: resolveContext.stack + }, + (err, result) => { + if (err) return callback(err); + return finishWithoutResolve(log); + } + ); + } + ); + } + } -module.exports = function forEachBail(array, iterator, callback) { - if (array.length === 0) return callback(); + doResolve(hook, request, message, resolveContext, callback) { + const stackEntry = Resolver.createStackEntry(hook, request); - let i = 0; - const next = () => { - let loop = undefined; - iterator(array[i++], (err, result) => { - if (err || result !== undefined || i >= array.length) { - return callback(err, result); + let newStack; + if (resolveContext.stack) { + newStack = new Set(resolveContext.stack); + if (resolveContext.stack.has(stackEntry)) { + /** + * Prevent recursion + * @type {Error & {recursion?: boolean}} + */ + const recursionError = new Error( + "Recursion in resolving\nStack:\n " + + Array.from(newStack).join("\n ") + ); + recursionError.recursion = true; + if (resolveContext.log) + resolveContext.log("abort resolving because of recursion"); + return callback(recursionError); } - if (loop === false) while (next()); - loop = true; - }); - if (!loop) loop = false; - return loop; - }; - while (next()); -}; - + newStack.add(stackEntry); + } else { + newStack = new Set([stackEntry]); + } + this.hooks.resolveStep.call(hook, request); -/***/ }), + if (hook.isUsed()) { + const innerContext = createInnerContext( + { + log: resolveContext.log, + fileDependencies: resolveContext.fileDependencies, + contextDependencies: resolveContext.contextDependencies, + missingDependencies: resolveContext.missingDependencies, + stack: newStack + }, + message + ); + return hook.callAsync(request, innerContext, (err, result) => { + if (err) return callback(err); + if (result) return callback(null, result); + callback(); + }); + } else { + callback(); + } + } -/***/ 98361: -/***/ (function(module) { + /** + * @param {string} identifier identifier + * @returns {ParsedIdentifier} parsed identifier + */ + parse(identifier) { + const part = { + request: "", + query: "", + fragment: "", + module: false, + directory: false, + file: false, + internal: false + }; -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ + const parsedIdentifier = parseIdentifier(identifier); + if (!parsedIdentifier) return part; + [part.request, part.query, part.fragment] = parsedIdentifier; -module.exports = function getInnerRequest(resolver, request) { - if ( - typeof request.__innerRequest === "string" && - request.__innerRequest_request === request.request && - request.__innerRequest_relativePath === request.relativePath - ) - return request.__innerRequest; - let innerRequest; - if (request.request) { - innerRequest = request.request; - if (/^\.\.?(?:\/|$)/.test(innerRequest) && request.relativePath) { - innerRequest = resolver.join(request.relativePath, innerRequest); + if (part.request.length > 0) { + part.internal = this.isPrivate(identifier); + part.module = this.isModule(part.request); + part.directory = this.isDirectory(part.request); + if (part.directory) { + part.request = part.request.substr(0, part.request.length - 1); + } } - } else { - innerRequest = request.relativePath; - } - request.__innerRequest_request = request.request; - request.__innerRequest_relativePath = request.relativePath; - return (request.__innerRequest = innerRequest); -}; + return part; + } -/***/ }), - -/***/ 17117: -/***/ (function(module) { + isModule(path) { + return getType(path) === PathType.Normal; + } -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ + isPrivate(path) { + return getType(path) === PathType.Internal; + } + /** + * @param {string} path a path + * @returns {boolean} true, if the path is a directory path + */ + isDirectory(path) { + return path.endsWith("/"); + } + join(path, request) { + return join(path, request); + } -module.exports = function getPaths(path) { - const parts = path.split(/(.*?[\\/]+)/); - const paths = [path]; - const seqments = [parts[parts.length - 1]]; - let part = parts[parts.length - 1]; - path = path.substr(0, path.length - part.length - 1); - for (let i = parts.length - 2; i > 2; i -= 2) { - paths.push(path); - part = parts[i]; - path = path.substr(0, path.length - part.length) || "/"; - seqments.push(part.substr(0, part.length - 1)); + normalize(path) { + return normalize(path); } - part = parts[1]; - seqments.push(part); - paths.push(part); - return { - paths: paths, - seqments: seqments - }; -}; +} -module.exports.basename = function basename(path) { - const i = path.lastIndexOf("/"), - j = path.lastIndexOf("\\"); - const p = i < 0 ? j : j < 0 ? i : i < j ? j : i; - if (p < 0) return null; - const s = path.substr(p + 1); - return s; -}; +module.exports = Resolver; /***/ }), -/***/ 27480: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { +/***/ 1453: +/***/ (function(__unused_webpack_module, exports, __webpack_require__) { "use strict"; /* @@ -139175,845 +139551,1181 @@ module.exports.basename = function basename(path) { -const fs = __webpack_require__(82161); -const CachedInputFileSystem = __webpack_require__(26785); -const ResolverFactory = __webpack_require__(1453); +const versions = __webpack_require__(61765).versions; +const Resolver = __webpack_require__(7675); +const { getType, PathType } = __webpack_require__(69821); + +const SyncAsyncFileSystemDecorator = __webpack_require__(83908); + +const AliasFieldPlugin = __webpack_require__(94469); +const AliasPlugin = __webpack_require__(42673); +const AppendPlugin = __webpack_require__(72405); +const ConditionalPlugin = __webpack_require__(13134); +const DescriptionFilePlugin = __webpack_require__(85774); +const DirectoryExistsPlugin = __webpack_require__(61827); +const ExportsFieldPlugin = __webpack_require__(98169); +const FileExistsPlugin = __webpack_require__(9412); +const ImportsFieldPlugin = __webpack_require__(41031); +const JoinRequestPartPlugin = __webpack_require__(11399); +const JoinRequestPlugin = __webpack_require__(90522); +const MainFieldPlugin = __webpack_require__(18425); +const ModulesInHierachicDirectoriesPlugin = __webpack_require__(44964); +const ModulesInRootPlugin = __webpack_require__(39803); +const NextPlugin = __webpack_require__(76354); +const ParsePlugin = __webpack_require__(95204); +const PnpPlugin = __webpack_require__(63321); +const RestrictionsPlugin = __webpack_require__(94620); +const ResultPlugin = __webpack_require__(47775); +const RootsPlugin = __webpack_require__(8068); +const SelfReferencePlugin = __webpack_require__(24887); +const SymlinkPlugin = __webpack_require__(69476); +const TryNextPlugin = __webpack_require__(73771); +const UnsafeCachePlugin = __webpack_require__(57943); +const UseFilePlugin = __webpack_require__(81190); +/** @typedef {import("./AliasPlugin").AliasOption} AliasOptionEntry */ /** @typedef {import("./PnpPlugin").PnpApiImpl} PnpApi */ -/** @typedef {import("./Resolver")} Resolver */ /** @typedef {import("./Resolver").FileSystem} FileSystem */ -/** @typedef {import("./Resolver").ResolveContext} ResolveContext */ /** @typedef {import("./Resolver").ResolveRequest} ResolveRequest */ -/** @typedef {import("./ResolverFactory").Plugin} Plugin */ -/** @typedef {import("./ResolverFactory").UserResolveOptions} ResolveOptions */ - -const nodeFileSystem = new CachedInputFileSystem(fs, 4000); - -const nodeContext = { - environments: ["node+es3+es5+process+native"] -}; - -const asyncResolver = ResolverFactory.createResolver({ - conditionNames: ["node"], - extensions: [".js", ".json", ".node"], - fileSystem: nodeFileSystem -}); -function resolve(context, path, request, resolveContext, callback) { - if (typeof context === "string") { - callback = resolveContext; - resolveContext = request; - request = path; - path = context; - context = nodeContext; - } - if (typeof callback !== "function") { - callback = resolveContext; - } - asyncResolver.resolve(context, path, request, resolveContext, callback); -} - -const syncResolver = ResolverFactory.createResolver({ - conditionNames: ["node"], - extensions: [".js", ".json", ".node"], - useSyncFileSystemCalls: true, - fileSystem: nodeFileSystem -}); -function resolveSync(context, path, request) { - if (typeof context === "string") { - request = path; - path = context; - context = nodeContext; - } - return syncResolver.resolveSync(context, path, request); -} +/** @typedef {import("./Resolver").SyncFileSystem} SyncFileSystem */ -function create(options) { - options = { - fileSystem: nodeFileSystem, - ...options - }; - const resolver = ResolverFactory.createResolver(options); - return function (context, path, request, resolveContext, callback) { - if (typeof context === "string") { - callback = resolveContext; - resolveContext = request; - request = path; - path = context; - context = nodeContext; - } - if (typeof callback !== "function") { - callback = resolveContext; - } - resolver.resolve(context, path, request, resolveContext, callback); - }; -} +/** @typedef {string|string[]|false} AliasOptionNewRequest */ +/** @typedef {{[k: string]: AliasOptionNewRequest}} AliasOptions */ +/** @typedef {{apply: function(Resolver): void} | function(this: Resolver, Resolver): void} Plugin */ -function createSync(options) { - options = { - useSyncFileSystemCalls: true, - fileSystem: nodeFileSystem, - ...options - }; - const resolver = ResolverFactory.createResolver(options); - return function (context, path, request) { - if (typeof context === "string") { - request = path; - path = context; - context = nodeContext; - } - return resolver.resolveSync(context, path, request); - }; -} +/** + * @typedef {Object} UserResolveOptions + * @property {(AliasOptions | AliasOptionEntry[])=} alias A list of module alias configurations or an object which maps key to value + * @property {(AliasOptions | AliasOptionEntry[])=} fallback A list of module alias configurations or an object which maps key to value, applied only after modules option + * @property {(string | string[])[]=} aliasFields A list of alias fields in description files + * @property {(function(ResolveRequest): boolean)=} cachePredicate A function which decides whether a request should be cached or not. An object is passed with at least `path` and `request` properties. + * @property {boolean=} cacheWithContext Whether or not the unsafeCache should include request context as part of the cache key. + * @property {string[]=} descriptionFiles A list of description files to read from + * @property {string[]=} conditionNames A list of exports field condition names. + * @property {boolean=} enforceExtension Enforce that a extension from extensions must be used + * @property {(string | string[])[]=} exportsFields A list of exports fields in description files + * @property {(string | string[])[]=} importsFields A list of imports fields in description files + * @property {string[]=} extensions A list of extensions which should be tried for files + * @property {FileSystem} fileSystem The file system which should be used + * @property {(object | boolean)=} unsafeCache Use this cache object to unsafely cache the successful requests + * @property {boolean=} symlinks Resolve symlinks to their symlinked location + * @property {Resolver=} resolver A prepared Resolver to which the plugins are attached + * @property {string[] | string=} modules A list of directories to resolve modules from, can be absolute path or folder name + * @property {(string | string[] | {name: string | string[], forceRelative: boolean})[]=} mainFields A list of main fields in description files + * @property {string[]=} mainFiles A list of main files in directories + * @property {Plugin[]=} plugins A list of additional resolve plugins which should be applied + * @property {PnpApi | null=} pnpApi A PnP API that should be used - null is "never", undefined is "auto" + * @property {string[]=} roots A list of root paths + * @property {boolean=} fullySpecified The request is already fully specified and no extensions or directories are resolved for it + * @property {boolean=} resolveToContext Resolve to a context instead of a file + * @property {(string|RegExp)[]=} restrictions A list of resolve restrictions + * @property {boolean=} useSyncFileSystemCalls Use only the sync constiants of the file system calls + * @property {boolean=} preferRelative Prefer to resolve module requests as relative requests before falling back to modules + * @property {boolean=} preferAbsolute Prefer to resolve server-relative urls as absolute paths before falling back to resolve in roots + */ /** - * @template A - * @template B - * @param {A} obj input a - * @param {B} exports input b - * @returns {A & B} merged + * @typedef {Object} ResolveOptions + * @property {AliasOptionEntry[]} alias + * @property {AliasOptionEntry[]} fallback + * @property {Set} aliasFields + * @property {(function(ResolveRequest): boolean)} cachePredicate + * @property {boolean} cacheWithContext + * @property {Set} conditionNames A list of exports field condition names. + * @property {string[]} descriptionFiles + * @property {boolean} enforceExtension + * @property {Set} exportsFields + * @property {Set} importsFields + * @property {Set} extensions + * @property {FileSystem} fileSystem + * @property {object | false} unsafeCache + * @property {boolean} symlinks + * @property {Resolver=} resolver + * @property {Array} modules + * @property {{name: string[], forceRelative: boolean}[]} mainFields + * @property {Set} mainFiles + * @property {Plugin[]} plugins + * @property {PnpApi | null} pnpApi + * @property {Set} roots + * @property {boolean} fullySpecified + * @property {boolean} resolveToContext + * @property {Set} restrictions + * @property {boolean} preferRelative + * @property {boolean} preferAbsolute */ -const mergeExports = (obj, exports) => { - const descriptors = Object.getOwnPropertyDescriptors(exports); - Object.defineProperties(obj, descriptors); - return /** @type {A & B} */ (Object.freeze(obj)); -}; -module.exports = mergeExports(resolve, { - get sync() { - return resolveSync; - }, - create: mergeExports(create, { - get sync() { - return createSync; - } - }), - ResolverFactory, - CachedInputFileSystem, - get CloneBasenamePlugin() { - return __webpack_require__(36154); - }, - get LogInfoPlugin() { - return __webpack_require__(50098); - }, - get forEachBail() { - return __webpack_require__(55426); +/** + * @param {PnpApi | null=} option option + * @returns {PnpApi | null} processed option + */ +function processPnpApiOption(option) { + if ( + option === undefined && + /** @type {NodeJS.ProcessVersions & {pnp: string}} */ versions.pnp + ) { + // @ts-ignore + return __webpack_require__(97289); // eslint-disable-line node/no-missing-require } -}); - -/***/ }), - -/***/ 94340: -/***/ (function(module) { - -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Ivan Kopeykin @vankop -*/ + return option || null; +} +/** + * @param {AliasOptions | AliasOptionEntry[] | undefined} alias alias + * @returns {AliasOptionEntry[]} normalized aliases + */ +function normalizeAlias(alias) { + return typeof alias === "object" && !Array.isArray(alias) && alias !== null + ? Object.keys(alias).map(key => { + /** @type {AliasOptionEntry} */ + const obj = { name: key, onlyModule: false, alias: alias[key] }; + if (/\$$/.test(key)) { + obj.onlyModule = true; + obj.name = key.substr(0, key.length - 1); + } -/** @typedef {string|(string|ConditionalMapping)[]} DirectMapping */ -/** @typedef {{[k: string]: MappingValue}} ConditionalMapping */ -/** @typedef {ConditionalMapping|DirectMapping|null} MappingValue */ -/** @typedef {Record|ConditionalMapping|DirectMapping} ExportsField */ -/** @typedef {Record} ImportsField */ + return obj; + }) + : /** @type {Array} */ (alias) || []; +} /** - * @typedef {Object} PathTreeNode - * @property {Map|null} children - * @property {MappingValue} folder - * @property {Map|null} wildcards - * @property {Map} files + * @param {UserResolveOptions} options input options + * @returns {ResolveOptions} output options */ +function createOptions(options) { + const mainFieldsSet = new Set(options.mainFields || ["main"]); + const mainFields = []; -/** - * Processing exports/imports field - * @callback FieldProcessor - * @param {string} request request - * @param {Set} conditionNames condition names - * @returns {string[]} resolved paths - */ + for (const item of mainFieldsSet) { + if (typeof item === "string") { + mainFields.push({ + name: [item], + forceRelative: true + }); + } else if (Array.isArray(item)) { + mainFields.push({ + name: item, + forceRelative: true + }); + } else { + mainFields.push({ + name: Array.isArray(item.name) ? item.name : [item.name], + forceRelative: item.forceRelative + }); + } + } -/* -Example exports field: -{ - ".": "./main.js", - "./feature": { - "browser": "./feature-browser.js", - "default": "./feature.js" - } + return { + alias: normalizeAlias(options.alias), + fallback: normalizeAlias(options.fallback), + aliasFields: new Set(options.aliasFields), + cachePredicate: + options.cachePredicate || + function () { + return true; + }, + cacheWithContext: + typeof options.cacheWithContext !== "undefined" + ? options.cacheWithContext + : true, + exportsFields: new Set(options.exportsFields || ["exports"]), + importsFields: new Set(options.importsFields || ["imports"]), + conditionNames: new Set(options.conditionNames), + descriptionFiles: Array.from( + new Set(options.descriptionFiles || ["package.json"]) + ), + enforceExtension: + options.enforceExtension === undefined + ? options.extensions && options.extensions.includes("") + ? true + : false + : options.enforceExtension, + extensions: new Set(options.extensions || [".js", ".json", ".node"]), + fileSystem: options.useSyncFileSystemCalls + ? new SyncAsyncFileSystemDecorator( + /** @type {SyncFileSystem} */ ( + /** @type {unknown} */ (options.fileSystem) + ) + ) + : options.fileSystem, + unsafeCache: + options.unsafeCache && typeof options.unsafeCache !== "object" + ? {} + : options.unsafeCache || false, + symlinks: typeof options.symlinks !== "undefined" ? options.symlinks : true, + resolver: options.resolver, + modules: mergeFilteredToArray( + Array.isArray(options.modules) + ? options.modules + : options.modules + ? [options.modules] + : ["node_modules"], + item => { + const type = getType(item); + return type === PathType.Normal || type === PathType.Relative; + } + ), + mainFields, + mainFiles: new Set(options.mainFiles || ["index"]), + plugins: options.plugins || [], + pnpApi: processPnpApiOption(options.pnpApi), + roots: new Set(options.roots || undefined), + fullySpecified: options.fullySpecified || false, + resolveToContext: options.resolveToContext || false, + preferRelative: options.preferRelative || false, + preferAbsolute: options.preferAbsolute || false, + restrictions: new Set(options.restrictions) + }; } -Terminology: -Enhanced-resolve name keys ("." and "./feature") as exports field keys. +/** + * @param {UserResolveOptions} options resolve options + * @returns {Resolver} created resolver + */ +exports.createResolver = function (options) { + const normalizedOptions = createOptions(options); -If value is string or string[], mapping is called as a direct mapping -and value called as a direct export. + const { + alias, + fallback, + aliasFields, + cachePredicate, + cacheWithContext, + conditionNames, + descriptionFiles, + enforceExtension, + exportsFields, + importsFields, + extensions, + fileSystem, + fullySpecified, + mainFields, + mainFiles, + modules, + plugins: userPlugins, + pnpApi, + resolveToContext, + preferRelative, + preferAbsolute, + symlinks, + unsafeCache, + resolver: customResolver, + restrictions, + roots + } = normalizedOptions; -If value is key-value object, mapping is called as a conditional mapping -and value called as a conditional export. + const plugins = userPlugins.slice(); -Key in conditional mapping is called condition name. + const resolver = customResolver + ? customResolver + : new Resolver(fileSystem, normalizedOptions); -Conditional mapping nested in another conditional mapping is called nested mapping. + //// pipeline //// ----------- + resolver.ensureHook("resolve"); + resolver.ensureHook("internalResolve"); + resolver.ensureHook("newInteralResolve"); + resolver.ensureHook("parsedResolve"); + resolver.ensureHook("describedResolve"); + resolver.ensureHook("internal"); + resolver.ensureHook("rawModule"); + resolver.ensureHook("module"); + resolver.ensureHook("resolveAsModule"); + resolver.ensureHook("undescribedResolveInPackage"); + resolver.ensureHook("resolveInPackage"); + resolver.ensureHook("resolveInExistingDirectory"); + resolver.ensureHook("relative"); + resolver.ensureHook("describedRelative"); + resolver.ensureHook("directory"); + resolver.ensureHook("undescribedExistingDirectory"); + resolver.ensureHook("existingDirectory"); + resolver.ensureHook("undescribedRawFile"); + resolver.ensureHook("rawFile"); + resolver.ensureHook("file"); + resolver.ensureHook("finalFile"); + resolver.ensureHook("existingFile"); + resolver.ensureHook("resolved"); -Example imports field: -{ - "#a": "./main.js", - "#moment": { - "browser": "./moment/index.js", - "default": "moment" - }, - "#moment/": { - "browser": "./moment/", - "default": "moment/" - } -} -Terminology: + // resolve + for (const { source, resolveOptions } of [ + { source: "resolve", resolveOptions: { fullySpecified } }, + { source: "internal-resolve", resolveOptions: { fullySpecified: false } } + ]) { + if (unsafeCache) { + plugins.push( + new UnsafeCachePlugin( + source, + cachePredicate, + unsafeCache, + cacheWithContext, + `new-${source}` + ) + ); + plugins.push( + new ParsePlugin(`new-${source}`, resolveOptions, "parsed-resolve") + ); + } else { + plugins.push(new ParsePlugin(source, resolveOptions, "parsed-resolve")); + } + } -Enhanced-resolve name keys ("#a" and "#moment/", "#moment") as imports field keys. + // parsed-resolve + plugins.push( + new DescriptionFilePlugin( + "parsed-resolve", + descriptionFiles, + false, + "described-resolve" + ) + ); + plugins.push(new NextPlugin("after-parsed-resolve", "described-resolve")); -If value is string or string[], mapping is called as a direct mapping -and value called as a direct export. + // described-resolve + plugins.push(new NextPlugin("described-resolve", "normal-resolve")); + if (fallback.length > 0) { + plugins.push( + new AliasPlugin("described-resolve", fallback, "internal-resolve") + ); + } -If value is key-value object, mapping is called as a conditional mapping -and value called as a conditional export. + // normal-resolve + if (alias.length > 0) + plugins.push(new AliasPlugin("normal-resolve", alias, "internal-resolve")); + aliasFields.forEach(item => { + plugins.push( + new AliasFieldPlugin("normal-resolve", item, "internal-resolve") + ); + }); + if (preferRelative) { + plugins.push(new JoinRequestPlugin("after-normal-resolve", "relative")); + } + plugins.push( + new ConditionalPlugin( + "after-normal-resolve", + { module: true }, + "resolve as module", + false, + "raw-module" + ) + ); + plugins.push( + new ConditionalPlugin( + "after-normal-resolve", + { internal: true }, + "resolve as internal import", + false, + "internal" + ) + ); + if (preferAbsolute) { + plugins.push(new JoinRequestPlugin("after-normal-resolve", "relative")); + } + if (roots.size > 0) { + plugins.push(new RootsPlugin("after-normal-resolve", roots, "relative")); + } + if (!preferRelative && !preferAbsolute) { + plugins.push(new JoinRequestPlugin("after-normal-resolve", "relative")); + } -Key in conditional mapping is called condition name. + // internal + importsFields.forEach(importsField => { + plugins.push( + new ImportsFieldPlugin( + "internal", + conditionNames, + importsField, + "relative", + "internal-resolve" + ) + ); + }); -Conditional mapping nested in another conditional mapping is called nested mapping. + // raw-module + exportsFields.forEach(exportsField => { + plugins.push( + new SelfReferencePlugin("raw-module", exportsField, "resolve-as-module") + ); + }); + modules.forEach(item => { + if (Array.isArray(item)) { + if (item.includes("node_modules") && pnpApi) { + plugins.push( + new ModulesInHierachicDirectoriesPlugin( + "raw-module", + item.filter(i => i !== "node_modules"), + "module" + ) + ); + plugins.push( + new PnpPlugin("raw-module", pnpApi, "undescribed-resolve-in-package") + ); + } else { + plugins.push( + new ModulesInHierachicDirectoriesPlugin("raw-module", item, "module") + ); + } + } else { + plugins.push(new ModulesInRootPlugin("raw-module", item, "module")); + } + }); -*/ + // module + plugins.push(new JoinRequestPartPlugin("module", "resolve-as-module")); -const slashCode = "/".charCodeAt(0); -const dotCode = ".".charCodeAt(0); -const hashCode = "#".charCodeAt(0); + // resolve-as-module + if (!resolveToContext) { + plugins.push( + new ConditionalPlugin( + "resolve-as-module", + { directory: false, request: "." }, + "single file module", + true, + "undescribed-raw-file" + ) + ); + } + plugins.push( + new DirectoryExistsPlugin( + "resolve-as-module", + "undescribed-resolve-in-package" + ) + ); -/** - * @param {ExportsField} exportsField the exports field - * @returns {FieldProcessor} process callback - */ -module.exports.processExportsField = function processExportsField( - exportsField -) { - return createFieldProcessor( - buildExportsFieldPathTree(exportsField), - assertExportsFieldRequest, - assertExportTarget + // undescribed-resolve-in-package + plugins.push( + new DescriptionFilePlugin( + "undescribed-resolve-in-package", + descriptionFiles, + false, + "resolve-in-package" + ) + ); + plugins.push( + new NextPlugin("after-undescribed-resolve-in-package", "resolve-in-package") ); -}; -/** - * @param {ImportsField} importsField the exports field - * @returns {FieldProcessor} process callback - */ -module.exports.processImportsField = function processImportsField( - importsField -) { - return createFieldProcessor( - buildImportsFieldPathTree(importsField), - assertImportsFieldRequest, - assertImportTarget + // resolve-in-package + exportsFields.forEach(exportsField => { + plugins.push( + new ExportsFieldPlugin( + "resolve-in-package", + conditionNames, + exportsField, + "relative" + ) + ); + }); + plugins.push( + new NextPlugin("resolve-in-package", "resolve-in-existing-directory") ); -}; -/** - * @param {PathTreeNode} treeRoot root - * @param {(s: string) => string} assertRequest assertRequest - * @param {(s: string, f: boolean) => void} assertTarget assertTarget - * @returns {FieldProcessor} field processor - */ -function createFieldProcessor(treeRoot, assertRequest, assertTarget) { - return function fieldProcessor(request, conditionNames) { - request = assertRequest(request); + // resolve-in-existing-directory + plugins.push( + new JoinRequestPlugin("resolve-in-existing-directory", "relative") + ); - const match = findMatch(request, treeRoot); + // relative + plugins.push( + new DescriptionFilePlugin( + "relative", + descriptionFiles, + true, + "described-relative" + ) + ); + plugins.push(new NextPlugin("after-relative", "described-relative")); - if (match === null) return []; + // described-relative + if (resolveToContext) { + plugins.push(new NextPlugin("described-relative", "directory")); + } else { + plugins.push( + new ConditionalPlugin( + "described-relative", + { directory: false }, + null, + true, + "raw-file" + ) + ); + plugins.push( + new ConditionalPlugin( + "described-relative", + { fullySpecified: false }, + "as directory", + true, + "directory" + ) + ); + } - const [mapping, remainRequestIndex] = match; + // directory + plugins.push( + new DirectoryExistsPlugin("directory", "undescribed-existing-directory") + ); - /** @type {DirectMapping|null} */ - let direct = null; + if (resolveToContext) { + // undescribed-existing-directory + plugins.push(new NextPlugin("undescribed-existing-directory", "resolved")); + } else { + // undescribed-existing-directory + plugins.push( + new DescriptionFilePlugin( + "undescribed-existing-directory", + descriptionFiles, + false, + "existing-directory" + ) + ); + mainFiles.forEach(item => { + plugins.push( + new UseFilePlugin( + "undescribed-existing-directory", + item, + "undescribed-raw-file" + ) + ); + }); - if (isConditionalMapping(mapping)) { - direct = conditionalMapping( - /** @type {ConditionalMapping} */ (mapping), - conditionNames + // described-existing-directory + mainFields.forEach(item => { + plugins.push( + new MainFieldPlugin( + "existing-directory", + item, + "resolve-in-existing-directory" + ) + ); + }); + mainFiles.forEach(item => { + plugins.push( + new UseFilePlugin("existing-directory", item, "undescribed-raw-file") ); + }); - // matching not found - if (direct === null) return []; - } else { - direct = /** @type {DirectMapping} */ (mapping); + // undescribed-raw-file + plugins.push( + new DescriptionFilePlugin( + "undescribed-raw-file", + descriptionFiles, + true, + "raw-file" + ) + ); + plugins.push(new NextPlugin("after-undescribed-raw-file", "raw-file")); + + // raw-file + plugins.push( + new ConditionalPlugin( + "raw-file", + { fullySpecified: true }, + null, + false, + "file" + ) + ); + if (!enforceExtension) { + plugins.push(new TryNextPlugin("raw-file", "no extension", "file")); } + extensions.forEach(item => { + plugins.push(new AppendPlugin("raw-file", item, "file")); + }); - const remainingRequest = - remainRequestIndex === request.length + 1 - ? undefined - : remainRequestIndex < 0 - ? request.slice(-remainRequestIndex - 1) - : request.slice(remainRequestIndex); + // file + if (alias.length > 0) + plugins.push(new AliasPlugin("file", alias, "internal-resolve")); + aliasFields.forEach(item => { + plugins.push(new AliasFieldPlugin("file", item, "internal-resolve")); + }); + plugins.push(new NextPlugin("file", "final-file")); - return directMapping( - remainingRequest, - remainRequestIndex < 0, - direct, - conditionNames, - assertTarget - ); - }; -} + // final-file + plugins.push(new FileExistsPlugin("final-file", "existing-file")); -/** - * @param {string} request request - * @returns {string} updated request - */ -function assertExportsFieldRequest(request) { - if (request.charCodeAt(0) !== dotCode) { - throw new Error('Request should be relative path and start with "."'); - } - if (request.length === 1) return ""; - if (request.charCodeAt(1) !== slashCode) { - throw new Error('Request should be relative path and start with "./"'); + // existing-file + if (symlinks) + plugins.push(new SymlinkPlugin("existing-file", "existing-file")); + plugins.push(new NextPlugin("existing-file", "resolved")); } - if (request.charCodeAt(request.length - 1) === slashCode) { - throw new Error("Only requesting file allowed"); + + // resolved + if (restrictions.size > 0) { + plugins.push(new RestrictionsPlugin(resolver.hooks.resolved, restrictions)); } + plugins.push(new ResultPlugin(resolver.hooks.resolved)); - return request.slice(2); -} + //// RESOLVER //// -/** - * @param {string} request request - * @returns {string} updated request - */ -function assertImportsFieldRequest(request) { - if (request.charCodeAt(0) !== hashCode) { - throw new Error('Request should start with "#"'); - } - if (request.length === 1) { - throw new Error("Request should have at least 2 characters"); - } - if (request.charCodeAt(1) === slashCode) { - throw new Error('Request should not start with "#/"'); - } - if (request.charCodeAt(request.length - 1) === slashCode) { - throw new Error("Only requesting file allowed"); + for (const plugin of plugins) { + if (typeof plugin === "function") { + plugin.call(resolver, resolver); + } else { + plugin.apply(resolver); + } } - return request.slice(1); -} + return resolver; +}; /** - * @param {string} exp export target - * @param {boolean} expectFolder is folder expected + * Merging filtered elements + * @param {string[]} array source array + * @param {function(string): boolean} filter predicate + * @returns {Array} merge result */ -function assertExportTarget(exp, expectFolder) { - if ( - exp.charCodeAt(0) === slashCode || - (exp.charCodeAt(0) === dotCode && exp.charCodeAt(1) !== slashCode) - ) { - throw new Error( - `Export should be relative path and start with "./", got ${JSON.stringify( - exp - )}.` - ); - } - - const isFolder = exp.charCodeAt(exp.length - 1) === slashCode; +function mergeFilteredToArray(array, filter) { + /** @type {Array} */ + const result = []; + const set = new Set(array); - if (isFolder !== expectFolder) { - throw new Error( - expectFolder - ? `Expecting folder to folder mapping. ${JSON.stringify( - exp - )} should end with "/"` - : `Expecting file to file mapping. ${JSON.stringify( - exp - )} should not end with "/"` - ); + for (const item of set) { + if (filter(item)) { + const lastElement = + result.length > 0 ? result[result.length - 1] : undefined; + if (Array.isArray(lastElement)) { + lastElement.push(item); + } else { + result.push([item]); + } + } else { + result.push(item); + } } + + return result; } -/** - * @param {string} imp import target - * @param {boolean} expectFolder is folder expected - */ -function assertImportTarget(imp, expectFolder) { - const isFolder = imp.charCodeAt(imp.length - 1) === slashCode; - if (isFolder !== expectFolder) { - throw new Error( - expectFolder - ? `Expecting folder to folder mapping. ${JSON.stringify( - imp - )} should end with "/"` - : `Expecting file to file mapping. ${JSON.stringify( - imp - )} should not end with "/"` - ); - } -} +/***/ }), -/** - * Trying to match request to field - * @param {string} request request - * @param {PathTreeNode} treeRoot path tree root - * @returns {[MappingValue, number]|null} match or null, number is negative and one less when it's a folder mapping, number is request.length + 1 for direct mappings - */ -function findMatch(request, treeRoot) { - if (request.length === 0) { - const value = treeRoot.files.get(""); +/***/ 94620: +/***/ (function(module) { - return value ? [value, 1] : null; - } +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Ivan Kopeykin @vankop +*/ - if ( - treeRoot.children === null && - treeRoot.folder === null && - treeRoot.wildcards === null - ) { - const value = treeRoot.files.get(request); - return value ? [value, request.length + 1] : null; - } - let node = treeRoot; - let lastNonSlashIndex = 0; - let slashIndex = request.indexOf("/", 0); +/** @typedef {import("./Resolver")} Resolver */ +/** @typedef {import("./Resolver").ResolveStepHook} ResolveStepHook */ - /** @type {[MappingValue, number]|null} */ - let lastFolderMatch = null; +const slashCode = "/".charCodeAt(0); +const backslashCode = "\\".charCodeAt(0); - const applyFolderMapping = () => { - const folderMapping = node.folder; - if (folderMapping) { - if (lastFolderMatch) { - lastFolderMatch[0] = folderMapping; - lastFolderMatch[1] = -lastNonSlashIndex - 1; - } else { - lastFolderMatch = [folderMapping, -lastNonSlashIndex - 1]; - } - } - }; +const isInside = (path, parent) => { + if (!path.startsWith(parent)) return false; + if (path.length === parent.length) return true; + const charCode = path.charCodeAt(parent.length); + return charCode === slashCode || charCode === backslashCode; +}; - const applyWildcardMappings = (wildcardMappings, remainingRequest) => { - if (wildcardMappings) { - for (const [key, target] of wildcardMappings) { - if (remainingRequest.startsWith(key)) { - if (!lastFolderMatch) { - lastFolderMatch = [target, lastNonSlashIndex + key.length]; - } else if (lastFolderMatch[1] < lastNonSlashIndex + key.length) { - lastFolderMatch[0] = target; - lastFolderMatch[1] = lastNonSlashIndex + key.length; +module.exports = class RestrictionsPlugin { + /** + * @param {string | ResolveStepHook} source source + * @param {Set} restrictions restrictions + */ + constructor(source, restrictions) { + this.source = source; + this.restrictions = restrictions; + } + + /** + * @param {Resolver} resolver the resolver + * @returns {void} + */ + apply(resolver) { + resolver + .getHook(this.source) + .tapAsync("RestrictionsPlugin", (request, resolveContext, callback) => { + if (typeof request.path === "string") { + const path = request.path; + for (const rule of this.restrictions) { + if (typeof rule === "string") { + if (!isInside(path, rule)) { + if (resolveContext.log) { + resolveContext.log( + `${path} is not inside of the restriction ${rule}` + ); + } + return callback(null, null); + } + } else if (!rule.test(path)) { + if (resolveContext.log) { + resolveContext.log( + `${path} doesn't match the restriction ${rule}` + ); + } + return callback(null, null); + } } } - } - } - }; - while (slashIndex !== -1) { - applyFolderMapping(); + callback(); + }); + } +}; - const wildcardMappings = node.wildcards; - if (!wildcardMappings && node.children === null) return lastFolderMatch; +/***/ }), - const folder = request.slice(lastNonSlashIndex, slashIndex); +/***/ 47775: +/***/ (function(module) { - applyWildcardMappings(wildcardMappings, folder); +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ - if (node.children === null) return lastFolderMatch; - const newNode = node.children.get(folder); - if (!newNode) { - return lastFolderMatch; - } +/** @typedef {import("./Resolver")} Resolver */ +/** @typedef {import("./Resolver").ResolveStepHook} ResolveStepHook */ - node = newNode; - lastNonSlashIndex = slashIndex + 1; - slashIndex = request.indexOf("/", lastNonSlashIndex); +module.exports = class ResultPlugin { + /** + * @param {ResolveStepHook} source source + */ + constructor(source) { + this.source = source; } - const remainingRequest = - lastNonSlashIndex > 0 ? request.slice(lastNonSlashIndex) : request; - - const value = node.files.get(remainingRequest); - - if (value) { - return [value, request.length + 1]; + /** + * @param {Resolver} resolver the resolver + * @returns {void} + */ + apply(resolver) { + this.source.tapAsync( + "ResultPlugin", + (request, resolverContext, callback) => { + const obj = { ...request }; + if (resolverContext.log) + resolverContext.log("reporting result " + obj.path); + resolver.hooks.result.callAsync(obj, resolverContext, err => { + if (err) return callback(err); + callback(null, obj); + }); + } + ); } +}; - applyFolderMapping(); - - applyWildcardMappings(node.wildcards, remainingRequest); - - return lastFolderMatch; -} -/** - * @param {ConditionalMapping|DirectMapping|null} mapping mapping - * @returns {boolean} is conditional mapping - */ -function isConditionalMapping(mapping) { - return ( - mapping !== null && typeof mapping === "object" && !Array.isArray(mapping) - ); -} +/***/ }), -/** - * @param {string|undefined} remainingRequest remaining request when folder mapping, undefined for file mappings - * @param {boolean} subpathMapping true, for subpath mappings - * @param {DirectMapping|null} mappingTarget direct export - * @param {Set} conditionNames condition names - * @param {(d: string, f: boolean) => void} assert asserting direct value - * @returns {string[]} mapping result - */ -function directMapping( - remainingRequest, - subpathMapping, - mappingTarget, - conditionNames, - assert -) { - if (mappingTarget === null) return []; +/***/ 8068: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - if (typeof mappingTarget === "string") { - return [ - targetMapping(remainingRequest, subpathMapping, mappingTarget, assert) - ]; - } +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Ivan Kopeykin @vankop +*/ - const targets = []; - for (const exp of mappingTarget) { - if (typeof exp === "string") { - targets.push( - targetMapping(remainingRequest, subpathMapping, exp, assert) - ); - continue; - } - const mapping = conditionalMapping(exp, conditionNames); - if (!mapping) continue; - const innerExports = directMapping( - remainingRequest, - subpathMapping, - mapping, - conditionNames, - assert - ); - for (const innerExport of innerExports) { - targets.push(innerExport); - } - } +const forEachBail = __webpack_require__(55426); - return targets; -} +/** @typedef {import("./Resolver")} Resolver */ +/** @typedef {import("./Resolver").ResolveStepHook} ResolveStepHook */ -/** - * @param {string|undefined} remainingRequest remaining request when folder mapping, undefined for file mappings - * @param {boolean} subpathMapping true, for subpath mappings - * @param {string} mappingTarget direct export - * @param {(d: string, f: boolean) => void} assert asserting direct value - * @returns {string} mapping result - */ -function targetMapping( - remainingRequest, - subpathMapping, - mappingTarget, - assert -) { - if (remainingRequest === undefined) { - assert(mappingTarget, false); - return mappingTarget; +class RootsPlugin { + /** + * @param {string | ResolveStepHook} source source hook + * @param {Set} roots roots + * @param {string | ResolveStepHook} target target hook + */ + constructor(source, roots, target) { + this.roots = Array.from(roots); + this.source = source; + this.target = target; } - if (subpathMapping) { - assert(mappingTarget, true); - return mappingTarget + remainingRequest; + + /** + * @param {Resolver} resolver the resolver + * @returns {void} + */ + apply(resolver) { + const target = resolver.ensureHook(this.target); + + resolver + .getHook(this.source) + .tapAsync("RootsPlugin", (request, resolveContext, callback) => { + const req = request.request; + if (!req) return callback(); + if (!req.startsWith("/")) return callback(); + + forEachBail( + this.roots, + (root, callback) => { + const path = resolver.join(root, req.slice(1)); + const obj = { + ...request, + path, + relativePath: request.relativePath && path + }; + resolver.doResolve( + target, + obj, + `root path ${root}`, + resolveContext, + callback + ); + }, + callback + ); + }); } - assert(mappingTarget, false); - return mappingTarget.replace(/\*/g, remainingRequest.replace(/\$/g, "$$")); } -/** - * @param {ConditionalMapping} conditionalMapping_ conditional mapping - * @param {Set} conditionNames condition names - * @returns {DirectMapping|null} direct mapping if found - */ -function conditionalMapping(conditionalMapping_, conditionNames) { - /** @type {[ConditionalMapping, string[], number][]} */ - let lookup = [[conditionalMapping_, Object.keys(conditionalMapping_), 0]]; +module.exports = RootsPlugin; - loop: while (lookup.length > 0) { - const [mapping, conditions, j] = lookup[lookup.length - 1]; - const last = conditions.length - 1; - for (let i = j; i < conditions.length; i++) { - const condition = conditions[i]; +/***/ }), - // assert default. Could be last only - if (i !== last) { - if (condition === "default") { - throw new Error("Default condition should be last one"); - } - } else if (condition === "default") { - const innerMapping = mapping[condition]; - // is nested - if (isConditionalMapping(innerMapping)) { - const conditionalMapping = /** @type {ConditionalMapping} */ (innerMapping); - lookup[lookup.length - 1][2] = i + 1; - lookup.push([conditionalMapping, Object.keys(conditionalMapping), 0]); - continue loop; - } +/***/ 24887: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - return /** @type {DirectMapping} */ (innerMapping); - } +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ - if (conditionNames.has(condition)) { - const innerMapping = mapping[condition]; - // is nested - if (isConditionalMapping(innerMapping)) { - const conditionalMapping = /** @type {ConditionalMapping} */ (innerMapping); - lookup[lookup.length - 1][2] = i + 1; - lookup.push([conditionalMapping, Object.keys(conditionalMapping), 0]); - continue loop; - } - return /** @type {DirectMapping} */ (innerMapping); - } - } - lookup.pop(); - } +const DescriptionFileUtils = __webpack_require__(18641); - return null; -} +/** @typedef {import("./Resolver")} Resolver */ +/** @typedef {import("./Resolver").ResolveStepHook} ResolveStepHook */ -/** - * Internal helper to create path tree node - * to ensure that each node gets the same hidden class - * @returns {PathTreeNode} node - */ -function createNode() { - return { - children: null, - folder: null, - wildcards: null, - files: new Map() - }; -} +const slashCode = "/".charCodeAt(0); -/** - * Internal helper for building path tree - * @param {PathTreeNode} root root - * @param {string} path path - * @param {MappingValue} target target - */ -function walkPath(root, path, target) { - if (path.length === 0) { - root.folder = target; - return; +module.exports = class SelfReferencePlugin { + /** + * @param {string | ResolveStepHook} source source + * @param {string | string[]} fieldNamePath name path + * @param {string | ResolveStepHook} target target + */ + constructor(source, fieldNamePath, target) { + this.source = source; + this.target = target; + this.fieldName = fieldNamePath; } - let node = root; - // Typical path tree can looks like - // root - // - files: ["a.js", "b.js"] - // - children: - // node1: - // - files: ["a.js", "b.js"] - let lastNonSlashIndex = 0; - let slashIndex = path.indexOf("/", 0); + /** + * @param {Resolver} resolver the resolver + * @returns {void} + */ + apply(resolver) { + const target = resolver.ensureHook(this.target); + resolver + .getHook(this.source) + .tapAsync("SelfReferencePlugin", (request, resolveContext, callback) => { + if (!request.descriptionFilePath) return callback(); - while (slashIndex !== -1) { - const folder = path.slice(lastNonSlashIndex, slashIndex); - let newNode; + const req = request.request; + if (!req) return callback(); - if (node.children === null) { - newNode = createNode(); - node.children = new Map(); - node.children.set(folder, newNode); - } else { - newNode = node.children.get(folder); + // Feature is only enabled when an exports field is present + const exportsField = DescriptionFileUtils.getField( + request.descriptionFileData, + this.fieldName + ); + if (!exportsField) return callback(); - if (!newNode) { - newNode = createNode(); - node.children.set(folder, newNode); - } - } + const name = DescriptionFileUtils.getField( + request.descriptionFileData, + "name" + ); + if (typeof name !== "string") return callback(); - node = newNode; - lastNonSlashIndex = slashIndex + 1; - slashIndex = path.indexOf("/", lastNonSlashIndex); - } + if ( + req.startsWith(name) && + (req.length === name.length || + req.charCodeAt(name.length) === slashCode) + ) { + const remainingRequest = `.${req.slice(name.length)}`; - if (lastNonSlashIndex >= path.length) { - node.folder = target; - } else { - const file = lastNonSlashIndex > 0 ? path.slice(lastNonSlashIndex) : path; - if (file.endsWith("*")) { - if (node.wildcards === null) node.wildcards = new Map(); - node.wildcards.set(file.slice(0, -1), target); - } else { - node.files.set(file, target); - } + const obj = { + ...request, + request: remainingRequest, + path: /** @type {string} */ (request.descriptionFileRoot), + relativePath: "." + }; + + resolver.doResolve( + target, + obj, + "self reference", + resolveContext, + callback + ); + } else { + return callback(); + } + }); } -} +}; -/** - * @param {ExportsField} field exports field - * @returns {PathTreeNode} tree root - */ -function buildExportsFieldPathTree(field) { - const root = createNode(); - // handle syntax sugar, if exports field is direct mapping for "." - if (typeof field === "string") { - root.files.set("", field); +/***/ }), - return root; - } else if (Array.isArray(field)) { - root.files.set("", field.slice()); +/***/ 69476: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - return root; - } +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ - const keys = Object.keys(field); - for (let i = 0; i < keys.length; i++) { - const key = keys[i]; - if (key.charCodeAt(0) !== dotCode) { - // handle syntax sugar, if exports field is conditional mapping for "." - if (i === 0) { - while (i < keys.length) { - const charCode = keys[i].charCodeAt(0); - if (charCode === dotCode || charCode === slashCode) { - throw new Error( - `Exports field key should be relative path and start with "." (key: ${JSON.stringify( - key - )})` +const forEachBail = __webpack_require__(55426); +const getPaths = __webpack_require__(17117); +const { getType, PathType } = __webpack_require__(69821); + +/** @typedef {import("./Resolver")} Resolver */ +/** @typedef {import("./Resolver").ResolveStepHook} ResolveStepHook */ + +module.exports = class SymlinkPlugin { + /** + * @param {string | ResolveStepHook} source source + * @param {string | ResolveStepHook} target target + */ + constructor(source, target) { + this.source = source; + this.target = target; + } + + /** + * @param {Resolver} resolver the resolver + * @returns {void} + */ + apply(resolver) { + const target = resolver.ensureHook(this.target); + const fs = resolver.fileSystem; + resolver + .getHook(this.source) + .tapAsync("SymlinkPlugin", (request, resolveContext, callback) => { + if (request.ignoreSymlinks) return callback(); + const pathsResult = getPaths(request.path); + const pathSeqments = pathsResult.seqments; + const paths = pathsResult.paths; + + let containsSymlink = false; + let idx = -1; + forEachBail( + paths, + (path, callback) => { + idx++; + if (resolveContext.fileDependencies) + resolveContext.fileDependencies.add(path); + fs.readlink(path, (err, result) => { + if (!err && result) { + pathSeqments[idx] = result; + containsSymlink = true; + // Shortcut when absolute symlink found + const resultType = getType(result.toString()); + if ( + resultType === PathType.AbsoluteWin || + resultType === PathType.AbsolutePosix + ) { + return callback(null, idx); + } + } + callback(); + }); + }, + (err, idx) => { + if (!containsSymlink) return callback(); + const resultSeqments = + typeof idx === "number" + ? pathSeqments.slice(0, idx + 1) + : pathSeqments.slice(); + const result = resultSeqments.reduceRight((a, b) => { + return resolver.join(a, b); + }); + const obj = { + ...request, + path: result + }; + resolver.doResolve( + target, + obj, + "resolved symlink to " + result, + resolveContext, + callback ); } - i++; - } + ); + }); + } +}; - root.files.set("", field); - return root; - } - throw new Error( - `Exports field key should be relative path and start with "." (key: ${JSON.stringify( - key - )})` - ); - } +/***/ }), - if (key.length === 1) { - root.files.set("", field[key]); - continue; - } +/***/ 83908: +/***/ (function(module) { - if (key.charCodeAt(1) !== slashCode) { - throw new Error( - `Exports field key should be relative path and start with "./" (key: ${JSON.stringify( - key - )})` - ); - } +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ - walkPath(root, key.slice(2), field[key]); - } - return root; -} + +/** @typedef {import("./Resolver").FileSystem} FileSystem */ +/** @typedef {import("./Resolver").SyncFileSystem} SyncFileSystem */ /** - * @param {ImportsField} field imports field - * @returns {PathTreeNode} root + * @param {SyncFileSystem} fs file system implementation + * @constructor */ -function buildImportsFieldPathTree(field) { - const root = createNode(); +function SyncAsyncFileSystemDecorator(fs) { + this.fs = fs; - const keys = Object.keys(field); + this.lstat = undefined; + this.lstatSync = undefined; + const lstatSync = fs.lstatSync; + if (lstatSync) { + this.lstat = (arg, options, callback) => { + let result; + try { + result = lstatSync.call(fs, arg); + } catch (e) { + return (callback || options)(e); + } + (callback || options)(null, result); + }; + this.lstatSync = (arg, options) => lstatSync.call(fs, arg, options); + } - for (let i = 0; i < keys.length; i++) { - const key = keys[i]; + this.stat = (arg, options, callback) => { + let result; + try { + result = callback ? fs.statSync(arg, options) : fs.statSync(arg); + } catch (e) { + return (callback || options)(e); + } + (callback || options)(null, result); + }; + this.statSync = (arg, options) => fs.statSync(arg, options); - if (key.charCodeAt(0) !== hashCode) { - throw new Error( - `Imports field key should start with "#" (key: ${JSON.stringify(key)})` - ); + this.readdir = (arg, options, callback) => { + let result; + try { + result = fs.readdirSync(arg); + } catch (e) { + return (callback || options)(e); } + (callback || options)(null, result); + }; + this.readdirSync = (arg, options) => fs.readdirSync(arg, options); - if (key.length === 1) { - throw new Error( - `Imports field key should have at least 2 characters (key: ${JSON.stringify( - key - )})` - ); + this.readFile = (arg, options, callback) => { + let result; + try { + result = fs.readFileSync(arg); + } catch (e) { + return (callback || options)(e); } + (callback || options)(null, result); + }; + this.readFileSync = (arg, options) => fs.readFileSync(arg, options); - if (key.charCodeAt(1) === slashCode) { - throw new Error( - `Imports field key should not start with "#/" (key: ${JSON.stringify( - key - )})` - ); + this.readlink = (arg, options, callback) => { + let result; + try { + result = fs.readlinkSync(arg); + } catch (e) { + return (callback || options)(e); } + (callback || options)(null, result); + }; + this.readlinkSync = (arg, options) => fs.readlinkSync(arg, options); - walkPath(root, key.slice(1), field[key]); - } + this.readJson = undefined; + this.readJsonSync = undefined; + const readJsonSync = fs.readJsonSync; + if (readJsonSync) { + this.readJson = (arg, options, callback) => { + let result; + try { + result = readJsonSync.call(fs, arg); + } catch (e) { + return (callback || options)(e); + } + (callback || options)(null, result); + }; - return root; + this.readJsonSync = (arg, options) => readJsonSync.call(fs, arg, options); + } } +module.exports = SyncAsyncFileSystemDecorator; /***/ }), -/***/ 98623: +/***/ 73771: /***/ (function(module) { "use strict"; /* MIT License http://www.opensource.org/licenses/mit-license.php - Author Ivan Kopeykin @vankop + Author Tobias Koppers @sokra */ -const PATH_QUERY_FRAGMENT_REGEXP = /^(#?(?:\0.|[^?#\0])*)(\?(?:\0.|[^#\0])*)?(#.*)?$/; - -/** - * @param {string} identifier identifier - * @returns {[string, string, string]|null} parsed identifier - */ -function parseIdentifier(identifier) { - const match = PATH_QUERY_FRAGMENT_REGEXP.exec(identifier); - - if (!match) return null; +/** @typedef {import("./Resolver")} Resolver */ +/** @typedef {import("./Resolver").ResolveStepHook} ResolveStepHook */ - return [ - match[1].replace(/\0(.)/g, "$1"), - match[2] ? match[2].replace(/\0(.)/g, "$1") : "", - match[3] || "" - ]; -} +module.exports = class TryNextPlugin { + /** + * @param {string | ResolveStepHook} source source + * @param {string} message message + * @param {string | ResolveStepHook} target target + */ + constructor(source, message, target) { + this.source = source; + this.message = message; + this.target = target; + } -module.exports.parseIdentifier = parseIdentifier; + /** + * @param {Resolver} resolver the resolver + * @returns {void} + */ + apply(resolver) { + const target = resolver.ensureHook(this.target); + resolver + .getHook(this.source) + .tapAsync("TryNextPlugin", (request, resolveContext, callback) => { + resolver.doResolve( + target, + request, + this.message, + resolveContext, + callback + ); + }); + } +}; /***/ }), -/***/ 69821: -/***/ (function(__unused_webpack_module, exports, __webpack_require__) { +/***/ 57943: +/***/ (function(module) { "use strict"; /* @@ -140023,1275 +140735,1133 @@ module.exports.parseIdentifier = parseIdentifier; -const path = __webpack_require__(85622); - -const CHAR_HASH = "#".charCodeAt(0); -const CHAR_SLASH = "/".charCodeAt(0); -const CHAR_BACKSLASH = "\\".charCodeAt(0); -const CHAR_A = "A".charCodeAt(0); -const CHAR_Z = "Z".charCodeAt(0); -const CHAR_LOWER_A = "a".charCodeAt(0); -const CHAR_LOWER_Z = "z".charCodeAt(0); -const CHAR_DOT = ".".charCodeAt(0); -const CHAR_COLON = ":".charCodeAt(0); - -const posixNormalize = path.posix.normalize; -const winNormalize = path.win32.normalize; +/** @typedef {import("./Resolver")} Resolver */ +/** @typedef {import("./Resolver").ResolveRequest} ResolveRequest */ +/** @typedef {import("./Resolver").ResolveStepHook} ResolveStepHook */ +/** @typedef {{[k: string]: any}} Cache */ -/** - * @enum {number} - */ -const PathType = Object.freeze({ - Empty: 0, - Normal: 1, - Relative: 2, - AbsoluteWin: 3, - AbsolutePosix: 4, - Internal: 5 -}); -exports.PathType = PathType; +function getCacheId(request, withContext) { + return JSON.stringify({ + context: withContext ? request.context : "", + path: request.path, + query: request.query, + fragment: request.fragment, + request: request.request + }); +} -/** - * @param {string} p a path - * @returns {PathType} type of path - */ -const getType = p => { - switch (p.length) { - case 0: - return PathType.Empty; - case 1: { - const c0 = p.charCodeAt(0); - switch (c0) { - case CHAR_DOT: - return PathType.Relative; - case CHAR_SLASH: - return PathType.AbsolutePosix; - case CHAR_HASH: - return PathType.Internal; - } - return PathType.Normal; - } - case 2: { - const c0 = p.charCodeAt(0); - switch (c0) { - case CHAR_DOT: { - const c1 = p.charCodeAt(1); - switch (c1) { - case CHAR_DOT: - case CHAR_SLASH: - return PathType.Relative; - } - return PathType.Normal; - } - case CHAR_SLASH: - return PathType.AbsolutePosix; - case CHAR_HASH: - return PathType.Internal; - } - const c1 = p.charCodeAt(1); - if (c1 === CHAR_COLON) { - if ( - (c0 >= CHAR_A && c0 <= CHAR_Z) || - (c0 >= CHAR_LOWER_A && c0 <= CHAR_LOWER_Z) - ) { - return PathType.AbsoluteWin; - } - } - return PathType.Normal; - } +module.exports = class UnsafeCachePlugin { + /** + * @param {string | ResolveStepHook} source source + * @param {function(ResolveRequest): boolean} filterPredicate filterPredicate + * @param {Cache} cache cache + * @param {boolean} withContext withContext + * @param {string | ResolveStepHook} target target + */ + constructor(source, filterPredicate, cache, withContext, target) { + this.source = source; + this.filterPredicate = filterPredicate; + this.withContext = withContext; + this.cache = cache; + this.target = target; } - const c0 = p.charCodeAt(0); - switch (c0) { - case CHAR_DOT: { - const c1 = p.charCodeAt(1); - switch (c1) { - case CHAR_SLASH: - return PathType.Relative; - case CHAR_DOT: { - const c2 = p.charCodeAt(2); - if (c2 === CHAR_SLASH) return PathType.Relative; - return PathType.Normal; + + /** + * @param {Resolver} resolver the resolver + * @returns {void} + */ + apply(resolver) { + const target = resolver.ensureHook(this.target); + resolver + .getHook(this.source) + .tapAsync("UnsafeCachePlugin", (request, resolveContext, callback) => { + if (!this.filterPredicate(request)) return callback(); + const cacheId = getCacheId(request, this.withContext); + const cacheEntry = this.cache[cacheId]; + if (cacheEntry) { + return callback(null, cacheEntry); } - } - return PathType.Normal; - } - case CHAR_SLASH: - return PathType.AbsolutePosix; - case CHAR_HASH: - return PathType.Internal; - } - const c1 = p.charCodeAt(1); - if (c1 === CHAR_COLON) { - const c2 = p.charCodeAt(2); - if ( - (c2 === CHAR_BACKSLASH || c2 === CHAR_SLASH) && - ((c0 >= CHAR_A && c0 <= CHAR_Z) || - (c0 >= CHAR_LOWER_A && c0 <= CHAR_LOWER_Z)) - ) { - return PathType.AbsoluteWin; - } + resolver.doResolve( + target, + request, + null, + resolveContext, + (err, result) => { + if (err) return callback(err); + if (result) return callback(null, (this.cache[cacheId] = result)); + callback(); + } + ); + }); } - return PathType.Normal; }; -exports.getType = getType; -/** - * @param {string} p a path - * @returns {string} the normalized path - */ -const normalize = p => { - switch (getType(p)) { - case PathType.Empty: - return p; - case PathType.AbsoluteWin: - return winNormalize(p); - case PathType.Relative: { - const r = posixNormalize(p); - return getType(r) === PathType.Relative ? r : `./${r}`; - } - } - return posixNormalize(p); -}; -exports.normalize = normalize; -/** - * @param {string} rootPath the root path - * @param {string | undefined} request the request path - * @returns {string} the joined path - */ -const join = (rootPath, request) => { - if (!request) return normalize(rootPath); - const requestType = getType(request); - switch (requestType) { - case PathType.AbsolutePosix: - return posixNormalize(request); - case PathType.AbsoluteWin: - return winNormalize(request); - } - switch (getType(rootPath)) { - case PathType.Normal: - case PathType.Relative: - case PathType.AbsolutePosix: - return posixNormalize(`${rootPath}/${request}`); - case PathType.AbsoluteWin: - return winNormalize(`${rootPath}\\${request}`); - } - switch (requestType) { - case PathType.Empty: - return rootPath; - case PathType.Relative: { - const r = posixNormalize(rootPath); - return getType(r) === PathType.Relative ? r : `./${r}`; - } - } - return posixNormalize(rootPath); -}; -exports.join = join; +/***/ }), -const joinCache = new Map(); +/***/ 81190: +/***/ (function(module) { -/** - * @param {string} rootPath the root path - * @param {string | undefined} request the request path - * @returns {string} the joined path - */ -const cachedJoin = (rootPath, request) => { - let cacheEntry; - let cache = joinCache.get(rootPath); - if (cache === undefined) { - joinCache.set(rootPath, (cache = new Map())); - } else { - cacheEntry = cache.get(request); - if (cacheEntry !== undefined) return cacheEntry; - } - cacheEntry = join(rootPath, request); - cache.set(request, cacheEntry); - return cacheEntry; -}; -exports.cachedJoin = cachedJoin; +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ -const checkExportsFieldTarget = relativePath => { - let lastNonSlashIndex = 2; - let slashIndex = relativePath.indexOf("/", 2); - let cd = 0; - while (slashIndex !== -1) { - const folder = relativePath.slice(lastNonSlashIndex, slashIndex); - switch (folder) { - case "..": { - cd--; - if (cd < 0) - return new Error( - `Trying to access out of package scope. Requesting ${relativePath}` - ); - break; - } - default: - cd++; - break; - } +/** @typedef {import("./Resolver")} Resolver */ +/** @typedef {import("./Resolver").ResolveStepHook} ResolveStepHook */ - lastNonSlashIndex = slashIndex + 1; - slashIndex = relativePath.indexOf("/", lastNonSlashIndex); +module.exports = class UseFilePlugin { + /** + * @param {string | ResolveStepHook} source source + * @param {string} filename filename + * @param {string | ResolveStepHook} target target + */ + constructor(source, filename, target) { + this.source = source; + this.filename = filename; + this.target = target; + } + + /** + * @param {Resolver} resolver the resolver + * @returns {void} + */ + apply(resolver) { + const target = resolver.ensureHook(this.target); + resolver + .getHook(this.source) + .tapAsync("UseFilePlugin", (request, resolveContext, callback) => { + const filePath = resolver.join(request.path, this.filename); + const obj = { + ...request, + path: filePath, + relativePath: + request.relativePath && + resolver.join(request.relativePath, this.filename) + }; + resolver.doResolve( + target, + obj, + "using path: " + filePath, + resolveContext, + callback + ); + }); } }; -exports.checkExportsFieldTarget = checkExportsFieldTarget; /***/ }), -/***/ 83798: +/***/ 710: /***/ (function(module) { "use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ -class LoadingLoaderError extends Error { - constructor(message) { - super(message); - this.name = "LoaderRunnerError"; - Error.captureStackTrace(this, this.constructor); - } -} -module.exports = LoadingLoaderError; +module.exports = function createInnerContext( + options, + message, + messageOptional +) { + let messageReported = false; + let innerLog = undefined; + if (options.log) { + if (message) { + innerLog = msg => { + if (!messageReported) { + options.log(message); + messageReported = true; + } + options.log(" " + msg); + }; + } else { + innerLog = options.log; + } + } + const childContext = { + log: innerLog, + fileDependencies: options.fileDependencies, + contextDependencies: options.contextDependencies, + missingDependencies: options.missingDependencies, + stack: options.stack + }; + return childContext; +}; /***/ }), -/***/ 67578: -/***/ (function(__unused_webpack_module, exports, __webpack_require__) { +/***/ 55426: +/***/ (function(module) { +"use strict"; /* MIT License http://www.opensource.org/licenses/mit-license.php Author Tobias Koppers @sokra */ -var fs = __webpack_require__(35747); -var readFile = fs.readFile.bind(fs); -var loadLoader = __webpack_require__(63395); - -function utf8BufferToString(buf) { - var str = buf.toString("utf-8"); - if(str.charCodeAt(0) === 0xFEFF) { - return str.substr(1); - } else { - return str; - } -} - -const PATH_QUERY_FRAGMENT_REGEXP = /^((?:\0.|[^?#\0])*)(\?(?:\0.|[^#\0])*)?(#.*)?$/; -/** - * @param {string} str the path with query and fragment - * @returns {{ path: string, query: string, fragment: string }} parsed parts - */ -function parsePathQueryFragment(str) { - var match = PATH_QUERY_FRAGMENT_REGEXP.exec(str); - return { - path: match[1].replace(/\0(.)/g, "$1"), - query: match[2] ? match[2].replace(/\0(.)/g, "$1") : "", - fragment: match[3] || "" - }; -} -function dirname(path) { - if(path === "/") return "/"; - var i = path.lastIndexOf("/"); - var j = path.lastIndexOf("\\"); - var i2 = path.indexOf("/"); - var j2 = path.indexOf("\\"); - var idx = i > j ? i : j; - var idx2 = i > j ? i2 : j2; - if(idx < 0) return path; - if(idx === idx2) return path.substr(0, idx + 1); - return path.substr(0, idx); -} -function createLoaderObject(loader) { - var obj = { - path: null, - query: null, - fragment: null, - options: null, - ident: null, - normal: null, - pitch: null, - raw: null, - data: null, - pitchExecuted: false, - normalExecuted: false - }; - Object.defineProperty(obj, "request", { - enumerable: true, - get: function() { - return obj.path.replace(/#/g, "\0#") + obj.query.replace(/#/g, "\0#") + obj.fragment; - }, - set: function(value) { - if(typeof value === "string") { - var splittedRequest = parsePathQueryFragment(value); - obj.path = splittedRequest.path; - obj.query = splittedRequest.query; - obj.fragment = splittedRequest.fragment; - obj.options = undefined; - obj.ident = undefined; - } else { - if(!value.loader) - throw new Error("request should be a string or object with loader and options (" + JSON.stringify(value) + ")"); - obj.path = value.loader; - obj.fragment = value.fragment || ""; - obj.type = value.type; - obj.options = value.options; - obj.ident = value.ident; - if(obj.options === null) - obj.query = ""; - else if(obj.options === undefined) - obj.query = ""; - else if(typeof obj.options === "string") - obj.query = "?" + obj.options; - else if(obj.ident) - obj.query = "??" + obj.ident; - else if(typeof obj.options === "object" && obj.options.ident) - obj.query = "??" + obj.options.ident; - else - obj.query = "?" + JSON.stringify(obj.options); - } - } - }); - obj.request = loader; - if(Object.preventExtensions) { - Object.preventExtensions(obj); - } - return obj; -} +module.exports = function forEachBail(array, iterator, callback) { + if (array.length === 0) return callback(); -function runSyncOrAsync(fn, context, args, callback) { - var isSync = true; - var isDone = false; - var isError = false; // internal error - var reportedError = false; - context.async = function async() { - if(isDone) { - if(reportedError) return; // ignore - throw new Error("async(): The callback was already called."); - } - isSync = false; - return innerCallback; - }; - var innerCallback = context.callback = function() { - if(isDone) { - if(reportedError) return; // ignore - throw new Error("callback(): The callback was already called."); - } - isDone = true; - isSync = false; - try { - callback.apply(null, arguments); - } catch(e) { - isError = true; - throw e; - } - }; - try { - var result = (function LOADER_EXECUTION() { - return fn.apply(context, args); - }()); - if(isSync) { - isDone = true; - if(result === undefined) - return callback(); - if(result && typeof result === "object" && typeof result.then === "function") { - return result.then(function(r) { - callback(null, r); - }, callback); + let i = 0; + const next = () => { + let loop = undefined; + iterator(array[i++], (err, result) => { + if (err || result !== undefined || i >= array.length) { + return callback(err, result); } - return callback(null, result); - } - } catch(e) { - if(isError) throw e; - if(isDone) { - // loader is already "done", so we cannot use the callback function - // for better debugging we print the error on the console - if(typeof e === "object" && e.stack) console.error(e.stack); - else console.error(e); - return; - } - isDone = true; - reportedError = true; - callback(e); - } + if (loop === false) while (next()); + loop = true; + }); + if (!loop) loop = false; + return loop; + }; + while (next()); +}; -} -function convertArgs(args, raw) { - if(!raw && Buffer.isBuffer(args[0])) - args[0] = utf8BufferToString(args[0]); - else if(raw && typeof args[0] === "string") - args[0] = Buffer.from(args[0], "utf-8"); -} +/***/ }), -function iteratePitchingLoaders(options, loaderContext, callback) { - // abort after last loader - if(loaderContext.loaderIndex >= loaderContext.loaders.length) - return processResource(options, loaderContext, callback); +/***/ 98361: +/***/ (function(module) { - var currentLoaderObject = loaderContext.loaders[loaderContext.loaderIndex]; +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ - // iterate - if(currentLoaderObject.pitchExecuted) { - loaderContext.loaderIndex++; - return iteratePitchingLoaders(options, loaderContext, callback); - } - // load loader module - loadLoader(currentLoaderObject, function(err) { - if(err) { - loaderContext.cacheable(false); - return callback(err); + +module.exports = function getInnerRequest(resolver, request) { + if ( + typeof request.__innerRequest === "string" && + request.__innerRequest_request === request.request && + request.__innerRequest_relativePath === request.relativePath + ) + return request.__innerRequest; + let innerRequest; + if (request.request) { + innerRequest = request.request; + if (/^\.\.?(?:\/|$)/.test(innerRequest) && request.relativePath) { + innerRequest = resolver.join(request.relativePath, innerRequest); } - var fn = currentLoaderObject.pitch; - currentLoaderObject.pitchExecuted = true; - if(!fn) return iteratePitchingLoaders(options, loaderContext, callback); + } else { + innerRequest = request.relativePath; + } + request.__innerRequest_request = request.request; + request.__innerRequest_relativePath = request.relativePath; + return (request.__innerRequest = innerRequest); +}; - runSyncOrAsync( - fn, - loaderContext, [loaderContext.remainingRequest, loaderContext.previousRequest, currentLoaderObject.data = {}], - function(err) { - if(err) return callback(err); - var args = Array.prototype.slice.call(arguments, 1); - // Determine whether to continue the pitching process based on - // argument values (as opposed to argument presence) in order - // to support synchronous and asynchronous usages. - var hasArg = args.some(function(value) { - return value !== undefined; - }); - if(hasArg) { - loaderContext.loaderIndex--; - iterateNormalLoaders(options, loaderContext, args, callback); - } else { - iteratePitchingLoaders(options, loaderContext, callback); - } - } - ); - }); -} -function processResource(options, loaderContext, callback) { - // set loader index to last loader - loaderContext.loaderIndex = loaderContext.loaders.length - 1; +/***/ }), - var resourcePath = loaderContext.resourcePath; - if(resourcePath) { - options.processResource(loaderContext, resourcePath, function(err, buffer) { - if(err) return callback(err); - options.resourceBuffer = buffer; - iterateNormalLoaders(options, loaderContext, [buffer], callback); - }); - } else { - iterateNormalLoaders(options, loaderContext, [null], callback); - } -} +/***/ 17117: +/***/ (function(module) { -function iterateNormalLoaders(options, loaderContext, args, callback) { - if(loaderContext.loaderIndex < 0) - return callback(null, args); +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ - var currentLoaderObject = loaderContext.loaders[loaderContext.loaderIndex]; - // iterate - if(currentLoaderObject.normalExecuted) { - loaderContext.loaderIndex--; - return iterateNormalLoaders(options, loaderContext, args, callback); - } - var fn = currentLoaderObject.normal; - currentLoaderObject.normalExecuted = true; - if(!fn) { - return iterateNormalLoaders(options, loaderContext, args, callback); +module.exports = function getPaths(path) { + const parts = path.split(/(.*?[\\/]+)/); + const paths = [path]; + const seqments = [parts[parts.length - 1]]; + let part = parts[parts.length - 1]; + path = path.substr(0, path.length - part.length - 1); + for (let i = parts.length - 2; i > 2; i -= 2) { + paths.push(path); + part = parts[i]; + path = path.substr(0, path.length - part.length) || "/"; + seqments.push(part.substr(0, part.length - 1)); } + part = parts[1]; + seqments.push(part); + paths.push(part); + return { + paths: paths, + seqments: seqments + }; +}; - convertArgs(args, currentLoaderObject.raw); +module.exports.basename = function basename(path) { + const i = path.lastIndexOf("/"), + j = path.lastIndexOf("\\"); + const p = i < 0 ? j : j < 0 ? i : i < j ? j : i; + if (p < 0) return null; + const s = path.substr(p + 1); + return s; +}; - runSyncOrAsync(fn, loaderContext, args, function(err) { - if(err) return callback(err); - var args = Array.prototype.slice.call(arguments, 1); - iterateNormalLoaders(options, loaderContext, args, callback); - }); -} +/***/ }), -exports.getContext = function getContext(resource) { - var path = parsePathQueryFragment(resource).path; - return dirname(path); -}; +/***/ 27480: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { -exports.runLoaders = function runLoaders(options, callback) { - // read options - var resource = options.resource || ""; - var loaders = options.loaders || []; - var loaderContext = options.context || {}; - var processResource = options.processResource || ((readResource, context, resource, callback) => { - context.addDependency(resource); - readResource(resource, callback); - }).bind(null, options.readResource || readFile); +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ - // - var splittedResource = resource && parsePathQueryFragment(resource); - var resourcePath = splittedResource ? splittedResource.path : undefined; - var resourceQuery = splittedResource ? splittedResource.query : undefined; - var resourceFragment = splittedResource ? splittedResource.fragment : undefined; - var contextDirectory = resourcePath ? dirname(resourcePath) : null; - // execution state - var requestCacheable = true; - var fileDependencies = []; - var contextDependencies = []; - var missingDependencies = []; - // prepare loader objects - loaders = loaders.map(createLoaderObject); +const fs = __webpack_require__(82161); +const CachedInputFileSystem = __webpack_require__(26785); +const ResolverFactory = __webpack_require__(1453); - loaderContext.context = contextDirectory; - loaderContext.loaderIndex = 0; - loaderContext.loaders = loaders; - loaderContext.resourcePath = resourcePath; - loaderContext.resourceQuery = resourceQuery; - loaderContext.resourceFragment = resourceFragment; - loaderContext.async = null; - loaderContext.callback = null; - loaderContext.cacheable = function cacheable(flag) { - if(flag === false) { - requestCacheable = false; - } - }; - loaderContext.dependency = loaderContext.addDependency = function addDependency(file) { - fileDependencies.push(file); - }; - loaderContext.addContextDependency = function addContextDependency(context) { - contextDependencies.push(context); - }; - loaderContext.addMissingDependency = function addMissingDependency(context) { - missingDependencies.push(context); - }; - loaderContext.getDependencies = function getDependencies() { - return fileDependencies.slice(); - }; - loaderContext.getContextDependencies = function getContextDependencies() { - return contextDependencies.slice(); - }; - loaderContext.getMissingDependencies = function getMissingDependencies() { - return missingDependencies.slice(); - }; - loaderContext.clearDependencies = function clearDependencies() { - fileDependencies.length = 0; - contextDependencies.length = 0; - missingDependencies.length = 0; - requestCacheable = true; +/** @typedef {import("./PnpPlugin").PnpApiImpl} PnpApi */ +/** @typedef {import("./Resolver")} Resolver */ +/** @typedef {import("./Resolver").FileSystem} FileSystem */ +/** @typedef {import("./Resolver").ResolveContext} ResolveContext */ +/** @typedef {import("./Resolver").ResolveRequest} ResolveRequest */ +/** @typedef {import("./ResolverFactory").Plugin} Plugin */ +/** @typedef {import("./ResolverFactory").UserResolveOptions} ResolveOptions */ + +const nodeFileSystem = new CachedInputFileSystem(fs, 4000); + +const nodeContext = { + environments: ["node+es3+es5+process+native"] +}; + +const asyncResolver = ResolverFactory.createResolver({ + conditionNames: ["node"], + extensions: [".js", ".json", ".node"], + fileSystem: nodeFileSystem +}); +function resolve(context, path, request, resolveContext, callback) { + if (typeof context === "string") { + callback = resolveContext; + resolveContext = request; + request = path; + path = context; + context = nodeContext; + } + if (typeof callback !== "function") { + callback = resolveContext; + } + asyncResolver.resolve(context, path, request, resolveContext, callback); +} + +const syncResolver = ResolverFactory.createResolver({ + conditionNames: ["node"], + extensions: [".js", ".json", ".node"], + useSyncFileSystemCalls: true, + fileSystem: nodeFileSystem +}); +function resolveSync(context, path, request) { + if (typeof context === "string") { + request = path; + path = context; + context = nodeContext; + } + return syncResolver.resolveSync(context, path, request); +} + +function create(options) { + options = { + fileSystem: nodeFileSystem, + ...options }; - Object.defineProperty(loaderContext, "resource", { - enumerable: true, - get: function() { - if(loaderContext.resourcePath === undefined) - return undefined; - return loaderContext.resourcePath.replace(/#/g, "\0#") + loaderContext.resourceQuery.replace(/#/g, "\0#") + loaderContext.resourceFragment; - }, - set: function(value) { - var splittedResource = value && parsePathQueryFragment(value); - loaderContext.resourcePath = splittedResource ? splittedResource.path : undefined; - loaderContext.resourceQuery = splittedResource ? splittedResource.query : undefined; - loaderContext.resourceFragment = splittedResource ? splittedResource.fragment : undefined; - } - }); - Object.defineProperty(loaderContext, "request", { - enumerable: true, - get: function() { - return loaderContext.loaders.map(function(o) { - return o.request; - }).concat(loaderContext.resource || "").join("!"); - } - }); - Object.defineProperty(loaderContext, "remainingRequest", { - enumerable: true, - get: function() { - if(loaderContext.loaderIndex >= loaderContext.loaders.length - 1 && !loaderContext.resource) - return ""; - return loaderContext.loaders.slice(loaderContext.loaderIndex + 1).map(function(o) { - return o.request; - }).concat(loaderContext.resource || "").join("!"); - } - }); - Object.defineProperty(loaderContext, "currentRequest", { - enumerable: true, - get: function() { - return loaderContext.loaders.slice(loaderContext.loaderIndex).map(function(o) { - return o.request; - }).concat(loaderContext.resource || "").join("!"); - } - }); - Object.defineProperty(loaderContext, "previousRequest", { - enumerable: true, - get: function() { - return loaderContext.loaders.slice(0, loaderContext.loaderIndex).map(function(o) { - return o.request; - }).join("!"); - } - }); - Object.defineProperty(loaderContext, "query", { - enumerable: true, - get: function() { - var entry = loaderContext.loaders[loaderContext.loaderIndex]; - return entry.options && typeof entry.options === "object" ? entry.options : entry.query; + const resolver = ResolverFactory.createResolver(options); + return function (context, path, request, resolveContext, callback) { + if (typeof context === "string") { + callback = resolveContext; + resolveContext = request; + request = path; + path = context; + context = nodeContext; } - }); - Object.defineProperty(loaderContext, "data", { - enumerable: true, - get: function() { - return loaderContext.loaders[loaderContext.loaderIndex].data; + if (typeof callback !== "function") { + callback = resolveContext; } - }); - - // finish loader context - if(Object.preventExtensions) { - Object.preventExtensions(loaderContext); - } + resolver.resolve(context, path, request, resolveContext, callback); + }; +} - var processOptions = { - resourceBuffer: null, - processResource: processResource +function createSync(options) { + options = { + useSyncFileSystemCalls: true, + fileSystem: nodeFileSystem, + ...options }; - iteratePitchingLoaders(processOptions, loaderContext, function(err, result) { - if(err) { - return callback(err, { - cacheable: requestCacheable, - fileDependencies: fileDependencies, - contextDependencies: contextDependencies, - missingDependencies: missingDependencies - }); + const resolver = ResolverFactory.createResolver(options); + return function (context, path, request) { + if (typeof context === "string") { + request = path; + path = context; + context = nodeContext; } - callback(null, { - result: result, - resourceBuffer: processOptions.resourceBuffer, - cacheable: requestCacheable, - fileDependencies: fileDependencies, - contextDependencies: contextDependencies, - missingDependencies: missingDependencies - }); - }); + return resolver.resolveSync(context, path, request); + }; +} + +/** + * @template A + * @template B + * @param {A} obj input a + * @param {B} exports input b + * @returns {A & B} merged + */ +const mergeExports = (obj, exports) => { + const descriptors = Object.getOwnPropertyDescriptors(exports); + Object.defineProperties(obj, descriptors); + return /** @type {A & B} */ (Object.freeze(obj)); }; +module.exports = mergeExports(resolve, { + get sync() { + return resolveSync; + }, + create: mergeExports(create, { + get sync() { + return createSync; + } + }), + ResolverFactory, + CachedInputFileSystem, + get CloneBasenamePlugin() { + return __webpack_require__(36154); + }, + get LogInfoPlugin() { + return __webpack_require__(50098); + }, + get forEachBail() { + return __webpack_require__(55426); + } +}); + /***/ }), -/***/ 63395: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { +/***/ 94340: +/***/ (function(module) { -var LoaderLoadingError = __webpack_require__(83798); -var url; +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Ivan Kopeykin @vankop +*/ -module.exports = function loadLoader(loader, callback) { - if(loader.type === "module") { - try { - if(url === undefined) url = __webpack_require__(78835); - var loaderUrl = url.pathToFileURL(loader.path); - var modulePromise = eval("import(" + JSON.stringify(loaderUrl.toString()) + ")"); - modulePromise.then(function(module) { - handleResult(loader, module, callback); - }, callback); - return; - } catch(e) { - callback(e); - } - } else { - try { - var module = require(loader.path); - } catch(e) { - // it is possible for node to choke on a require if the FD descriptor - // limit has been reached. give it a chance to recover. - if(e instanceof Error && e.code === "EMFILE") { - var retry = loadLoader.bind(null, loader, callback); - if(typeof setImmediate === "function") { - // node >= 0.9.0 - return setImmediate(retry); - } else { - // node < 0.9.0 - return process.nextTick(retry); - } - } - return callback(e); - } - return handleResult(loader, module, callback); - } -}; -function handleResult(loader, module, callback) { - if(typeof module !== "function" && typeof module !== "object") { - return callback(new LoaderLoadingError( - "Module '" + loader.path + "' is not a loader (export function or es6 module)" - )); - } - loader.normal = typeof module === "function" ? module : module.default; - loader.pitch = module.pitch; - loader.raw = module.raw; - if(typeof loader.normal !== "function" && typeof loader.pitch !== "function") { - return callback(new LoaderLoadingError( - "Module '" + loader.path + "' is not a loader (must have normal or pitch function)" - )); - } - callback(); + +/** @typedef {string|(string|ConditionalMapping)[]} DirectMapping */ +/** @typedef {{[k: string]: MappingValue}} ConditionalMapping */ +/** @typedef {ConditionalMapping|DirectMapping|null} MappingValue */ +/** @typedef {Record|ConditionalMapping|DirectMapping} ExportsField */ +/** @typedef {Record} ImportsField */ + +/** + * @typedef {Object} PathTreeNode + * @property {Map|null} children + * @property {MappingValue} folder + * @property {Map|null} wildcards + * @property {Map} files + */ + +/** + * Processing exports/imports field + * @callback FieldProcessor + * @param {string} request request + * @param {Set} conditionNames condition names + * @returns {string[]} resolved paths + */ + +/* +Example exports field: +{ + ".": "./main.js", + "./feature": { + "browser": "./feature-browser.js", + "default": "./feature.js" + } } +Terminology: +Enhanced-resolve name keys ("." and "./feature") as exports field keys. -/***/ }), +If value is string or string[], mapping is called as a direct mapping +and value called as a direct export. -/***/ 11060: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { +If value is key-value object, mapping is called as a conditional mapping +and value called as a conditional export. -/*! - * mime-db - * Copyright(c) 2014 Jonathan Ong - * MIT Licensed - */ +Key in conditional mapping is called condition name. -/** - * Module exports. - */ +Conditional mapping nested in another conditional mapping is called nested mapping. -module.exports = __webpack_require__(53243) +---------- +Example imports field: +{ + "#a": "./main.js", + "#moment": { + "browser": "./moment/index.js", + "default": "moment" + }, + "#moment/": { + "browser": "./moment/", + "default": "moment/" + } +} +Terminology: -/***/ }), +Enhanced-resolve name keys ("#a" and "#moment/", "#moment") as imports field keys. -/***/ 19338: -/***/ (function(__unused_webpack_module, exports, __webpack_require__) { +If value is string or string[], mapping is called as a direct mapping +and value called as a direct export. -"use strict"; -/*! - * mime-types - * Copyright(c) 2014 Jonathan Ong - * Copyright(c) 2015 Douglas Christopher Wilson - * MIT Licensed - */ +If value is key-value object, mapping is called as a conditional mapping +and value called as a conditional export. +Key in conditional mapping is called condition name. +Conditional mapping nested in another conditional mapping is called nested mapping. -/** - * Module dependencies. - * @private - */ +*/ -var db = __webpack_require__(11060) -var extname = __webpack_require__(85622).extname +const slashCode = "/".charCodeAt(0); +const dotCode = ".".charCodeAt(0); +const hashCode = "#".charCodeAt(0); /** - * Module variables. - * @private + * @param {ExportsField} exportsField the exports field + * @returns {FieldProcessor} process callback */ +module.exports.processExportsField = function processExportsField( + exportsField +) { + return createFieldProcessor( + buildExportsFieldPathTree(exportsField), + assertExportsFieldRequest, + assertExportTarget + ); +}; -var EXTRACT_TYPE_REGEXP = /^\s*([^;\s]*)(?:;|\s|$)/ -var TEXT_TYPE_REGEXP = /^text\//i +/** + * @param {ImportsField} importsField the exports field + * @returns {FieldProcessor} process callback + */ +module.exports.processImportsField = function processImportsField( + importsField +) { + return createFieldProcessor( + buildImportsFieldPathTree(importsField), + assertImportsFieldRequest, + assertImportTarget + ); +}; /** - * Module exports. - * @public + * @param {PathTreeNode} treeRoot root + * @param {(s: string) => string} assertRequest assertRequest + * @param {(s: string, f: boolean) => void} assertTarget assertTarget + * @returns {FieldProcessor} field processor */ +function createFieldProcessor(treeRoot, assertRequest, assertTarget) { + return function fieldProcessor(request, conditionNames) { + request = assertRequest(request); -exports.charset = charset -exports.charsets = { lookup: charset } -exports.contentType = contentType -exports.extension = extension -exports.extensions = Object.create(null) -exports.lookup = lookup -exports.types = Object.create(null) + const match = findMatch(request, treeRoot); -// Populate the extensions/types maps -populateMaps(exports.extensions, exports.types) + if (match === null) return []; -/** - * Get the default charset for a MIME type. - * - * @param {string} type - * @return {boolean|string} - */ + const [mapping, remainRequestIndex] = match; -function charset (type) { - if (!type || typeof type !== 'string') { - return false - } + /** @type {DirectMapping|null} */ + let direct = null; - // TODO: use media-typer - var match = EXTRACT_TYPE_REGEXP.exec(type) - var mime = match && db[match[1].toLowerCase()] + if (isConditionalMapping(mapping)) { + direct = conditionalMapping( + /** @type {ConditionalMapping} */ (mapping), + conditionNames + ); - if (mime && mime.charset) { - return mime.charset - } + // matching not found + if (direct === null) return []; + } else { + direct = /** @type {DirectMapping} */ (mapping); + } - // default text/* to utf-8 - if (match && TEXT_TYPE_REGEXP.test(match[1])) { - return 'UTF-8' - } + const remainingRequest = + remainRequestIndex === request.length + 1 + ? undefined + : remainRequestIndex < 0 + ? request.slice(-remainRequestIndex - 1) + : request.slice(remainRequestIndex); - return false + return directMapping( + remainingRequest, + remainRequestIndex < 0, + direct, + conditionNames, + assertTarget + ); + }; } /** - * Create a full Content-Type header given a MIME type or extension. - * - * @param {string} str - * @return {boolean|string} + * @param {string} request request + * @returns {string} updated request */ +function assertExportsFieldRequest(request) { + if (request.charCodeAt(0) !== dotCode) { + throw new Error('Request should be relative path and start with "."'); + } + if (request.length === 1) return ""; + if (request.charCodeAt(1) !== slashCode) { + throw new Error('Request should be relative path and start with "./"'); + } + if (request.charCodeAt(request.length - 1) === slashCode) { + throw new Error("Only requesting file allowed"); + } -function contentType (str) { - // TODO: should this even be in this module? - if (!str || typeof str !== 'string') { - return false - } - - var mime = str.indexOf('/') === -1 - ? exports.lookup(str) - : str - - if (!mime) { - return false - } + return request.slice(2); +} - // TODO: use content-type or other module - if (mime.indexOf('charset') === -1) { - var charset = exports.charset(mime) - if (charset) mime += '; charset=' + charset.toLowerCase() - } +/** + * @param {string} request request + * @returns {string} updated request + */ +function assertImportsFieldRequest(request) { + if (request.charCodeAt(0) !== hashCode) { + throw new Error('Request should start with "#"'); + } + if (request.length === 1) { + throw new Error("Request should have at least 2 characters"); + } + if (request.charCodeAt(1) === slashCode) { + throw new Error('Request should not start with "#/"'); + } + if (request.charCodeAt(request.length - 1) === slashCode) { + throw new Error("Only requesting file allowed"); + } - return mime + return request.slice(1); } /** - * Get the default extension for a MIME type. - * - * @param {string} type - * @return {boolean|string} + * @param {string} exp export target + * @param {boolean} expectFolder is folder expected */ +function assertExportTarget(exp, expectFolder) { + if ( + exp.charCodeAt(0) === slashCode || + (exp.charCodeAt(0) === dotCode && exp.charCodeAt(1) !== slashCode) + ) { + throw new Error( + `Export should be relative path and start with "./", got ${JSON.stringify( + exp + )}.` + ); + } -function extension (type) { - if (!type || typeof type !== 'string') { - return false - } - - // TODO: use media-typer - var match = EXTRACT_TYPE_REGEXP.exec(type) + const isFolder = exp.charCodeAt(exp.length - 1) === slashCode; - // get extensions - var exts = match && exports.extensions[match[1].toLowerCase()] + if (isFolder !== expectFolder) { + throw new Error( + expectFolder + ? `Expecting folder to folder mapping. ${JSON.stringify( + exp + )} should end with "/"` + : `Expecting file to file mapping. ${JSON.stringify( + exp + )} should not end with "/"` + ); + } +} - if (!exts || !exts.length) { - return false - } +/** + * @param {string} imp import target + * @param {boolean} expectFolder is folder expected + */ +function assertImportTarget(imp, expectFolder) { + const isFolder = imp.charCodeAt(imp.length - 1) === slashCode; - return exts[0] + if (isFolder !== expectFolder) { + throw new Error( + expectFolder + ? `Expecting folder to folder mapping. ${JSON.stringify( + imp + )} should end with "/"` + : `Expecting file to file mapping. ${JSON.stringify( + imp + )} should not end with "/"` + ); + } } /** - * Lookup the MIME type for a file path/extension. - * - * @param {string} path - * @return {boolean|string} + * Trying to match request to field + * @param {string} request request + * @param {PathTreeNode} treeRoot path tree root + * @returns {[MappingValue, number]|null} match or null, number is negative and one less when it's a folder mapping, number is request.length + 1 for direct mappings */ +function findMatch(request, treeRoot) { + if (request.length === 0) { + const value = treeRoot.files.get(""); -function lookup (path) { - if (!path || typeof path !== 'string') { - return false - } + return value ? [value, 1] : null; + } - // get the extension ("ext" or ".ext" or full path) - var extension = extname('x.' + path) - .toLowerCase() - .substr(1) + if ( + treeRoot.children === null && + treeRoot.folder === null && + treeRoot.wildcards === null + ) { + const value = treeRoot.files.get(request); - if (!extension) { - return false - } + return value ? [value, request.length + 1] : null; + } - return exports.types[extension] || false -} + let node = treeRoot; + let lastNonSlashIndex = 0; + let slashIndex = request.indexOf("/", 0); -/** - * Populate the extensions and types maps. - * @private - */ + /** @type {[MappingValue, number]|null} */ + let lastFolderMatch = null; -function populateMaps (extensions, types) { - // source preference (least -> most) - var preference = ['nginx', 'apache', undefined, 'iana'] + const applyFolderMapping = () => { + const folderMapping = node.folder; + if (folderMapping) { + if (lastFolderMatch) { + lastFolderMatch[0] = folderMapping; + lastFolderMatch[1] = -lastNonSlashIndex - 1; + } else { + lastFolderMatch = [folderMapping, -lastNonSlashIndex - 1]; + } + } + }; - Object.keys(db).forEach(function forEachMimeType (type) { - var mime = db[type] - var exts = mime.extensions + const applyWildcardMappings = (wildcardMappings, remainingRequest) => { + if (wildcardMappings) { + for (const [key, target] of wildcardMappings) { + if (remainingRequest.startsWith(key)) { + if (!lastFolderMatch) { + lastFolderMatch = [target, lastNonSlashIndex + key.length]; + } else if (lastFolderMatch[1] < lastNonSlashIndex + key.length) { + lastFolderMatch[0] = target; + lastFolderMatch[1] = lastNonSlashIndex + key.length; + } + } + } + } + }; - if (!exts || !exts.length) { - return - } + while (slashIndex !== -1) { + applyFolderMapping(); - // mime -> extensions - extensions[type] = exts + const wildcardMappings = node.wildcards; - // extension -> mime - for (var i = 0; i < exts.length; i++) { - var extension = exts[i] + if (!wildcardMappings && node.children === null) return lastFolderMatch; - if (types[extension]) { - var from = preference.indexOf(db[types[extension]].source) - var to = preference.indexOf(mime.source) + const folder = request.slice(lastNonSlashIndex, slashIndex); - if (types[extension] !== 'application/octet-stream' && - (from > to || (from === to && types[extension].substr(0, 12) === 'application/'))) { - // skip the remapping - continue - } - } + applyWildcardMappings(wildcardMappings, folder); - // set the extension -> mime - types[extension] = type - } - }) -} + if (node.children === null) return lastFolderMatch; + const newNode = node.children.get(folder); -/***/ }), + if (!newNode) { + return lastFolderMatch; + } -/***/ 28339: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + node = newNode; + lastNonSlashIndex = slashIndex + 1; + slashIndex = request.indexOf("/", lastNonSlashIndex); + } -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ + const remainingRequest = + lastNonSlashIndex > 0 ? request.slice(lastNonSlashIndex) : request; + const value = node.files.get(remainingRequest); -const Hook = __webpack_require__(36591); -const HookCodeFactory = __webpack_require__(85572); + if (value) { + return [value, request.length + 1]; + } -class AsyncParallelBailHookCodeFactory extends HookCodeFactory { - content({ onError, onResult, onDone }) { - let code = ""; - code += `var _results = new Array(${this.options.taps.length});\n`; - code += "var _checkDone = function() {\n"; - code += "for(var i = 0; i < _results.length; i++) {\n"; - code += "var item = _results[i];\n"; - code += "if(item === undefined) return false;\n"; - code += "if(item.result !== undefined) {\n"; - code += onResult("item.result"); - code += "return true;\n"; - code += "}\n"; - code += "if(item.error) {\n"; - code += onError("item.error"); - code += "return true;\n"; - code += "}\n"; - code += "}\n"; - code += "return false;\n"; - code += "}\n"; - code += this.callTapsParallel({ - onError: (i, err, done, doneBreak) => { - let code = ""; - code += `if(${i} < _results.length && ((_results.length = ${i + - 1}), (_results[${i}] = { error: ${err} }), _checkDone())) {\n`; - code += doneBreak(true); - code += "} else {\n"; - code += done(); - code += "}\n"; - return code; - }, - onResult: (i, result, done, doneBreak) => { - let code = ""; - code += `if(${i} < _results.length && (${result} !== undefined && (_results.length = ${i + - 1}), (_results[${i}] = { result: ${result} }), _checkDone())) {\n`; - code += doneBreak(true); - code += "} else {\n"; - code += done(); - code += "}\n"; - return code; - }, - onTap: (i, run, done, doneBreak) => { - let code = ""; - if (i > 0) { - code += `if(${i} >= _results.length) {\n`; - code += done(); - code += "} else {\n"; - } - code += run(); - if (i > 0) code += "}\n"; - return code; - }, - onDone - }); - return code; + applyFolderMapping(); + + applyWildcardMappings(node.wildcards, remainingRequest); + + return lastFolderMatch; +} + +/** + * @param {ConditionalMapping|DirectMapping|null} mapping mapping + * @returns {boolean} is conditional mapping + */ +function isConditionalMapping(mapping) { + return ( + mapping !== null && typeof mapping === "object" && !Array.isArray(mapping) + ); +} + +/** + * @param {string|undefined} remainingRequest remaining request when folder mapping, undefined for file mappings + * @param {boolean} subpathMapping true, for subpath mappings + * @param {DirectMapping|null} mappingTarget direct export + * @param {Set} conditionNames condition names + * @param {(d: string, f: boolean) => void} assert asserting direct value + * @returns {string[]} mapping result + */ +function directMapping( + remainingRequest, + subpathMapping, + mappingTarget, + conditionNames, + assert +) { + if (mappingTarget === null) return []; + + if (typeof mappingTarget === "string") { + return [ + targetMapping(remainingRequest, subpathMapping, mappingTarget, assert) + ]; + } + + const targets = []; + + for (const exp of mappingTarget) { + if (typeof exp === "string") { + targets.push( + targetMapping(remainingRequest, subpathMapping, exp, assert) + ); + continue; + } + + const mapping = conditionalMapping(exp, conditionNames); + if (!mapping) continue; + const innerExports = directMapping( + remainingRequest, + subpathMapping, + mapping, + conditionNames, + assert + ); + for (const innerExport of innerExports) { + targets.push(innerExport); + } } -} - -const factory = new AsyncParallelBailHookCodeFactory(); - -const COMPILE = function(options) { - factory.setup(this, options); - return factory.create(options); -}; -function AsyncParallelBailHook(args = [], name = undefined) { - const hook = new Hook(args, name); - hook.constructor = AsyncParallelBailHook; - hook.compile = COMPILE; - hook._call = undefined; - hook.call = undefined; - return hook; + return targets; } -AsyncParallelBailHook.prototype = null; +/** + * @param {string|undefined} remainingRequest remaining request when folder mapping, undefined for file mappings + * @param {boolean} subpathMapping true, for subpath mappings + * @param {string} mappingTarget direct export + * @param {(d: string, f: boolean) => void} assert asserting direct value + * @returns {string} mapping result + */ +function targetMapping( + remainingRequest, + subpathMapping, + mappingTarget, + assert +) { + if (remainingRequest === undefined) { + assert(mappingTarget, false); + return mappingTarget; + } + if (subpathMapping) { + assert(mappingTarget, true); + return mappingTarget + remainingRequest; + } + assert(mappingTarget, false); + return mappingTarget.replace(/\*/g, remainingRequest.replace(/\$/g, "$$")); +} -module.exports = AsyncParallelBailHook; +/** + * @param {ConditionalMapping} conditionalMapping_ conditional mapping + * @param {Set} conditionNames condition names + * @returns {DirectMapping|null} direct mapping if found + */ +function conditionalMapping(conditionalMapping_, conditionNames) { + /** @type {[ConditionalMapping, string[], number][]} */ + let lookup = [[conditionalMapping_, Object.keys(conditionalMapping_), 0]]; + loop: while (lookup.length > 0) { + const [mapping, conditions, j] = lookup[lookup.length - 1]; + const last = conditions.length - 1; -/***/ }), + for (let i = j; i < conditions.length; i++) { + const condition = conditions[i]; -/***/ 82890: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + // assert default. Could be last only + if (i !== last) { + if (condition === "default") { + throw new Error("Default condition should be last one"); + } + } else if (condition === "default") { + const innerMapping = mapping[condition]; + // is nested + if (isConditionalMapping(innerMapping)) { + const conditionalMapping = /** @type {ConditionalMapping} */ (innerMapping); + lookup[lookup.length - 1][2] = i + 1; + lookup.push([conditionalMapping, Object.keys(conditionalMapping), 0]); + continue loop; + } -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ + return /** @type {DirectMapping} */ (innerMapping); + } + if (conditionNames.has(condition)) { + const innerMapping = mapping[condition]; + // is nested + if (isConditionalMapping(innerMapping)) { + const conditionalMapping = /** @type {ConditionalMapping} */ (innerMapping); + lookup[lookup.length - 1][2] = i + 1; + lookup.push([conditionalMapping, Object.keys(conditionalMapping), 0]); + continue loop; + } -const Hook = __webpack_require__(36591); -const HookCodeFactory = __webpack_require__(85572); + return /** @type {DirectMapping} */ (innerMapping); + } + } -class AsyncParallelHookCodeFactory extends HookCodeFactory { - content({ onError, onDone }) { - return this.callTapsParallel({ - onError: (i, err, done, doneBreak) => onError(err) + doneBreak(true), - onDone - }); + lookup.pop(); } -} - -const factory = new AsyncParallelHookCodeFactory(); - -const COMPILE = function(options) { - factory.setup(this, options); - return factory.create(options); -}; -function AsyncParallelHook(args = [], name = undefined) { - const hook = new Hook(args, name); - hook.constructor = AsyncParallelHook; - hook.compile = COMPILE; - hook._call = undefined; - hook.call = undefined; - return hook; + return null; } -AsyncParallelHook.prototype = null; - -module.exports = AsyncParallelHook; +/** + * Internal helper to create path tree node + * to ensure that each node gets the same hidden class + * @returns {PathTreeNode} node + */ +function createNode() { + return { + children: null, + folder: null, + wildcards: null, + files: new Map() + }; +} +/** + * Internal helper for building path tree + * @param {PathTreeNode} root root + * @param {string} path path + * @param {MappingValue} target target + */ +function walkPath(root, path, target) { + if (path.length === 0) { + root.folder = target; + return; + } -/***/ }), + let node = root; + // Typical path tree can looks like + // root + // - files: ["a.js", "b.js"] + // - children: + // node1: + // - files: ["a.js", "b.js"] + let lastNonSlashIndex = 0; + let slashIndex = path.indexOf("/", 0); -/***/ 97681: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + while (slashIndex !== -1) { + const folder = path.slice(lastNonSlashIndex, slashIndex); + let newNode; -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ + if (node.children === null) { + newNode = createNode(); + node.children = new Map(); + node.children.set(folder, newNode); + } else { + newNode = node.children.get(folder); + if (!newNode) { + newNode = createNode(); + node.children.set(folder, newNode); + } + } -const Hook = __webpack_require__(36591); -const HookCodeFactory = __webpack_require__(85572); + node = newNode; + lastNonSlashIndex = slashIndex + 1; + slashIndex = path.indexOf("/", lastNonSlashIndex); + } -class AsyncSeriesBailHookCodeFactory extends HookCodeFactory { - content({ onError, onResult, resultReturns, onDone }) { - return this.callTapsSeries({ - onError: (i, err, next, doneBreak) => onError(err) + doneBreak(true), - onResult: (i, result, next) => - `if(${result} !== undefined) {\n${onResult( - result - )}\n} else {\n${next()}}\n`, - resultReturns, - onDone - }); + if (lastNonSlashIndex >= path.length) { + node.folder = target; + } else { + const file = lastNonSlashIndex > 0 ? path.slice(lastNonSlashIndex) : path; + if (file.endsWith("*")) { + if (node.wildcards === null) node.wildcards = new Map(); + node.wildcards.set(file.slice(0, -1), target); + } else { + node.files.set(file, target); + } } } -const factory = new AsyncSeriesBailHookCodeFactory(); +/** + * @param {ExportsField} field exports field + * @returns {PathTreeNode} tree root + */ +function buildExportsFieldPathTree(field) { + const root = createNode(); -const COMPILE = function(options) { - factory.setup(this, options); - return factory.create(options); -}; + // handle syntax sugar, if exports field is direct mapping for "." + if (typeof field === "string") { + root.files.set("", field); -function AsyncSeriesBailHook(args = [], name = undefined) { - const hook = new Hook(args, name); - hook.constructor = AsyncSeriesBailHook; - hook.compile = COMPILE; - hook._call = undefined; - hook.call = undefined; - return hook; -} + return root; + } else if (Array.isArray(field)) { + root.files.set("", field.slice()); -AsyncSeriesBailHook.prototype = null; + return root; + } -module.exports = AsyncSeriesBailHook; + const keys = Object.keys(field); + for (let i = 0; i < keys.length; i++) { + const key = keys[i]; -/***/ }), + if (key.charCodeAt(0) !== dotCode) { + // handle syntax sugar, if exports field is conditional mapping for "." + if (i === 0) { + while (i < keys.length) { + const charCode = keys[i].charCodeAt(0); + if (charCode === dotCode || charCode === slashCode) { + throw new Error( + `Exports field key should be relative path and start with "." (key: ${JSON.stringify( + key + )})` + ); + } + i++; + } -/***/ 45146: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + root.files.set("", field); + return root; + } -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ + throw new Error( + `Exports field key should be relative path and start with "." (key: ${JSON.stringify( + key + )})` + ); + } + if (key.length === 1) { + root.files.set("", field[key]); + continue; + } -const Hook = __webpack_require__(36591); -const HookCodeFactory = __webpack_require__(85572); + if (key.charCodeAt(1) !== slashCode) { + throw new Error( + `Exports field key should be relative path and start with "./" (key: ${JSON.stringify( + key + )})` + ); + } -class AsyncSeriesHookCodeFactory extends HookCodeFactory { - content({ onError, onDone }) { - return this.callTapsSeries({ - onError: (i, err, next, doneBreak) => onError(err) + doneBreak(true), - onDone - }); + walkPath(root, key.slice(2), field[key]); } -} - -const factory = new AsyncSeriesHookCodeFactory(); - -const COMPILE = function(options) { - factory.setup(this, options); - return factory.create(options); -}; -function AsyncSeriesHook(args = [], name = undefined) { - const hook = new Hook(args, name); - hook.constructor = AsyncSeriesHook; - hook.compile = COMPILE; - hook._call = undefined; - hook.call = undefined; - return hook; + return root; } -AsyncSeriesHook.prototype = null; - -module.exports = AsyncSeriesHook; - +/** + * @param {ImportsField} field imports field + * @returns {PathTreeNode} root + */ +function buildImportsFieldPathTree(field) { + const root = createNode(); -/***/ }), + const keys = Object.keys(field); -/***/ 5463: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + for (let i = 0; i < keys.length; i++) { + const key = keys[i]; -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ + if (key.charCodeAt(0) !== hashCode) { + throw new Error( + `Imports field key should start with "#" (key: ${JSON.stringify(key)})` + ); + } + if (key.length === 1) { + throw new Error( + `Imports field key should have at least 2 characters (key: ${JSON.stringify( + key + )})` + ); + } -const Hook = __webpack_require__(36591); -const HookCodeFactory = __webpack_require__(85572); + if (key.charCodeAt(1) === slashCode) { + throw new Error( + `Imports field key should not start with "#/" (key: ${JSON.stringify( + key + )})` + ); + } -class AsyncSeriesLoopHookCodeFactory extends HookCodeFactory { - content({ onError, onDone }) { - return this.callTapsLooping({ - onError: (i, err, next, doneBreak) => onError(err) + doneBreak(true), - onDone - }); + walkPath(root, key.slice(1), field[key]); } -} - -const factory = new AsyncSeriesLoopHookCodeFactory(); - -const COMPILE = function(options) { - factory.setup(this, options); - return factory.create(options); -}; -function AsyncSeriesLoopHook(args = [], name = undefined) { - const hook = new Hook(args, name); - hook.constructor = AsyncSeriesLoopHook; - hook.compile = COMPILE; - hook._call = undefined; - hook.call = undefined; - return hook; + return root; } -AsyncSeriesLoopHook.prototype = null; - -module.exports = AsyncSeriesLoopHook; - /***/ }), -/***/ 73448: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { +/***/ 98623: +/***/ (function(module) { "use strict"; /* MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra + Author Ivan Kopeykin @vankop */ -const Hook = __webpack_require__(36591); -const HookCodeFactory = __webpack_require__(85572); -class AsyncSeriesWaterfallHookCodeFactory extends HookCodeFactory { - content({ onError, onResult, onDone }) { - return this.callTapsSeries({ - onError: (i, err, next, doneBreak) => onError(err) + doneBreak(true), - onResult: (i, result, next) => { - let code = ""; - code += `if(${result} !== undefined) {\n`; - code += `${this._args[0]} = ${result};\n`; - code += `}\n`; - code += next(); - return code; - }, - onDone: () => onResult(this._args[0]) - }); - } -} +const PATH_QUERY_FRAGMENT_REGEXP = /^(#?(?:\0.|[^?#\0])*)(\?(?:\0.|[^#\0])*)?(#.*)?$/; -const factory = new AsyncSeriesWaterfallHookCodeFactory(); +/** + * @param {string} identifier identifier + * @returns {[string, string, string]|null} parsed identifier + */ +function parseIdentifier(identifier) { + const match = PATH_QUERY_FRAGMENT_REGEXP.exec(identifier); -const COMPILE = function(options) { - factory.setup(this, options); - return factory.create(options); -}; + if (!match) return null; -function AsyncSeriesWaterfallHook(args = [], name = undefined) { - if (args.length < 1) - throw new Error("Waterfall hooks must have at least one argument"); - const hook = new Hook(args, name); - hook.constructor = AsyncSeriesWaterfallHook; - hook.compile = COMPILE; - hook._call = undefined; - hook.call = undefined; - return hook; + return [ + match[1].replace(/\0(.)/g, "$1"), + match[2] ? match[2].replace(/\0(.)/g, "$1") : "", + match[3] || "" + ]; } -AsyncSeriesWaterfallHook.prototype = null; - -module.exports = AsyncSeriesWaterfallHook; +module.exports.parseIdentifier = parseIdentifier; /***/ }), -/***/ 36591: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { +/***/ 69821: +/***/ (function(__unused_webpack_module, exports, __webpack_require__) { "use strict"; /* @@ -141300,725 +141870,942 @@ module.exports = AsyncSeriesWaterfallHook; */ -const util = __webpack_require__(31669); -const deprecateContext = util.deprecate(() => {}, -"Hook.context is deprecated and will be removed"); +const path = __webpack_require__(85622); -const CALL_DELEGATE = function(...args) { - this.call = this._createCall("sync"); - return this.call(...args); -}; -const CALL_ASYNC_DELEGATE = function(...args) { - this.callAsync = this._createCall("async"); - return this.callAsync(...args); -}; -const PROMISE_DELEGATE = function(...args) { - this.promise = this._createCall("promise"); - return this.promise(...args); +const CHAR_HASH = "#".charCodeAt(0); +const CHAR_SLASH = "/".charCodeAt(0); +const CHAR_BACKSLASH = "\\".charCodeAt(0); +const CHAR_A = "A".charCodeAt(0); +const CHAR_Z = "Z".charCodeAt(0); +const CHAR_LOWER_A = "a".charCodeAt(0); +const CHAR_LOWER_Z = "z".charCodeAt(0); +const CHAR_DOT = ".".charCodeAt(0); +const CHAR_COLON = ":".charCodeAt(0); + +const posixNormalize = path.posix.normalize; +const winNormalize = path.win32.normalize; + +/** + * @enum {number} + */ +const PathType = Object.freeze({ + Empty: 0, + Normal: 1, + Relative: 2, + AbsoluteWin: 3, + AbsolutePosix: 4, + Internal: 5 +}); +exports.PathType = PathType; + +/** + * @param {string} p a path + * @returns {PathType} type of path + */ +const getType = p => { + switch (p.length) { + case 0: + return PathType.Empty; + case 1: { + const c0 = p.charCodeAt(0); + switch (c0) { + case CHAR_DOT: + return PathType.Relative; + case CHAR_SLASH: + return PathType.AbsolutePosix; + case CHAR_HASH: + return PathType.Internal; + } + return PathType.Normal; + } + case 2: { + const c0 = p.charCodeAt(0); + switch (c0) { + case CHAR_DOT: { + const c1 = p.charCodeAt(1); + switch (c1) { + case CHAR_DOT: + case CHAR_SLASH: + return PathType.Relative; + } + return PathType.Normal; + } + case CHAR_SLASH: + return PathType.AbsolutePosix; + case CHAR_HASH: + return PathType.Internal; + } + const c1 = p.charCodeAt(1); + if (c1 === CHAR_COLON) { + if ( + (c0 >= CHAR_A && c0 <= CHAR_Z) || + (c0 >= CHAR_LOWER_A && c0 <= CHAR_LOWER_Z) + ) { + return PathType.AbsoluteWin; + } + } + return PathType.Normal; + } + } + const c0 = p.charCodeAt(0); + switch (c0) { + case CHAR_DOT: { + const c1 = p.charCodeAt(1); + switch (c1) { + case CHAR_SLASH: + return PathType.Relative; + case CHAR_DOT: { + const c2 = p.charCodeAt(2); + if (c2 === CHAR_SLASH) return PathType.Relative; + return PathType.Normal; + } + } + return PathType.Normal; + } + case CHAR_SLASH: + return PathType.AbsolutePosix; + case CHAR_HASH: + return PathType.Internal; + } + const c1 = p.charCodeAt(1); + if (c1 === CHAR_COLON) { + const c2 = p.charCodeAt(2); + if ( + (c2 === CHAR_BACKSLASH || c2 === CHAR_SLASH) && + ((c0 >= CHAR_A && c0 <= CHAR_Z) || + (c0 >= CHAR_LOWER_A && c0 <= CHAR_LOWER_Z)) + ) { + return PathType.AbsoluteWin; + } + } + return PathType.Normal; }; +exports.getType = getType; -class Hook { - constructor(args = [], name = undefined) { - this._args = args; - this.name = name; - this.taps = []; - this.interceptors = []; - this._call = CALL_DELEGATE; - this.call = CALL_DELEGATE; - this._callAsync = CALL_ASYNC_DELEGATE; - this.callAsync = CALL_ASYNC_DELEGATE; - this._promise = PROMISE_DELEGATE; - this.promise = PROMISE_DELEGATE; - this._x = undefined; - - this.compile = this.compile; - this.tap = this.tap; - this.tapAsync = this.tapAsync; - this.tapPromise = this.tapPromise; +/** + * @param {string} p a path + * @returns {string} the normalized path + */ +const normalize = p => { + switch (getType(p)) { + case PathType.Empty: + return p; + case PathType.AbsoluteWin: + return winNormalize(p); + case PathType.Relative: { + const r = posixNormalize(p); + return getType(r) === PathType.Relative ? r : `./${r}`; + } } + return posixNormalize(p); +}; +exports.normalize = normalize; - compile(options) { - throw new Error("Abstract: should be overridden"); +/** + * @param {string} rootPath the root path + * @param {string | undefined} request the request path + * @returns {string} the joined path + */ +const join = (rootPath, request) => { + if (!request) return normalize(rootPath); + const requestType = getType(request); + switch (requestType) { + case PathType.AbsolutePosix: + return posixNormalize(request); + case PathType.AbsoluteWin: + return winNormalize(request); } - - _createCall(type) { - return this.compile({ - taps: this.taps, - interceptors: this.interceptors, - args: this._args, - type: type - }); + switch (getType(rootPath)) { + case PathType.Normal: + case PathType.Relative: + case PathType.AbsolutePosix: + return posixNormalize(`${rootPath}/${request}`); + case PathType.AbsoluteWin: + return winNormalize(`${rootPath}\\${request}`); } - - _tap(type, options, fn) { - if (typeof options === "string") { - options = { - name: options.trim() - }; - } else if (typeof options !== "object" || options === null) { - throw new Error("Invalid tap options"); - } - if (typeof options.name !== "string" || options.name === "") { - throw new Error("Missing name for tap"); - } - if (typeof options.context !== "undefined") { - deprecateContext(); + switch (requestType) { + case PathType.Empty: + return rootPath; + case PathType.Relative: { + const r = posixNormalize(rootPath); + return getType(r) === PathType.Relative ? r : `./${r}`; } - options = Object.assign({ type, fn }, options); - options = this._runRegisterInterceptors(options); - this._insert(options); } + return posixNormalize(rootPath); +}; +exports.join = join; - tap(options, fn) { - this._tap("sync", options, fn); - } +const joinCache = new Map(); - tapAsync(options, fn) { - this._tap("async", options, fn); +/** + * @param {string} rootPath the root path + * @param {string | undefined} request the request path + * @returns {string} the joined path + */ +const cachedJoin = (rootPath, request) => { + let cacheEntry; + let cache = joinCache.get(rootPath); + if (cache === undefined) { + joinCache.set(rootPath, (cache = new Map())); + } else { + cacheEntry = cache.get(request); + if (cacheEntry !== undefined) return cacheEntry; } + cacheEntry = join(rootPath, request); + cache.set(request, cacheEntry); + return cacheEntry; +}; +exports.cachedJoin = cachedJoin; - tapPromise(options, fn) { - this._tap("promise", options, fn); - } +const checkExportsFieldTarget = relativePath => { + let lastNonSlashIndex = 2; + let slashIndex = relativePath.indexOf("/", 2); + let cd = 0; - _runRegisterInterceptors(options) { - for (const interceptor of this.interceptors) { - if (interceptor.register) { - const newOptions = interceptor.register(options); - if (newOptions !== undefined) { - options = newOptions; - } + while (slashIndex !== -1) { + const folder = relativePath.slice(lastNonSlashIndex, slashIndex); + + switch (folder) { + case "..": { + cd--; + if (cd < 0) + return new Error( + `Trying to access out of package scope. Requesting ${relativePath}` + ); + break; } + default: + cd++; + break; } - return options; + + lastNonSlashIndex = slashIndex + 1; + slashIndex = relativePath.indexOf("/", lastNonSlashIndex); } +}; +exports.checkExportsFieldTarget = checkExportsFieldTarget; - withOptions(options) { - const mergeOptions = opt => - Object.assign({}, options, typeof opt === "string" ? { name: opt } : opt); - return { - name: this.name, - tap: (opt, fn) => this.tap(mergeOptions(opt), fn), - tapAsync: (opt, fn) => this.tapAsync(mergeOptions(opt), fn), - tapPromise: (opt, fn) => this.tapPromise(mergeOptions(opt), fn), - intercept: interceptor => this.intercept(interceptor), - isUsed: () => this.isUsed(), - withOptions: opt => this.withOptions(mergeOptions(opt)) - }; - } +/***/ }), - isUsed() { - return this.taps.length > 0 || this.interceptors.length > 0; - } +/***/ 83798: +/***/ (function(module) { - intercept(interceptor) { - this._resetCompilation(); - this.interceptors.push(Object.assign({}, interceptor)); - if (interceptor.register) { - for (let i = 0; i < this.taps.length; i++) { - this.taps[i] = interceptor.register(this.taps[i]); - } - } - } +"use strict"; - _resetCompilation() { - this.call = this._call; - this.callAsync = this._callAsync; - this.promise = this._promise; - } - _insert(item) { - this._resetCompilation(); - let before; - if (typeof item.before === "string") { - before = new Set([item.before]); - } else if (Array.isArray(item.before)) { - before = new Set(item.before); - } - let stage = 0; - if (typeof item.stage === "number") { - stage = item.stage; - } - let i = this.taps.length; - while (i > 0) { - i--; - const x = this.taps[i]; - this.taps[i + 1] = x; - const xStage = x.stage || 0; - if (before) { - if (before.has(x.name)) { - before.delete(x.name); - continue; - } - if (before.size > 0) { - continue; - } - } - if (xStage > stage) { - continue; - } - i++; - break; - } - this.taps[i] = item; +class LoadingLoaderError extends Error { + constructor(message) { + super(message); + this.name = "LoaderRunnerError"; + Error.captureStackTrace(this, this.constructor); } } -Object.setPrototypeOf(Hook.prototype, null); - -module.exports = Hook; +module.exports = LoadingLoaderError; /***/ }), -/***/ 85572: -/***/ (function(module) { +/***/ 67578: +/***/ (function(__unused_webpack_module, exports, __webpack_require__) { -"use strict"; /* MIT License http://www.opensource.org/licenses/mit-license.php Author Tobias Koppers @sokra */ +var fs = __webpack_require__(35747); +var readFile = fs.readFile.bind(fs); +var loadLoader = __webpack_require__(63395); - -class HookCodeFactory { - constructor(config) { - this.config = config; - this.options = undefined; - this._args = undefined; +function utf8BufferToString(buf) { + var str = buf.toString("utf-8"); + if(str.charCodeAt(0) === 0xFEFF) { + return str.substr(1); + } else { + return str; } +} - create(options) { - this.init(options); - let fn; - switch (this.options.type) { - case "sync": - fn = new Function( - this.args(), - '"use strict";\n' + - this.header() + - this.contentWithInterceptors({ - onError: err => `throw ${err};\n`, - onResult: result => `return ${result};\n`, - resultReturns: true, - onDone: () => "", - rethrowIfPossible: true - }) - ); - break; - case "async": - fn = new Function( - this.args({ - after: "_callback" - }), - '"use strict";\n' + - this.header() + - this.contentWithInterceptors({ - onError: err => `_callback(${err});\n`, - onResult: result => `_callback(null, ${result});\n`, - onDone: () => "_callback();\n" - }) - ); - break; - case "promise": - let errorHelperUsed = false; - const content = this.contentWithInterceptors({ - onError: err => { - errorHelperUsed = true; - return `_error(${err});\n`; - }, - onResult: result => `_resolve(${result});\n`, - onDone: () => "_resolve();\n" - }); - let code = ""; - code += '"use strict";\n'; - code += this.header(); - code += "return new Promise((function(_resolve, _reject) {\n"; - if (errorHelperUsed) { - code += "var _sync = true;\n"; - code += "function _error(_err) {\n"; - code += "if(_sync)\n"; - code += - "_resolve(Promise.resolve().then((function() { throw _err; })));\n"; - code += "else\n"; - code += "_reject(_err);\n"; - code += "};\n"; - } - code += content; - if (errorHelperUsed) { - code += "_sync = false;\n"; - } - code += "}));\n"; - fn = new Function(this.args(), code); - break; - } - this.deinit(); - return fn; - } +const PATH_QUERY_FRAGMENT_REGEXP = /^((?:\0.|[^?#\0])*)(\?(?:\0.|[^#\0])*)?(#.*)?$/; - setup(instance, options) { - instance._x = options.taps.map(t => t.fn); - } +/** + * @param {string} str the path with query and fragment + * @returns {{ path: string, query: string, fragment: string }} parsed parts + */ +function parsePathQueryFragment(str) { + var match = PATH_QUERY_FRAGMENT_REGEXP.exec(str); + return { + path: match[1].replace(/\0(.)/g, "$1"), + query: match[2] ? match[2].replace(/\0(.)/g, "$1") : "", + fragment: match[3] || "" + }; +} - /** - * @param {{ type: "sync" | "promise" | "async", taps: Array, interceptors: Array }} options - */ - init(options) { - this.options = options; - this._args = options.args.slice(); - } +function dirname(path) { + if(path === "/") return "/"; + var i = path.lastIndexOf("/"); + var j = path.lastIndexOf("\\"); + var i2 = path.indexOf("/"); + var j2 = path.indexOf("\\"); + var idx = i > j ? i : j; + var idx2 = i > j ? i2 : j2; + if(idx < 0) return path; + if(idx === idx2) return path.substr(0, idx + 1); + return path.substr(0, idx); +} - deinit() { - this.options = undefined; - this._args = undefined; +function createLoaderObject(loader) { + var obj = { + path: null, + query: null, + fragment: null, + options: null, + ident: null, + normal: null, + pitch: null, + raw: null, + data: null, + pitchExecuted: false, + normalExecuted: false + }; + Object.defineProperty(obj, "request", { + enumerable: true, + get: function() { + return obj.path.replace(/#/g, "\0#") + obj.query.replace(/#/g, "\0#") + obj.fragment; + }, + set: function(value) { + if(typeof value === "string") { + var splittedRequest = parsePathQueryFragment(value); + obj.path = splittedRequest.path; + obj.query = splittedRequest.query; + obj.fragment = splittedRequest.fragment; + obj.options = undefined; + obj.ident = undefined; + } else { + if(!value.loader) + throw new Error("request should be a string or object with loader and options (" + JSON.stringify(value) + ")"); + obj.path = value.loader; + obj.fragment = value.fragment || ""; + obj.type = value.type; + obj.options = value.options; + obj.ident = value.ident; + if(obj.options === null) + obj.query = ""; + else if(obj.options === undefined) + obj.query = ""; + else if(typeof obj.options === "string") + obj.query = "?" + obj.options; + else if(obj.ident) + obj.query = "??" + obj.ident; + else if(typeof obj.options === "object" && obj.options.ident) + obj.query = "??" + obj.options.ident; + else + obj.query = "?" + JSON.stringify(obj.options); + } + } + }); + obj.request = loader; + if(Object.preventExtensions) { + Object.preventExtensions(obj); } + return obj; +} - contentWithInterceptors(options) { - if (this.options.interceptors.length > 0) { - const onError = options.onError; - const onResult = options.onResult; - const onDone = options.onDone; - let code = ""; - for (let i = 0; i < this.options.interceptors.length; i++) { - const interceptor = this.options.interceptors[i]; - if (interceptor.call) { - code += `${this.getInterceptor(i)}.call(${this.args({ - before: interceptor.context ? "_context" : undefined - })});\n`; - } - } - code += this.content( - Object.assign(options, { - onError: - onError && - (err => { - let code = ""; - for (let i = 0; i < this.options.interceptors.length; i++) { - const interceptor = this.options.interceptors[i]; - if (interceptor.error) { - code += `${this.getInterceptor(i)}.error(${err});\n`; - } - } - code += onError(err); - return code; - }), - onResult: - onResult && - (result => { - let code = ""; - for (let i = 0; i < this.options.interceptors.length; i++) { - const interceptor = this.options.interceptors[i]; - if (interceptor.result) { - code += `${this.getInterceptor(i)}.result(${result});\n`; - } - } - code += onResult(result); - return code; - }), - onDone: - onDone && - (() => { - let code = ""; - for (let i = 0; i < this.options.interceptors.length; i++) { - const interceptor = this.options.interceptors[i]; - if (interceptor.done) { - code += `${this.getInterceptor(i)}.done();\n`; - } - } - code += onDone(); - return code; - }) - }) - ); - return code; - } else { - return this.content(options); +function runSyncOrAsync(fn, context, args, callback) { + var isSync = true; + var isDone = false; + var isError = false; // internal error + var reportedError = false; + context.async = function async() { + if(isDone) { + if(reportedError) return; // ignore + throw new Error("async(): The callback was already called."); } - } - - header() { - let code = ""; - if (this.needContext()) { - code += "var _context = {};\n"; - } else { - code += "var _context;\n"; + isSync = false; + return innerCallback; + }; + var innerCallback = context.callback = function() { + if(isDone) { + if(reportedError) return; // ignore + throw new Error("callback(): The callback was already called."); } - code += "var _x = this._x;\n"; - if (this.options.interceptors.length > 0) { - code += "var _taps = this.taps;\n"; - code += "var _interceptors = this.interceptors;\n"; + isDone = true; + isSync = false; + try { + callback.apply(null, arguments); + } catch(e) { + isError = true; + throw e; } - return code; + }; + try { + var result = (function LOADER_EXECUTION() { + return fn.apply(context, args); + }()); + if(isSync) { + isDone = true; + if(result === undefined) + return callback(); + if(result && typeof result === "object" && typeof result.then === "function") { + return result.then(function(r) { + callback(null, r); + }, callback); + } + return callback(null, result); + } + } catch(e) { + if(isError) throw e; + if(isDone) { + // loader is already "done", so we cannot use the callback function + // for better debugging we print the error on the console + if(typeof e === "object" && e.stack) console.error(e.stack); + else console.error(e); + return; + } + isDone = true; + reportedError = true; + callback(e); } - needContext() { - for (const tap of this.options.taps) if (tap.context) return true; - return false; +} + +function convertArgs(args, raw) { + if(!raw && Buffer.isBuffer(args[0])) + args[0] = utf8BufferToString(args[0]); + else if(raw && typeof args[0] === "string") + args[0] = Buffer.from(args[0], "utf-8"); +} + +function iteratePitchingLoaders(options, loaderContext, callback) { + // abort after last loader + if(loaderContext.loaderIndex >= loaderContext.loaders.length) + return processResource(options, loaderContext, callback); + + var currentLoaderObject = loaderContext.loaders[loaderContext.loaderIndex]; + + // iterate + if(currentLoaderObject.pitchExecuted) { + loaderContext.loaderIndex++; + return iteratePitchingLoaders(options, loaderContext, callback); } - callTap(tapIndex, { onError, onResult, onDone, rethrowIfPossible }) { - let code = ""; - let hasTapCached = false; - for (let i = 0; i < this.options.interceptors.length; i++) { - const interceptor = this.options.interceptors[i]; - if (interceptor.tap) { - if (!hasTapCached) { - code += `var _tap${tapIndex} = ${this.getTap(tapIndex)};\n`; - hasTapCached = true; - } - code += `${this.getInterceptor(i)}.tap(${ - interceptor.context ? "_context, " : "" - }_tap${tapIndex});\n`; - } + // load loader module + loadLoader(currentLoaderObject, function(err) { + if(err) { + loaderContext.cacheable(false); + return callback(err); } - code += `var _fn${tapIndex} = ${this.getTapFn(tapIndex)};\n`; - const tap = this.options.taps[tapIndex]; - switch (tap.type) { - case "sync": - if (!rethrowIfPossible) { - code += `var _hasError${tapIndex} = false;\n`; - code += "try {\n"; - } - if (onResult) { - code += `var _result${tapIndex} = _fn${tapIndex}(${this.args({ - before: tap.context ? "_context" : undefined - })});\n`; + var fn = currentLoaderObject.pitch; + currentLoaderObject.pitchExecuted = true; + if(!fn) return iteratePitchingLoaders(options, loaderContext, callback); + + runSyncOrAsync( + fn, + loaderContext, [loaderContext.remainingRequest, loaderContext.previousRequest, currentLoaderObject.data = {}], + function(err) { + if(err) return callback(err); + var args = Array.prototype.slice.call(arguments, 1); + // Determine whether to continue the pitching process based on + // argument values (as opposed to argument presence) in order + // to support synchronous and asynchronous usages. + var hasArg = args.some(function(value) { + return value !== undefined; + }); + if(hasArg) { + loaderContext.loaderIndex--; + iterateNormalLoaders(options, loaderContext, args, callback); } else { - code += `_fn${tapIndex}(${this.args({ - before: tap.context ? "_context" : undefined - })});\n`; - } - if (!rethrowIfPossible) { - code += "} catch(_err) {\n"; - code += `_hasError${tapIndex} = true;\n`; - code += onError("_err"); - code += "}\n"; - code += `if(!_hasError${tapIndex}) {\n`; - } - if (onResult) { - code += onResult(`_result${tapIndex}`); - } - if (onDone) { - code += onDone(); - } - if (!rethrowIfPossible) { - code += "}\n"; - } - break; - case "async": - let cbCode = ""; - if (onResult) - cbCode += `(function(_err${tapIndex}, _result${tapIndex}) {\n`; - else cbCode += `(function(_err${tapIndex}) {\n`; - cbCode += `if(_err${tapIndex}) {\n`; - cbCode += onError(`_err${tapIndex}`); - cbCode += "} else {\n"; - if (onResult) { - cbCode += onResult(`_result${tapIndex}`); - } - if (onDone) { - cbCode += onDone(); - } - cbCode += "}\n"; - cbCode += "})"; - code += `_fn${tapIndex}(${this.args({ - before: tap.context ? "_context" : undefined, - after: cbCode - })});\n`; - break; - case "promise": - code += `var _hasResult${tapIndex} = false;\n`; - code += `var _promise${tapIndex} = _fn${tapIndex}(${this.args({ - before: tap.context ? "_context" : undefined - })});\n`; - code += `if (!_promise${tapIndex} || !_promise${tapIndex}.then)\n`; - code += ` throw new Error('Tap function (tapPromise) did not return promise (returned ' + _promise${tapIndex} + ')');\n`; - code += `_promise${tapIndex}.then((function(_result${tapIndex}) {\n`; - code += `_hasResult${tapIndex} = true;\n`; - if (onResult) { - code += onResult(`_result${tapIndex}`); - } - if (onDone) { - code += onDone(); + iteratePitchingLoaders(options, loaderContext, callback); } - code += `}), function(_err${tapIndex}) {\n`; - code += `if(_hasResult${tapIndex}) throw _err${tapIndex};\n`; - code += onError(`_err${tapIndex}`); - code += "});\n"; - break; - } - return code; + } + ); + }); +} + +function processResource(options, loaderContext, callback) { + // set loader index to last loader + loaderContext.loaderIndex = loaderContext.loaders.length - 1; + + var resourcePath = loaderContext.resourcePath; + if(resourcePath) { + options.processResource(loaderContext, resourcePath, function(err, buffer) { + if(err) return callback(err); + options.resourceBuffer = buffer; + iterateNormalLoaders(options, loaderContext, [buffer], callback); + }); + } else { + iterateNormalLoaders(options, loaderContext, [null], callback); } +} - callTapsSeries({ - onError, - onResult, - resultReturns, - onDone, - doneReturns, - rethrowIfPossible - }) { - if (this.options.taps.length === 0) return onDone(); - const firstAsync = this.options.taps.findIndex(t => t.type !== "sync"); - const somethingReturns = resultReturns || doneReturns; - let code = ""; - let current = onDone; - let unrollCounter = 0; - for (let j = this.options.taps.length - 1; j >= 0; j--) { - const i = j; - const unroll = - current !== onDone && - (this.options.taps[i].type !== "sync" || unrollCounter++ > 20); - if (unroll) { - unrollCounter = 0; - code += `function _next${i}() {\n`; - code += current(); - code += `}\n`; - current = () => `${somethingReturns ? "return " : ""}_next${i}();\n`; - } - const done = current; - const doneBreak = skipDone => { - if (skipDone) return ""; - return onDone(); - }; - const content = this.callTap(i, { - onError: error => onError(i, error, done, doneBreak), - onResult: - onResult && - (result => { - return onResult(i, result, done, doneBreak); - }), - onDone: !onResult && done, - rethrowIfPossible: - rethrowIfPossible && (firstAsync < 0 || i < firstAsync) - }); - current = () => content; - } - code += current(); - return code; +function iterateNormalLoaders(options, loaderContext, args, callback) { + if(loaderContext.loaderIndex < 0) + return callback(null, args); + + var currentLoaderObject = loaderContext.loaders[loaderContext.loaderIndex]; + + // iterate + if(currentLoaderObject.normalExecuted) { + loaderContext.loaderIndex--; + return iterateNormalLoaders(options, loaderContext, args, callback); } - callTapsLooping({ onError, onDone, rethrowIfPossible }) { - if (this.options.taps.length === 0) return onDone(); - const syncOnly = this.options.taps.every(t => t.type === "sync"); - let code = ""; - if (!syncOnly) { - code += "var _looper = (function() {\n"; - code += "var _loopAsync = false;\n"; + var fn = currentLoaderObject.normal; + currentLoaderObject.normalExecuted = true; + if(!fn) { + return iterateNormalLoaders(options, loaderContext, args, callback); + } + + convertArgs(args, currentLoaderObject.raw); + + runSyncOrAsync(fn, loaderContext, args, function(err) { + if(err) return callback(err); + + var args = Array.prototype.slice.call(arguments, 1); + iterateNormalLoaders(options, loaderContext, args, callback); + }); +} + +exports.getContext = function getContext(resource) { + var path = parsePathQueryFragment(resource).path; + return dirname(path); +}; + +exports.runLoaders = function runLoaders(options, callback) { + // read options + var resource = options.resource || ""; + var loaders = options.loaders || []; + var loaderContext = options.context || {}; + var processResource = options.processResource || ((readResource, context, resource, callback) => { + context.addDependency(resource); + readResource(resource, callback); + }).bind(null, options.readResource || readFile); + + // + var splittedResource = resource && parsePathQueryFragment(resource); + var resourcePath = splittedResource ? splittedResource.path : undefined; + var resourceQuery = splittedResource ? splittedResource.query : undefined; + var resourceFragment = splittedResource ? splittedResource.fragment : undefined; + var contextDirectory = resourcePath ? dirname(resourcePath) : null; + + // execution state + var requestCacheable = true; + var fileDependencies = []; + var contextDependencies = []; + var missingDependencies = []; + + // prepare loader objects + loaders = loaders.map(createLoaderObject); + + loaderContext.context = contextDirectory; + loaderContext.loaderIndex = 0; + loaderContext.loaders = loaders; + loaderContext.resourcePath = resourcePath; + loaderContext.resourceQuery = resourceQuery; + loaderContext.resourceFragment = resourceFragment; + loaderContext.async = null; + loaderContext.callback = null; + loaderContext.cacheable = function cacheable(flag) { + if(flag === false) { + requestCacheable = false; } - code += "var _loop;\n"; - code += "do {\n"; - code += "_loop = false;\n"; - for (let i = 0; i < this.options.interceptors.length; i++) { - const interceptor = this.options.interceptors[i]; - if (interceptor.loop) { - code += `${this.getInterceptor(i)}.loop(${this.args({ - before: interceptor.context ? "_context" : undefined - })});\n`; - } + }; + loaderContext.dependency = loaderContext.addDependency = function addDependency(file) { + fileDependencies.push(file); + }; + loaderContext.addContextDependency = function addContextDependency(context) { + contextDependencies.push(context); + }; + loaderContext.addMissingDependency = function addMissingDependency(context) { + missingDependencies.push(context); + }; + loaderContext.getDependencies = function getDependencies() { + return fileDependencies.slice(); + }; + loaderContext.getContextDependencies = function getContextDependencies() { + return contextDependencies.slice(); + }; + loaderContext.getMissingDependencies = function getMissingDependencies() { + return missingDependencies.slice(); + }; + loaderContext.clearDependencies = function clearDependencies() { + fileDependencies.length = 0; + contextDependencies.length = 0; + missingDependencies.length = 0; + requestCacheable = true; + }; + Object.defineProperty(loaderContext, "resource", { + enumerable: true, + get: function() { + if(loaderContext.resourcePath === undefined) + return undefined; + return loaderContext.resourcePath.replace(/#/g, "\0#") + loaderContext.resourceQuery.replace(/#/g, "\0#") + loaderContext.resourceFragment; + }, + set: function(value) { + var splittedResource = value && parsePathQueryFragment(value); + loaderContext.resourcePath = splittedResource ? splittedResource.path : undefined; + loaderContext.resourceQuery = splittedResource ? splittedResource.query : undefined; + loaderContext.resourceFragment = splittedResource ? splittedResource.fragment : undefined; } - code += this.callTapsSeries({ - onError, - onResult: (i, result, next, doneBreak) => { - let code = ""; - code += `if(${result} !== undefined) {\n`; - code += "_loop = true;\n"; - if (!syncOnly) code += "if(_loopAsync) _looper();\n"; - code += doneBreak(true); - code += `} else {\n`; - code += next(); - code += `}\n`; - return code; - }, - onDone: - onDone && - (() => { - let code = ""; - code += "if(!_loop) {\n"; - code += onDone(); - code += "}\n"; - return code; - }), - rethrowIfPossible: rethrowIfPossible && syncOnly - }); - code += "} while(_loop);\n"; - if (!syncOnly) { - code += "_loopAsync = true;\n"; - code += "});\n"; - code += "_looper();\n"; + }); + Object.defineProperty(loaderContext, "request", { + enumerable: true, + get: function() { + return loaderContext.loaders.map(function(o) { + return o.request; + }).concat(loaderContext.resource || "").join("!"); } - return code; - } - - callTapsParallel({ - onError, - onResult, - onDone, - rethrowIfPossible, - onTap = (i, run) => run() - }) { - if (this.options.taps.length <= 1) { - return this.callTapsSeries({ - onError, - onResult, - onDone, - rethrowIfPossible - }); + }); + Object.defineProperty(loaderContext, "remainingRequest", { + enumerable: true, + get: function() { + if(loaderContext.loaderIndex >= loaderContext.loaders.length - 1 && !loaderContext.resource) + return ""; + return loaderContext.loaders.slice(loaderContext.loaderIndex + 1).map(function(o) { + return o.request; + }).concat(loaderContext.resource || "").join("!"); } - let code = ""; - code += "do {\n"; - code += `var _counter = ${this.options.taps.length};\n`; - if (onDone) { - code += "var _done = (function() {\n"; - code += onDone(); - code += "});\n"; + }); + Object.defineProperty(loaderContext, "currentRequest", { + enumerable: true, + get: function() { + return loaderContext.loaders.slice(loaderContext.loaderIndex).map(function(o) { + return o.request; + }).concat(loaderContext.resource || "").join("!"); } - for (let i = 0; i < this.options.taps.length; i++) { - const done = () => { - if (onDone) return "if(--_counter === 0) _done();\n"; - else return "--_counter;"; - }; - const doneBreak = skipDone => { - if (skipDone || !onDone) return "_counter = 0;\n"; - else return "_counter = 0;\n_done();\n"; - }; - code += "if(_counter <= 0) break;\n"; - code += onTap( - i, - () => - this.callTap(i, { - onError: error => { - let code = ""; - code += "if(_counter > 0) {\n"; - code += onError(i, error, done, doneBreak); - code += "}\n"; - return code; - }, - onResult: - onResult && - (result => { - let code = ""; - code += "if(_counter > 0) {\n"; - code += onResult(i, result, done, doneBreak); - code += "}\n"; - return code; - }), - onDone: - !onResult && - (() => { - return done(); - }), - rethrowIfPossible - }), - done, - doneBreak - ); + }); + Object.defineProperty(loaderContext, "previousRequest", { + enumerable: true, + get: function() { + return loaderContext.loaders.slice(0, loaderContext.loaderIndex).map(function(o) { + return o.request; + }).join("!"); + } + }); + Object.defineProperty(loaderContext, "query", { + enumerable: true, + get: function() { + var entry = loaderContext.loaders[loaderContext.loaderIndex]; + return entry.options && typeof entry.options === "object" ? entry.options : entry.query; } - code += "} while(false);\n"; - return code; + }); + Object.defineProperty(loaderContext, "data", { + enumerable: true, + get: function() { + return loaderContext.loaders[loaderContext.loaderIndex].data; + } + }); + + // finish loader context + if(Object.preventExtensions) { + Object.preventExtensions(loaderContext); } - args({ before, after } = {}) { - let allArgs = this._args; - if (before) allArgs = [before].concat(allArgs); - if (after) allArgs = allArgs.concat(after); - if (allArgs.length === 0) { - return ""; - } else { - return allArgs.join(", "); + var processOptions = { + resourceBuffer: null, + processResource: processResource + }; + iteratePitchingLoaders(processOptions, loaderContext, function(err, result) { + if(err) { + return callback(err, { + cacheable: requestCacheable, + fileDependencies: fileDependencies, + contextDependencies: contextDependencies, + missingDependencies: missingDependencies + }); } - } + callback(null, { + result: result, + resourceBuffer: processOptions.resourceBuffer, + cacheable: requestCacheable, + fileDependencies: fileDependencies, + contextDependencies: contextDependencies, + missingDependencies: missingDependencies + }); + }); +}; - getTapFn(idx) { - return `_x[${idx}]`; - } - getTap(idx) { - return `_taps[${idx}]`; +/***/ }), + +/***/ 63395: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + +var LoaderLoadingError = __webpack_require__(83798); +var url; + +module.exports = function loadLoader(loader, callback) { + if(loader.type === "module") { + try { + if(url === undefined) url = __webpack_require__(78835); + var loaderUrl = url.pathToFileURL(loader.path); + var modulePromise = eval("import(" + JSON.stringify(loaderUrl.toString()) + ")"); + modulePromise.then(function(module) { + handleResult(loader, module, callback); + }, callback); + return; + } catch(e) { + callback(e); + } + } else { + try { + var module = require(loader.path); + } catch(e) { + // it is possible for node to choke on a require if the FD descriptor + // limit has been reached. give it a chance to recover. + if(e instanceof Error && e.code === "EMFILE") { + var retry = loadLoader.bind(null, loader, callback); + if(typeof setImmediate === "function") { + // node >= 0.9.0 + return setImmediate(retry); + } else { + // node < 0.9.0 + return process.nextTick(retry); + } + } + return callback(e); + } + return handleResult(loader, module, callback); } +}; - getInterceptor(idx) { - return `_interceptors[${idx}]`; +function handleResult(loader, module, callback) { + if(typeof module !== "function" && typeof module !== "object") { + return callback(new LoaderLoadingError( + "Module '" + loader.path + "' is not a loader (export function or es6 module)" + )); + } + loader.normal = typeof module === "function" ? module : module.default; + loader.pitch = module.pitch; + loader.raw = module.raw; + if(typeof loader.normal !== "function" && typeof loader.pitch !== "function") { + return callback(new LoaderLoadingError( + "Module '" + loader.path + "' is not a loader (must have normal or pitch function)" + )); } + callback(); } -module.exports = HookCodeFactory; - /***/ }), -/***/ 81647: +/***/ 11060: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { +/*! + * mime-db + * Copyright(c) 2014 Jonathan Ong + * MIT Licensed + */ + +/** + * Module exports. + */ + +module.exports = __webpack_require__(53243) + + +/***/ }), + +/***/ 19338: +/***/ (function(__unused_webpack_module, exports, __webpack_require__) { + "use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ +/*! + * mime-types + * Copyright(c) 2014 Jonathan Ong + * Copyright(c) 2015 Douglas Christopher Wilson + * MIT Licensed + */ -const util = __webpack_require__(31669); -const defaultFactory = (key, hook) => hook; +/** + * Module dependencies. + * @private + */ -class HookMap { - constructor(factory, name = undefined) { - this._map = new Map(); - this.name = name; - this._factory = factory; - this._interceptors = []; - } +var db = __webpack_require__(11060) +var extname = __webpack_require__(85622).extname - get(key) { - return this._map.get(key); - } +/** + * Module variables. + * @private + */ - for(key) { - const hook = this.get(key); - if (hook !== undefined) { - return hook; - } - let newHook = this._factory(key); - const interceptors = this._interceptors; - for (let i = 0; i < interceptors.length; i++) { - newHook = interceptors[i].factory(key, newHook); - } - this._map.set(key, newHook); - return newHook; - } +var EXTRACT_TYPE_REGEXP = /^\s*([^;\s]*)(?:;|\s|$)/ +var TEXT_TYPE_REGEXP = /^text\//i - intercept(interceptor) { - this._interceptors.push( - Object.assign( - { - factory: defaultFactory - }, - interceptor - ) - ); - } +/** + * Module exports. + * @public + */ + +exports.charset = charset +exports.charsets = { lookup: charset } +exports.contentType = contentType +exports.extension = extension +exports.extensions = Object.create(null) +exports.lookup = lookup +exports.types = Object.create(null) + +// Populate the extensions/types maps +populateMaps(exports.extensions, exports.types) + +/** + * Get the default charset for a MIME type. + * + * @param {string} type + * @return {boolean|string} + */ + +function charset (type) { + if (!type || typeof type !== 'string') { + return false + } + + // TODO: use media-typer + var match = EXTRACT_TYPE_REGEXP.exec(type) + var mime = match && db[match[1].toLowerCase()] + + if (mime && mime.charset) { + return mime.charset + } + + // default text/* to utf-8 + if (match && TEXT_TYPE_REGEXP.test(match[1])) { + return 'UTF-8' + } + + return false } -HookMap.prototype.tap = util.deprecate(function(key, options, fn) { - return this.for(key).tap(options, fn); -}, "HookMap#tap(key,…) is deprecated. Use HookMap#for(key).tap(…) instead."); +/** + * Create a full Content-Type header given a MIME type or extension. + * + * @param {string} str + * @return {boolean|string} + */ -HookMap.prototype.tapAsync = util.deprecate(function(key, options, fn) { - return this.for(key).tapAsync(options, fn); -}, "HookMap#tapAsync(key,…) is deprecated. Use HookMap#for(key).tapAsync(…) instead."); +function contentType (str) { + // TODO: should this even be in this module? + if (!str || typeof str !== 'string') { + return false + } -HookMap.prototype.tapPromise = util.deprecate(function(key, options, fn) { - return this.for(key).tapPromise(options, fn); -}, "HookMap#tapPromise(key,…) is deprecated. Use HookMap#for(key).tapPromise(…) instead."); + var mime = str.indexOf('/') === -1 + ? exports.lookup(str) + : str -module.exports = HookMap; + if (!mime) { + return false + } + + // TODO: use content-type or other module + if (mime.indexOf('charset') === -1) { + var charset = exports.charset(mime) + if (charset) mime += '; charset=' + charset.toLowerCase() + } + + return mime +} + +/** + * Get the default extension for a MIME type. + * + * @param {string} type + * @return {boolean|string} + */ + +function extension (type) { + if (!type || typeof type !== 'string') { + return false + } + + // TODO: use media-typer + var match = EXTRACT_TYPE_REGEXP.exec(type) + + // get extensions + var exts = match && exports.extensions[match[1].toLowerCase()] + + if (!exts || !exts.length) { + return false + } + + return exts[0] +} + +/** + * Lookup the MIME type for a file path/extension. + * + * @param {string} path + * @return {boolean|string} + */ + +function lookup (path) { + if (!path || typeof path !== 'string') { + return false + } + + // get the extension ("ext" or ".ext" or full path) + var extension = extname('x.' + path) + .toLowerCase() + .substr(1) + + if (!extension) { + return false + } + + return exports.types[extension] || false +} + +/** + * Populate the extensions and types maps. + * @private + */ + +function populateMaps (extensions, types) { + // source preference (least -> most) + var preference = ['nginx', 'apache', undefined, 'iana'] + + Object.keys(db).forEach(function forEachMimeType (type) { + var mime = db[type] + var exts = mime.extensions + + if (!exts || !exts.length) { + return + } + + // mime -> extensions + extensions[type] = exts + + // extension -> mime + for (var i = 0; i < exts.length; i++) { + var extension = exts[i] + + if (types[extension]) { + var from = preference.indexOf(db[types[extension]].source) + var to = preference.indexOf(mime.source) + + if (types[extension] !== 'application/octet-stream' && + (from > to || (from === to && types[extension].substr(0, 12) === 'application/'))) { + // skip the remapping + continue + } + } + + // set the extension -> mime + types[extension] = type + } + }) +} /***/ }), -/***/ 63708: +/***/ 28339: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; @@ -142029,58 +142816,89 @@ module.exports = HookMap; const Hook = __webpack_require__(36591); +const HookCodeFactory = __webpack_require__(85572); -class MultiHook { - constructor(hooks, name = undefined) { - this.hooks = hooks; - this.name = name; - } - - tap(options, fn) { - for (const hook of this.hooks) { - hook.tap(options, fn); - } - } - - tapAsync(options, fn) { - for (const hook of this.hooks) { - hook.tapAsync(options, fn); - } - } - - tapPromise(options, fn) { - for (const hook of this.hooks) { - hook.tapPromise(options, fn); - } +class AsyncParallelBailHookCodeFactory extends HookCodeFactory { + content({ onError, onResult, onDone }) { + let code = ""; + code += `var _results = new Array(${this.options.taps.length});\n`; + code += "var _checkDone = function() {\n"; + code += "for(var i = 0; i < _results.length; i++) {\n"; + code += "var item = _results[i];\n"; + code += "if(item === undefined) return false;\n"; + code += "if(item.result !== undefined) {\n"; + code += onResult("item.result"); + code += "return true;\n"; + code += "}\n"; + code += "if(item.error) {\n"; + code += onError("item.error"); + code += "return true;\n"; + code += "}\n"; + code += "}\n"; + code += "return false;\n"; + code += "}\n"; + code += this.callTapsParallel({ + onError: (i, err, done, doneBreak) => { + let code = ""; + code += `if(${i} < _results.length && ((_results.length = ${i + + 1}), (_results[${i}] = { error: ${err} }), _checkDone())) {\n`; + code += doneBreak(true); + code += "} else {\n"; + code += done(); + code += "}\n"; + return code; + }, + onResult: (i, result, done, doneBreak) => { + let code = ""; + code += `if(${i} < _results.length && (${result} !== undefined && (_results.length = ${i + + 1}), (_results[${i}] = { result: ${result} }), _checkDone())) {\n`; + code += doneBreak(true); + code += "} else {\n"; + code += done(); + code += "}\n"; + return code; + }, + onTap: (i, run, done, doneBreak) => { + let code = ""; + if (i > 0) { + code += `if(${i} >= _results.length) {\n`; + code += done(); + code += "} else {\n"; + } + code += run(); + if (i > 0) code += "}\n"; + return code; + }, + onDone + }); + return code; } +} - isUsed() { - for (const hook of this.hooks) { - if (hook.isUsed()) return true; - } - return false; - } +const factory = new AsyncParallelBailHookCodeFactory(); - intercept(interceptor) { - for (const hook of this.hooks) { - hook.intercept(interceptor); - } - } +const COMPILE = function(options) { + factory.setup(this, options); + return factory.create(options); +}; - withOptions(options) { - return new MultiHook( - this.hooks.map(h => h.withOptions(options)), - this.name - ); - } +function AsyncParallelBailHook(args = [], name = undefined) { + const hook = new Hook(args, name); + hook.constructor = AsyncParallelBailHook; + hook.compile = COMPILE; + hook._call = undefined; + hook.call = undefined; + return hook; } -module.exports = MultiHook; +AsyncParallelBailHook.prototype = null; + +module.exports = AsyncParallelBailHook; /***/ }), -/***/ 98034: +/***/ 82890: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; @@ -142093,53 +142911,39 @@ module.exports = MultiHook; const Hook = __webpack_require__(36591); const HookCodeFactory = __webpack_require__(85572); -class SyncBailHookCodeFactory extends HookCodeFactory { - content({ onError, onResult, resultReturns, onDone, rethrowIfPossible }) { - return this.callTapsSeries({ - onError: (i, err) => onError(err), - onResult: (i, result, next) => - `if(${result} !== undefined) {\n${onResult( - result - )};\n} else {\n${next()}}\n`, - resultReturns, - onDone, - rethrowIfPossible +class AsyncParallelHookCodeFactory extends HookCodeFactory { + content({ onError, onDone }) { + return this.callTapsParallel({ + onError: (i, err, done, doneBreak) => onError(err) + doneBreak(true), + onDone }); } } -const factory = new SyncBailHookCodeFactory(); - -const TAP_ASYNC = () => { - throw new Error("tapAsync is not supported on a SyncBailHook"); -}; - -const TAP_PROMISE = () => { - throw new Error("tapPromise is not supported on a SyncBailHook"); -}; +const factory = new AsyncParallelHookCodeFactory(); const COMPILE = function(options) { factory.setup(this, options); return factory.create(options); }; -function SyncBailHook(args = [], name = undefined) { +function AsyncParallelHook(args = [], name = undefined) { const hook = new Hook(args, name); - hook.constructor = SyncBailHook; - hook.tapAsync = TAP_ASYNC; - hook.tapPromise = TAP_PROMISE; + hook.constructor = AsyncParallelHook; hook.compile = COMPILE; + hook._call = undefined; + hook.call = undefined; return hook; } -SyncBailHook.prototype = null; +AsyncParallelHook.prototype = null; -module.exports = SyncBailHook; +module.exports = AsyncParallelHook; /***/ }), -/***/ 35079: +/***/ 97681: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; @@ -142152,48 +142956,44 @@ module.exports = SyncBailHook; const Hook = __webpack_require__(36591); const HookCodeFactory = __webpack_require__(85572); -class SyncHookCodeFactory extends HookCodeFactory { - content({ onError, onDone, rethrowIfPossible }) { +class AsyncSeriesBailHookCodeFactory extends HookCodeFactory { + content({ onError, onResult, resultReturns, onDone }) { return this.callTapsSeries({ - onError: (i, err) => onError(err), - onDone, - rethrowIfPossible + onError: (i, err, next, doneBreak) => onError(err) + doneBreak(true), + onResult: (i, result, next) => + `if(${result} !== undefined) {\n${onResult( + result + )}\n} else {\n${next()}}\n`, + resultReturns, + onDone }); } } -const factory = new SyncHookCodeFactory(); - -const TAP_ASYNC = () => { - throw new Error("tapAsync is not supported on a SyncHook"); -}; - -const TAP_PROMISE = () => { - throw new Error("tapPromise is not supported on a SyncHook"); -}; +const factory = new AsyncSeriesBailHookCodeFactory(); const COMPILE = function(options) { factory.setup(this, options); return factory.create(options); }; -function SyncHook(args = [], name = undefined) { +function AsyncSeriesBailHook(args = [], name = undefined) { const hook = new Hook(args, name); - hook.constructor = SyncHook; - hook.tapAsync = TAP_ASYNC; - hook.tapPromise = TAP_PROMISE; + hook.constructor = AsyncSeriesBailHook; hook.compile = COMPILE; + hook._call = undefined; + hook.call = undefined; return hook; } -SyncHook.prototype = null; +AsyncSeriesBailHook.prototype = null; -module.exports = SyncHook; +module.exports = AsyncSeriesBailHook; /***/ }), -/***/ 66953: +/***/ 45146: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; @@ -142206,48 +143006,39 @@ module.exports = SyncHook; const Hook = __webpack_require__(36591); const HookCodeFactory = __webpack_require__(85572); -class SyncLoopHookCodeFactory extends HookCodeFactory { - content({ onError, onDone, rethrowIfPossible }) { - return this.callTapsLooping({ - onError: (i, err) => onError(err), - onDone, - rethrowIfPossible +class AsyncSeriesHookCodeFactory extends HookCodeFactory { + content({ onError, onDone }) { + return this.callTapsSeries({ + onError: (i, err, next, doneBreak) => onError(err) + doneBreak(true), + onDone }); } } -const factory = new SyncLoopHookCodeFactory(); - -const TAP_ASYNC = () => { - throw new Error("tapAsync is not supported on a SyncLoopHook"); -}; - -const TAP_PROMISE = () => { - throw new Error("tapPromise is not supported on a SyncLoopHook"); -}; +const factory = new AsyncSeriesHookCodeFactory(); const COMPILE = function(options) { factory.setup(this, options); return factory.create(options); }; -function SyncLoopHook(args = [], name = undefined) { +function AsyncSeriesHook(args = [], name = undefined) { const hook = new Hook(args, name); - hook.constructor = SyncLoopHook; - hook.tapAsync = TAP_ASYNC; - hook.tapPromise = TAP_PROMISE; + hook.constructor = AsyncSeriesHook; hook.compile = COMPILE; + hook._call = undefined; + hook.call = undefined; return hook; } -SyncLoopHook.prototype = null; +AsyncSeriesHook.prototype = null; -module.exports = SyncLoopHook; +module.exports = AsyncSeriesHook; /***/ }), -/***/ 92878: +/***/ 5463: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; @@ -142260,86 +143051,39 @@ module.exports = SyncLoopHook; const Hook = __webpack_require__(36591); const HookCodeFactory = __webpack_require__(85572); -class SyncWaterfallHookCodeFactory extends HookCodeFactory { - content({ onError, onResult, resultReturns, rethrowIfPossible }) { - return this.callTapsSeries({ - onError: (i, err) => onError(err), - onResult: (i, result, next) => { - let code = ""; - code += `if(${result} !== undefined) {\n`; - code += `${this._args[0]} = ${result};\n`; - code += `}\n`; - code += next(); - return code; - }, - onDone: () => onResult(this._args[0]), - doneReturns: resultReturns, - rethrowIfPossible +class AsyncSeriesLoopHookCodeFactory extends HookCodeFactory { + content({ onError, onDone }) { + return this.callTapsLooping({ + onError: (i, err, next, doneBreak) => onError(err) + doneBreak(true), + onDone }); } } -const factory = new SyncWaterfallHookCodeFactory(); - -const TAP_ASYNC = () => { - throw new Error("tapAsync is not supported on a SyncWaterfallHook"); -}; - -const TAP_PROMISE = () => { - throw new Error("tapPromise is not supported on a SyncWaterfallHook"); -}; +const factory = new AsyncSeriesLoopHookCodeFactory(); const COMPILE = function(options) { factory.setup(this, options); return factory.create(options); }; -function SyncWaterfallHook(args = [], name = undefined) { - if (args.length < 1) - throw new Error("Waterfall hooks must have at least one argument"); +function AsyncSeriesLoopHook(args = [], name = undefined) { const hook = new Hook(args, name); - hook.constructor = SyncWaterfallHook; - hook.tapAsync = TAP_ASYNC; - hook.tapPromise = TAP_PROMISE; + hook.constructor = AsyncSeriesLoopHook; hook.compile = COMPILE; + hook._call = undefined; + hook.call = undefined; return hook; } -SyncWaterfallHook.prototype = null; - -module.exports = SyncWaterfallHook; - - -/***/ }), - -/***/ 34718: -/***/ (function(__unused_webpack_module, exports, __webpack_require__) { - -"use strict"; -/* - MIT License http://www.opensource.org/licenses/mit-license.php - Author Tobias Koppers @sokra -*/ - +AsyncSeriesLoopHook.prototype = null; -exports.__esModule = true; -exports.SyncHook = __webpack_require__(35079); -exports.SyncBailHook = __webpack_require__(98034); -exports.SyncWaterfallHook = __webpack_require__(92878); -exports.SyncLoopHook = __webpack_require__(66953); -exports.AsyncParallelHook = __webpack_require__(82890); -exports.AsyncParallelBailHook = __webpack_require__(28339); -exports.AsyncSeriesHook = __webpack_require__(45146); -exports.AsyncSeriesBailHook = __webpack_require__(97681); -exports.AsyncSeriesLoopHook = __webpack_require__(5463); -exports.AsyncSeriesWaterfallHook = __webpack_require__(73448); -exports.HookMap = __webpack_require__(81647); -exports.MultiHook = __webpack_require__(63708); +module.exports = AsyncSeriesLoopHook; /***/ }), -/***/ 39144: +/***/ 73448: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; @@ -142349,803 +143093,236 @@ exports.MultiHook = __webpack_require__(63708); */ -const EventEmitter = __webpack_require__(28614).EventEmitter; -const fs = __webpack_require__(82161); -const path = __webpack_require__(85622); - -const watchEventSource = __webpack_require__(10547); - -const EXISTANCE_ONLY_TIME_ENTRY = Object.freeze({}); - -let FS_ACCURACY = 1000; - -const IS_OSX = __webpack_require__(12087).platform() === "darwin"; -const WATCHPACK_POLLING = process.env.WATCHPACK_POLLING; -const FORCE_POLLING = - `${+WATCHPACK_POLLING}` === WATCHPACK_POLLING - ? +WATCHPACK_POLLING - : !!WATCHPACK_POLLING && WATCHPACK_POLLING !== "false"; - -function withoutCase(str) { - return str.toLowerCase(); -} - -function needCalls(times, callback) { - return function() { - if (--times === 0) { - return callback(); - } - }; -} - -class Watcher extends EventEmitter { - constructor(directoryWatcher, filePath, startTime) { - super(); - this.directoryWatcher = directoryWatcher; - this.path = filePath; - this.startTime = startTime && +startTime; - this._cachedTimeInfoEntries = undefined; - } - - checkStartTime(mtime, initial) { - const startTime = this.startTime; - if (typeof startTime !== "number") return !initial; - return startTime <= mtime; - } - - close() { - this.emit("closed"); - } -} - -class DirectoryWatcher extends EventEmitter { - constructor(watcherManager, directoryPath, options) { - super(); - if (FORCE_POLLING) { - options.poll = FORCE_POLLING; - } - this.watcherManager = watcherManager; - this.options = options; - this.path = directoryPath; - // safeTime is the point in time after which reading is safe to be unchanged - // timestamp is a value that should be compared with another timestamp (mtime) - /** @type {Map} */ - this.filesWithoutCase = new Map(); - this.directories = new Map(); - this.lastWatchEvent = 0; - this.initialScan = true; - this.ignored = options.ignored; - this.nestedWatching = false; - this.polledWatching = - typeof options.poll === "number" - ? options.poll - : options.poll - ? 5007 - : false; - this.timeout = undefined; - this.initialScanRemoved = new Set(); - this.initialScanFinished = undefined; - /** @type {Map>} */ - this.watchers = new Map(); - this.parentWatcher = null; - this.refs = 0; - this._activeEvents = new Map(); - this.closed = false; - this.scanning = false; - this.scanAgain = false; - this.scanAgainInitial = false; - - this.createWatcher(); - this.doScan(true); - } - - checkIgnore(path) { - if (!this.ignored) return false; - path = path.replace(/\\/g, "/"); - return this.ignored.test(path); - } - - createWatcher() { - try { - if (this.polledWatching) { - this.watcher = { - close: () => { - if (this.timeout) { - clearTimeout(this.timeout); - this.timeout = undefined; - } - } - }; - } else { - if (IS_OSX) { - this.watchInParentDirectory(); - } - this.watcher = watchEventSource.watch(this.path); - this.watcher.on("change", this.onWatchEvent.bind(this)); - this.watcher.on("error", this.onWatcherError.bind(this)); - } - } catch (err) { - this.onWatcherError(err); - } - } - - forEachWatcher(path, fn) { - const watchers = this.watchers.get(withoutCase(path)); - if (watchers !== undefined) { - for (const w of watchers) { - fn(w); - } - } - } - - setMissing(itemPath, initial, type) { - this._cachedTimeInfoEntries = undefined; - - if (this.initialScan) { - this.initialScanRemoved.add(itemPath); - } - - const oldDirectory = this.directories.get(itemPath); - if (oldDirectory) { - if (this.nestedWatching) oldDirectory.close(); - this.directories.delete(itemPath); - - this.forEachWatcher(itemPath, w => w.emit("remove", type)); - if (!initial) { - this.forEachWatcher(this.path, w => - w.emit("change", itemPath, null, type, initial) - ); - } - } - - const oldFile = this.files.get(itemPath); - if (oldFile) { - this.files.delete(itemPath); - const key = withoutCase(itemPath); - const count = this.filesWithoutCase.get(key) - 1; - if (count <= 0) { - this.filesWithoutCase.delete(key); - this.forEachWatcher(itemPath, w => w.emit("remove", type)); - } else { - this.filesWithoutCase.set(key, count); - } - - if (!initial) { - this.forEachWatcher(this.path, w => - w.emit("change", itemPath, null, type, initial) - ); - } - } - } - - setFileTime(filePath, mtime, initial, ignoreWhenEqual, type) { - const now = Date.now(); - - if (this.checkIgnore(filePath)) return; - - const old = this.files.get(filePath); - - let safeTime, accuracy; - if (initial) { - safeTime = Math.min(now, mtime) + FS_ACCURACY; - accuracy = FS_ACCURACY; - } else { - safeTime = now; - accuracy = 0; - - if (old && old.timestamp === mtime && mtime + FS_ACCURACY < now - 1000) { - // We are sure that mtime is untouched - // This can be caused by some file attribute change - // e. g. when access time has been changed - // but the file content is untouched - return; - } - } - - if (ignoreWhenEqual && old && old.timestamp === mtime) return; - - this.files.set(filePath, { - safeTime, - accuracy, - timestamp: mtime - }); - this._cachedTimeInfoEntries = undefined; - - if (!old) { - const key = withoutCase(filePath); - const count = this.filesWithoutCase.get(key); - this.filesWithoutCase.set(key, (count || 0) + 1); - if (count !== undefined) { - // There is already a file with case-insensitive-equal name - // On a case-insensitive filesystem we may miss the renaming - // when only casing is changed. - // To be sure that our information is correct - // we trigger a rescan here - this.doScan(false); - } - - this.forEachWatcher(filePath, w => { - if (!initial || w.checkStartTime(safeTime, initial)) { - w.emit("change", mtime, type); - } - }); - } else if (!initial) { - this.forEachWatcher(filePath, w => w.emit("change", mtime, type)); - } - this.forEachWatcher(this.path, w => { - if (!initial || w.checkStartTime(safeTime, initial)) { - w.emit("change", filePath, safeTime, type, initial); - } - }); - } - - setDirectory(directoryPath, birthtime, initial, type) { - if (this.checkIgnore(directoryPath)) return; - if (directoryPath === this.path) { - if (!initial) { - this.forEachWatcher(this.path, w => - w.emit("change", directoryPath, birthtime, type, initial) - ); - } - } else { - const old = this.directories.get(directoryPath); - if (!old) { - const now = Date.now(); - - this._cachedTimeInfoEntries = undefined; - if (this.nestedWatching) { - this.createNestedWatcher(directoryPath); - } else { - this.directories.set(directoryPath, true); - } - - let safeTime; - if (initial) { - safeTime = Math.min(now, birthtime) + FS_ACCURACY; - } else { - safeTime = now; - } - - this.forEachWatcher(directoryPath, w => { - if (!initial || w.checkStartTime(safeTime, false)) { - w.emit("change", birthtime, type); - } - }); - this.forEachWatcher(this.path, w => { - if (!initial || w.checkStartTime(safeTime, initial)) { - w.emit("change", directoryPath, safeTime, type, initial); - } - }); - } - } - } - - createNestedWatcher(directoryPath) { - const watcher = this.watcherManager.watchDirectory(directoryPath, 1); - watcher.on("change", (filePath, mtime, type, initial) => { - this._cachedTimeInfoEntries = undefined; - this.forEachWatcher(this.path, w => { - if (!initial || w.checkStartTime(mtime, initial)) { - w.emit("change", filePath, mtime, type, initial); - } - }); - }); - this.directories.set(directoryPath, watcher); - } - - setNestedWatching(flag) { - if (this.nestedWatching !== !!flag) { - this.nestedWatching = !!flag; - this._cachedTimeInfoEntries = undefined; - if (this.nestedWatching) { - for (const directory of this.directories.keys()) { - this.createNestedWatcher(directory); - } - } else { - for (const [directory, watcher] of this.directories) { - watcher.close(); - this.directories.set(directory, true); - } - } - } - } - - watch(filePath, startTime) { - const key = withoutCase(filePath); - let watchers = this.watchers.get(key); - if (watchers === undefined) { - watchers = new Set(); - this.watchers.set(key, watchers); - } - this.refs++; - const watcher = new Watcher(this, filePath, startTime); - watcher.on("closed", () => { - if (--this.refs <= 0) { - this.close(); - return; - } - watchers.delete(watcher); - if (watchers.size === 0) { - this.watchers.delete(key); - if (this.path === filePath) this.setNestedWatching(false); - } - }); - watchers.add(watcher); - let safeTime; - if (filePath === this.path) { - this.setNestedWatching(true); - safeTime = this.lastWatchEvent; - for (const entry of this.files.values()) { - fixupEntryAccuracy(entry); - safeTime = Math.max(safeTime, entry.safeTime); - } - } else { - const entry = this.files.get(filePath); - if (entry) { - fixupEntryAccuracy(entry); - safeTime = entry.safeTime; - } else { - safeTime = 0; - } - } - if (safeTime) { - if (safeTime >= startTime) { - process.nextTick(() => { - if (this.closed) return; - if (filePath === this.path) { - watcher.emit( - "change", - filePath, - safeTime, - "watch (outdated on attach)", - true - ); - } else { - watcher.emit( - "change", - safeTime, - "watch (outdated on attach)", - true - ); - } - }); - } - } else if (this.initialScan) { - if (this.initialScanRemoved.has(filePath)) { - process.nextTick(() => { - if (this.closed) return; - watcher.emit("remove"); - }); - } - } else if ( - !this.directories.has(filePath) && - watcher.checkStartTime(this.initialScanFinished, false) - ) { - process.nextTick(() => { - if (this.closed) return; - watcher.emit("initial-missing", "watch (missing on attach)"); - }); - } - return watcher; +const Hook = __webpack_require__(36591); +const HookCodeFactory = __webpack_require__(85572); + +class AsyncSeriesWaterfallHookCodeFactory extends HookCodeFactory { + content({ onError, onResult, onDone }) { + return this.callTapsSeries({ + onError: (i, err, next, doneBreak) => onError(err) + doneBreak(true), + onResult: (i, result, next) => { + let code = ""; + code += `if(${result} !== undefined) {\n`; + code += `${this._args[0]} = ${result};\n`; + code += `}\n`; + code += next(); + return code; + }, + onDone: () => onResult(this._args[0]) + }); } +} - onWatchEvent(eventType, filename) { - if (this.closed) return; - if (!filename) { - // In some cases no filename is provided - // This seem to happen on windows - // So some event happened but we don't know which file is affected - // We have to do a full scan of the directory - this.doScan(false); - return; - } +const factory = new AsyncSeriesWaterfallHookCodeFactory(); - const filePath = path.join(this.path, filename); - if (this.checkIgnore(filePath)) return; +const COMPILE = function(options) { + factory.setup(this, options); + return factory.create(options); +}; - if (this._activeEvents.get(filename) === undefined) { - this._activeEvents.set(filename, false); - const checkStats = () => { - if (this.closed) return; - this._activeEvents.set(filename, false); - fs.lstat(filePath, (err, stats) => { - if (this.closed) return; - if (this._activeEvents.get(filename) === true) { - process.nextTick(checkStats); - return; - } - this._activeEvents.delete(filename); - // ENOENT happens when the file/directory doesn't exist - // EPERM happens when the containing directory doesn't exist - if (err) { - if ( - err.code !== "ENOENT" && - err.code !== "EPERM" && - err.code !== "EBUSY" - ) { - this.onStatsError(err); - } else { - if (filename === path.basename(this.path)) { - // This may indicate that the directory itself was removed - if (!fs.existsSync(this.path)) { - this.onDirectoryRemoved("stat failed"); - } - } - } - } - this.lastWatchEvent = Date.now(); - this._cachedTimeInfoEntries = undefined; - if (!stats) { - this.setMissing(filePath, false, eventType); - } else if (stats.isDirectory()) { - this.setDirectory( - filePath, - +stats.birthtime || 1, - false, - eventType - ); - } else if (stats.isFile() || stats.isSymbolicLink()) { - if (stats.mtime) { - ensureFsAccuracy(stats.mtime); - } - this.setFileTime( - filePath, - +stats.mtime || +stats.ctime || 1, - false, - false, - eventType - ); - } - }); - }; - process.nextTick(checkStats); - } else { - this._activeEvents.set(filename, true); - } - } +function AsyncSeriesWaterfallHook(args = [], name = undefined) { + if (args.length < 1) + throw new Error("Waterfall hooks must have at least one argument"); + const hook = new Hook(args, name); + hook.constructor = AsyncSeriesWaterfallHook; + hook.compile = COMPILE; + hook._call = undefined; + hook.call = undefined; + return hook; +} - onWatcherError(err) { - if (this.closed) return; - if (err) { - if (err.code !== "EPERM" && err.code !== "ENOENT") { - console.error("Watchpack Error (watcher): " + err); - } - this.onDirectoryRemoved("watch error"); - } - } +AsyncSeriesWaterfallHook.prototype = null; - onStatsError(err) { - if (err) { - console.error("Watchpack Error (stats): " + err); - } +module.exports = AsyncSeriesWaterfallHook; + + +/***/ }), + +/***/ 36591: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ + + +const util = __webpack_require__(31669); + +const deprecateContext = util.deprecate(() => {}, +"Hook.context is deprecated and will be removed"); + +const CALL_DELEGATE = function(...args) { + this.call = this._createCall("sync"); + return this.call(...args); +}; +const CALL_ASYNC_DELEGATE = function(...args) { + this.callAsync = this._createCall("async"); + return this.callAsync(...args); +}; +const PROMISE_DELEGATE = function(...args) { + this.promise = this._createCall("promise"); + return this.promise(...args); +}; + +class Hook { + constructor(args = [], name = undefined) { + this._args = args; + this.name = name; + this.taps = []; + this.interceptors = []; + this._call = CALL_DELEGATE; + this.call = CALL_DELEGATE; + this._callAsync = CALL_ASYNC_DELEGATE; + this.callAsync = CALL_ASYNC_DELEGATE; + this._promise = PROMISE_DELEGATE; + this.promise = PROMISE_DELEGATE; + this._x = undefined; + + this.compile = this.compile; + this.tap = this.tap; + this.tapAsync = this.tapAsync; + this.tapPromise = this.tapPromise; } - onScanError(err) { - if (err) { - console.error("Watchpack Error (initial scan): " + err); - } - this.onScanFinished(); + compile(options) { + throw new Error("Abstract: should be overridden"); } - onScanFinished() { - if (this.polledWatching) { - this.timeout = setTimeout(() => { - if (this.closed) return; - this.doScan(false); - }, this.polledWatching); - } + _createCall(type) { + return this.compile({ + taps: this.taps, + interceptors: this.interceptors, + args: this._args, + type: type + }); } - onDirectoryRemoved(reason) { - if (this.watcher) { - this.watcher.close(); - this.watcher = null; + _tap(type, options, fn) { + if (typeof options === "string") { + options = { + name: options.trim() + }; + } else if (typeof options !== "object" || options === null) { + throw new Error("Invalid tap options"); } - this.watchInParentDirectory(); - const type = `directory-removed (${reason})`; - for (const directory of this.directories.keys()) { - this.setMissing(directory, null, type); + if (typeof options.name !== "string" || options.name === "") { + throw new Error("Missing name for tap"); } - for (const file of this.files.keys()) { - this.setMissing(file, null, type); + if (typeof options.context !== "undefined") { + deprecateContext(); } + options = Object.assign({ type, fn }, options); + options = this._runRegisterInterceptors(options); + this._insert(options); } - watchInParentDirectory() { - if (!this.parentWatcher) { - const parentDir = path.dirname(this.path); - // avoid watching in the root directory - // removing directories in the root directory is not supported - if (path.dirname(parentDir) === parentDir) return; + tap(options, fn) { + this._tap("sync", options, fn); + } - this.parentWatcher = this.watcherManager.watchFile(this.path, 1); - this.parentWatcher.on("change", (mtime, type) => { - if (this.closed) return; + tapAsync(options, fn) { + this._tap("async", options, fn); + } - // On non-osx platforms we don't need this watcher to detect - // directory removal, as an EPERM error indicates that - if ((!IS_OSX || this.polledWatching) && this.parentWatcher) { - this.parentWatcher.close(); - this.parentWatcher = null; - } - // Try to create the watcher when parent directory is found - if (!this.watcher) { - this.createWatcher(); - this.doScan(false); + tapPromise(options, fn) { + this._tap("promise", options, fn); + } - // directory was created so we emit an event - this.forEachWatcher(this.path, w => - w.emit("change", this.path, mtime, type, false) - ); + _runRegisterInterceptors(options) { + for (const interceptor of this.interceptors) { + if (interceptor.register) { + const newOptions = interceptor.register(options); + if (newOptions !== undefined) { + options = newOptions; } - }); - this.parentWatcher.on("remove", () => { - this.onDirectoryRemoved("parent directory removed"); - }); + } } + return options; } - doScan(initial) { - if (this.scanning) { - if (this.scanAgain) { - if (!initial) this.scanAgainInitial = false; - } else { - this.scanAgain = true; - this.scanAgainInitial = initial; - } - return; - } - this.scanning = true; - if (this.timeout) { - clearTimeout(this.timeout); - this.timeout = undefined; - } - process.nextTick(() => { - if (this.closed) return; - fs.readdir(this.path, (err, items) => { - if (this.closed) return; - if (err) { - if (err.code === "ENOENT" || err.code === "EPERM") { - this.onDirectoryRemoved("scan readdir failed"); - } else { - this.onScanError(err); - } - this.initialScan = false; - this.initialScanFinished = Date.now(); - if (initial) { - for (const watchers of this.watchers.values()) { - for (const watcher of watchers) { - if (watcher.checkStartTime(this.initialScanFinished, false)) { - watcher.emit( - "initial-missing", - "scan (parent directory missing in initial scan)" - ); - } - } - } - } - if (this.scanAgain) { - this.scanAgain = false; - this.doScan(this.scanAgainInitial); - } else { - this.scanning = false; - } - return; - } - const itemPaths = new Set( - items.map(item => path.join(this.path, item.normalize("NFC"))) - ); - for (const file of this.files.keys()) { - if (!itemPaths.has(file)) { - this.setMissing(file, initial, "scan (missing)"); - } - } - for (const directory of this.directories.keys()) { - if (!itemPaths.has(directory)) { - this.setMissing(directory, initial, "scan (missing)"); - } - } - if (this.scanAgain) { - // Early repeat of scan - this.scanAgain = false; - this.doScan(initial); - return; - } - const itemFinished = needCalls(itemPaths.size + 1, () => { - if (this.closed) return; - this.initialScan = false; - this.initialScanRemoved = null; - this.initialScanFinished = Date.now(); - if (initial) { - const missingWatchers = new Map(this.watchers); - missingWatchers.delete(withoutCase(this.path)); - for (const item of itemPaths) { - missingWatchers.delete(withoutCase(item)); - } - for (const watchers of missingWatchers.values()) { - for (const watcher of watchers) { - if (watcher.checkStartTime(this.initialScanFinished, false)) { - watcher.emit( - "initial-missing", - "scan (missing in initial scan)" - ); - } - } - } - } - if (this.scanAgain) { - this.scanAgain = false; - this.doScan(this.scanAgainInitial); - } else { - this.scanning = false; - this.onScanFinished(); - } - }); - for (const itemPath of itemPaths) { - fs.lstat(itemPath, (err2, stats) => { - if (this.closed) return; - if (err2) { - if ( - err2.code === "ENOENT" || - err2.code === "EPERM" || - err2.code === "EBUSY" - ) { - this.setMissing(itemPath, initial, "scan (" + err2.code + ")"); - } else { - this.onScanError(err2); - } - itemFinished(); - return; - } - if (stats.isFile() || stats.isSymbolicLink()) { - if (stats.mtime) { - ensureFsAccuracy(stats.mtime); - } - this.setFileTime( - itemPath, - +stats.mtime || +stats.ctime || 1, - initial, - true, - "scan (file)" - ); - } else if (stats.isDirectory()) { - if (!initial || !this.directories.has(itemPath)) - this.setDirectory( - itemPath, - +stats.birthtime || 1, - initial, - "scan (dir)" - ); - } - itemFinished(); - }); - } - itemFinished(); - }); - }); + withOptions(options) { + const mergeOptions = opt => + Object.assign({}, options, typeof opt === "string" ? { name: opt } : opt); + + return { + name: this.name, + tap: (opt, fn) => this.tap(mergeOptions(opt), fn), + tapAsync: (opt, fn) => this.tapAsync(mergeOptions(opt), fn), + tapPromise: (opt, fn) => this.tapPromise(mergeOptions(opt), fn), + intercept: interceptor => this.intercept(interceptor), + isUsed: () => this.isUsed(), + withOptions: opt => this.withOptions(mergeOptions(opt)) + }; } - getTimes() { - const obj = Object.create(null); - let safeTime = this.lastWatchEvent; - for (const [file, entry] of this.files) { - fixupEntryAccuracy(entry); - safeTime = Math.max(safeTime, entry.safeTime); - obj[file] = Math.max(entry.safeTime, entry.timestamp); - } - if (this.nestedWatching) { - for (const w of this.directories.values()) { - const times = w.directoryWatcher.getTimes(); - for (const file of Object.keys(times)) { - const time = times[file]; - safeTime = Math.max(safeTime, time); - obj[file] = time; - } - } - obj[this.path] = safeTime; - } - if (!this.initialScan) { - for (const watchers of this.watchers.values()) { - for (const watcher of watchers) { - const path = watcher.path; - if (!Object.prototype.hasOwnProperty.call(obj, path)) { - obj[path] = null; - } - } + isUsed() { + return this.taps.length > 0 || this.interceptors.length > 0; + } + + intercept(interceptor) { + this._resetCompilation(); + this.interceptors.push(Object.assign({}, interceptor)); + if (interceptor.register) { + for (let i = 0; i < this.taps.length; i++) { + this.taps[i] = interceptor.register(this.taps[i]); } } - return obj; } - getTimeInfoEntries() { - if (this._cachedTimeInfoEntries !== undefined) - return this._cachedTimeInfoEntries; - const map = new Map(); - let safeTime = this.lastWatchEvent; - for (const [file, entry] of this.files) { - fixupEntryAccuracy(entry); - safeTime = Math.max(safeTime, entry.safeTime); - map.set(file, entry); + _resetCompilation() { + this.call = this._call; + this.callAsync = this._callAsync; + this.promise = this._promise; + } + + _insert(item) { + this._resetCompilation(); + let before; + if (typeof item.before === "string") { + before = new Set([item.before]); + } else if (Array.isArray(item.before)) { + before = new Set(item.before); } - if (this.nestedWatching) { - for (const w of this.directories.values()) { - const timeInfoEntries = w.directoryWatcher.getTimeInfoEntries(); - for (const [file, entry] of timeInfoEntries) { - if (entry) { - safeTime = Math.max(safeTime, entry.safeTime); - } - map.set(file, entry); - } - } - map.set(this.path, { - safeTime - }); - } else { - for (const dir of this.directories.keys()) { - // No additional info about this directory - map.set(dir, EXISTANCE_ONLY_TIME_ENTRY); - } - map.set(this.path, EXISTANCE_ONLY_TIME_ENTRY); + let stage = 0; + if (typeof item.stage === "number") { + stage = item.stage; } - if (!this.initialScan) { - for (const watchers of this.watchers.values()) { - for (const watcher of watchers) { - const path = watcher.path; - if (!map.has(path)) { - map.set(path, null); - } + let i = this.taps.length; + while (i > 0) { + i--; + const x = this.taps[i]; + this.taps[i + 1] = x; + const xStage = x.stage || 0; + if (before) { + if (before.has(x.name)) { + before.delete(x.name); + continue; + } + if (before.size > 0) { + continue; } } - this._cachedTimeInfoEntries = map; - } - return map; - } - - close() { - this.closed = true; - this.initialScan = false; - if (this.watcher) { - this.watcher.close(); - this.watcher = null; - } - if (this.nestedWatching) { - for (const w of this.directories.values()) { - w.close(); + if (xStage > stage) { + continue; } - this.directories.clear(); - } - if (this.parentWatcher) { - this.parentWatcher.close(); - this.parentWatcher = null; + i++; + break; } - this.emit("closed"); + this.taps[i] = item; } } -module.exports = DirectoryWatcher; -module.exports.EXISTANCE_ONLY_TIME_ENTRY = EXISTANCE_ONLY_TIME_ENTRY; - -function fixupEntryAccuracy(entry) { - if (entry.accuracy > FS_ACCURACY) { - entry.safeTime = entry.safeTime - entry.accuracy + FS_ACCURACY; - entry.accuracy = FS_ACCURACY; - } -} +Object.setPrototypeOf(Hook.prototype, null); -function ensureFsAccuracy(mtime) { - if (!mtime) return; - if (FS_ACCURACY > 1 && mtime % 1 !== 0) FS_ACCURACY = 1; - else if (FS_ACCURACY > 10 && mtime % 10 !== 0) FS_ACCURACY = 10; - else if (FS_ACCURACY > 100 && mtime % 100 !== 0) FS_ACCURACY = 100; -} +module.exports = Hook; /***/ }), -/***/ 56083: -/***/ (function(module, __unused_webpack_exports, __webpack_require__) { +/***/ 85572: +/***/ (function(module) { "use strict"; /* @@ -143154,112 +143331,473 @@ function ensureFsAccuracy(mtime) { */ -const fs = __webpack_require__(35747); -const path = __webpack_require__(85622); - -// macOS, Linux, and Windows all rely on these errors -const EXPECTED_ERRORS = new Set(["EINVAL", "ENOENT"]); +class HookCodeFactory { + constructor(config) { + this.config = config; + this.options = undefined; + this._args = undefined; + } -// On Windows there is also this error in some cases -if (process.platform === "win32") EXPECTED_ERRORS.add("UNKNOWN"); + create(options) { + this.init(options); + let fn; + switch (this.options.type) { + case "sync": + fn = new Function( + this.args(), + '"use strict";\n' + + this.header() + + this.contentWithInterceptors({ + onError: err => `throw ${err};\n`, + onResult: result => `return ${result};\n`, + resultReturns: true, + onDone: () => "", + rethrowIfPossible: true + }) + ); + break; + case "async": + fn = new Function( + this.args({ + after: "_callback" + }), + '"use strict";\n' + + this.header() + + this.contentWithInterceptors({ + onError: err => `_callback(${err});\n`, + onResult: result => `_callback(null, ${result});\n`, + onDone: () => "_callback();\n" + }) + ); + break; + case "promise": + let errorHelperUsed = false; + const content = this.contentWithInterceptors({ + onError: err => { + errorHelperUsed = true; + return `_error(${err});\n`; + }, + onResult: result => `_resolve(${result});\n`, + onDone: () => "_resolve();\n" + }); + let code = ""; + code += '"use strict";\n'; + code += this.header(); + code += "return new Promise((function(_resolve, _reject) {\n"; + if (errorHelperUsed) { + code += "var _sync = true;\n"; + code += "function _error(_err) {\n"; + code += "if(_sync)\n"; + code += + "_resolve(Promise.resolve().then((function() { throw _err; })));\n"; + code += "else\n"; + code += "_reject(_err);\n"; + code += "};\n"; + } + code += content; + if (errorHelperUsed) { + code += "_sync = false;\n"; + } + code += "}));\n"; + fn = new Function(this.args(), code); + break; + } + this.deinit(); + return fn; + } -class LinkResolver { - constructor() { - this.cache = new Map(); + setup(instance, options) { + instance._x = options.taps.map(t => t.fn); } /** - * @param {string} file path to file or directory - * @returns {string[]} array of file and all symlinks contributed in the resolving process (first item is the resolved file) + * @param {{ type: "sync" | "promise" | "async", taps: Array, interceptors: Array }} options */ - resolve(file) { - const cacheEntry = this.cache.get(file); - if (cacheEntry !== undefined) { - return cacheEntry; - } - const parent = path.dirname(file); - if (parent === file) { - // At root of filesystem there can't be a link - const result = Object.freeze([file]); - this.cache.set(file, result); - return result; - } - // resolve the parent directory to find links there and get the real path - const parentResolved = this.resolve(parent); - let realFile = file; + init(options) { + this.options = options; + this._args = options.args.slice(); + } - // is the parent directory really somewhere else? - if (parentResolved[0] !== parent) { - // get the real location of file - const basename = path.basename(file); - realFile = path.resolve(parentResolved[0], basename); + deinit() { + this.options = undefined; + this._args = undefined; + } + + contentWithInterceptors(options) { + if (this.options.interceptors.length > 0) { + const onError = options.onError; + const onResult = options.onResult; + const onDone = options.onDone; + let code = ""; + for (let i = 0; i < this.options.interceptors.length; i++) { + const interceptor = this.options.interceptors[i]; + if (interceptor.call) { + code += `${this.getInterceptor(i)}.call(${this.args({ + before: interceptor.context ? "_context" : undefined + })});\n`; + } + } + code += this.content( + Object.assign(options, { + onError: + onError && + (err => { + let code = ""; + for (let i = 0; i < this.options.interceptors.length; i++) { + const interceptor = this.options.interceptors[i]; + if (interceptor.error) { + code += `${this.getInterceptor(i)}.error(${err});\n`; + } + } + code += onError(err); + return code; + }), + onResult: + onResult && + (result => { + let code = ""; + for (let i = 0; i < this.options.interceptors.length; i++) { + const interceptor = this.options.interceptors[i]; + if (interceptor.result) { + code += `${this.getInterceptor(i)}.result(${result});\n`; + } + } + code += onResult(result); + return code; + }), + onDone: + onDone && + (() => { + let code = ""; + for (let i = 0; i < this.options.interceptors.length; i++) { + const interceptor = this.options.interceptors[i]; + if (interceptor.done) { + code += `${this.getInterceptor(i)}.done();\n`; + } + } + code += onDone(); + return code; + }) + }) + ); + return code; + } else { + return this.content(options); } - // try to read the link content - try { - const linkContent = fs.readlinkSync(realFile); + } - // resolve the link content relative to the parent directory - const resolvedLink = path.resolve(parentResolved[0], linkContent); + header() { + let code = ""; + if (this.needContext()) { + code += "var _context = {};\n"; + } else { + code += "var _context;\n"; + } + code += "var _x = this._x;\n"; + if (this.options.interceptors.length > 0) { + code += "var _taps = this.taps;\n"; + code += "var _interceptors = this.interceptors;\n"; + } + return code; + } - // recursive resolve the link content for more links in the structure - const linkResolved = this.resolve(resolvedLink); + needContext() { + for (const tap of this.options.taps) if (tap.context) return true; + return false; + } - // merge parent and link resolve results - let result; - if (linkResolved.length > 1 && parentResolved.length > 1) { - // when both contain links we need to duplicate them with a Set - const resultSet = new Set(linkResolved); - // add the link - resultSet.add(realFile); - // add all symlinks of the parent - for (let i = 1; i < parentResolved.length; i++) { - resultSet.add(parentResolved[i]); + callTap(tapIndex, { onError, onResult, onDone, rethrowIfPossible }) { + let code = ""; + let hasTapCached = false; + for (let i = 0; i < this.options.interceptors.length; i++) { + const interceptor = this.options.interceptors[i]; + if (interceptor.tap) { + if (!hasTapCached) { + code += `var _tap${tapIndex} = ${this.getTap(tapIndex)};\n`; + hasTapCached = true; } - result = Object.freeze(Array.from(resultSet)); - } else if (parentResolved.length > 1) { - // we have links in the parent but not for the link content location - result = parentResolved.slice(); - result[0] = linkResolved[0]; - // add the link - result.push(realFile); - Object.freeze(result); - } else if (linkResolved.length > 1) { - // we can return the link content location result - result = linkResolved.slice(); - // add the link - result.push(realFile); - Object.freeze(result); - } else { - // neither link content location nor parent have links - // this link is the only link here - result = Object.freeze([ - // the resolve real location - linkResolved[0], - // add the link - realFile - ]); + code += `${this.getInterceptor(i)}.tap(${ + interceptor.context ? "_context, " : "" + }_tap${tapIndex});\n`; } - this.cache.set(file, result); - return result; - } catch (e) { - if (!EXPECTED_ERRORS.has(e.code)) { - throw e; + } + code += `var _fn${tapIndex} = ${this.getTapFn(tapIndex)};\n`; + const tap = this.options.taps[tapIndex]; + switch (tap.type) { + case "sync": + if (!rethrowIfPossible) { + code += `var _hasError${tapIndex} = false;\n`; + code += "try {\n"; + } + if (onResult) { + code += `var _result${tapIndex} = _fn${tapIndex}(${this.args({ + before: tap.context ? "_context" : undefined + })});\n`; + } else { + code += `_fn${tapIndex}(${this.args({ + before: tap.context ? "_context" : undefined + })});\n`; + } + if (!rethrowIfPossible) { + code += "} catch(_err) {\n"; + code += `_hasError${tapIndex} = true;\n`; + code += onError("_err"); + code += "}\n"; + code += `if(!_hasError${tapIndex}) {\n`; + } + if (onResult) { + code += onResult(`_result${tapIndex}`); + } + if (onDone) { + code += onDone(); + } + if (!rethrowIfPossible) { + code += "}\n"; + } + break; + case "async": + let cbCode = ""; + if (onResult) + cbCode += `(function(_err${tapIndex}, _result${tapIndex}) {\n`; + else cbCode += `(function(_err${tapIndex}) {\n`; + cbCode += `if(_err${tapIndex}) {\n`; + cbCode += onError(`_err${tapIndex}`); + cbCode += "} else {\n"; + if (onResult) { + cbCode += onResult(`_result${tapIndex}`); + } + if (onDone) { + cbCode += onDone(); + } + cbCode += "}\n"; + cbCode += "})"; + code += `_fn${tapIndex}(${this.args({ + before: tap.context ? "_context" : undefined, + after: cbCode + })});\n`; + break; + case "promise": + code += `var _hasResult${tapIndex} = false;\n`; + code += `var _promise${tapIndex} = _fn${tapIndex}(${this.args({ + before: tap.context ? "_context" : undefined + })});\n`; + code += `if (!_promise${tapIndex} || !_promise${tapIndex}.then)\n`; + code += ` throw new Error('Tap function (tapPromise) did not return promise (returned ' + _promise${tapIndex} + ')');\n`; + code += `_promise${tapIndex}.then((function(_result${tapIndex}) {\n`; + code += `_hasResult${tapIndex} = true;\n`; + if (onResult) { + code += onResult(`_result${tapIndex}`); + } + if (onDone) { + code += onDone(); + } + code += `}), function(_err${tapIndex}) {\n`; + code += `if(_hasResult${tapIndex}) throw _err${tapIndex};\n`; + code += onError(`_err${tapIndex}`); + code += "});\n"; + break; + } + return code; + } + + callTapsSeries({ + onError, + onResult, + resultReturns, + onDone, + doneReturns, + rethrowIfPossible + }) { + if (this.options.taps.length === 0) return onDone(); + const firstAsync = this.options.taps.findIndex(t => t.type !== "sync"); + const somethingReturns = resultReturns || doneReturns; + let code = ""; + let current = onDone; + let unrollCounter = 0; + for (let j = this.options.taps.length - 1; j >= 0; j--) { + const i = j; + const unroll = + current !== onDone && + (this.options.taps[i].type !== "sync" || unrollCounter++ > 20); + if (unroll) { + unrollCounter = 0; + code += `function _next${i}() {\n`; + code += current(); + code += `}\n`; + current = () => `${somethingReturns ? "return " : ""}_next${i}();\n`; } - // no link - const result = parentResolved.slice(); - result[0] = realFile; - Object.freeze(result); - this.cache.set(file, result); - return result; + const done = current; + const doneBreak = skipDone => { + if (skipDone) return ""; + return onDone(); + }; + const content = this.callTap(i, { + onError: error => onError(i, error, done, doneBreak), + onResult: + onResult && + (result => { + return onResult(i, result, done, doneBreak); + }), + onDone: !onResult && done, + rethrowIfPossible: + rethrowIfPossible && (firstAsync < 0 || i < firstAsync) + }); + current = () => content; + } + code += current(); + return code; + } + + callTapsLooping({ onError, onDone, rethrowIfPossible }) { + if (this.options.taps.length === 0) return onDone(); + const syncOnly = this.options.taps.every(t => t.type === "sync"); + let code = ""; + if (!syncOnly) { + code += "var _looper = (function() {\n"; + code += "var _loopAsync = false;\n"; + } + code += "var _loop;\n"; + code += "do {\n"; + code += "_loop = false;\n"; + for (let i = 0; i < this.options.interceptors.length; i++) { + const interceptor = this.options.interceptors[i]; + if (interceptor.loop) { + code += `${this.getInterceptor(i)}.loop(${this.args({ + before: interceptor.context ? "_context" : undefined + })});\n`; + } + } + code += this.callTapsSeries({ + onError, + onResult: (i, result, next, doneBreak) => { + let code = ""; + code += `if(${result} !== undefined) {\n`; + code += "_loop = true;\n"; + if (!syncOnly) code += "if(_loopAsync) _looper();\n"; + code += doneBreak(true); + code += `} else {\n`; + code += next(); + code += `}\n`; + return code; + }, + onDone: + onDone && + (() => { + let code = ""; + code += "if(!_loop) {\n"; + code += onDone(); + code += "}\n"; + return code; + }), + rethrowIfPossible: rethrowIfPossible && syncOnly + }); + code += "} while(_loop);\n"; + if (!syncOnly) { + code += "_loopAsync = true;\n"; + code += "});\n"; + code += "_looper();\n"; + } + return code; + } + + callTapsParallel({ + onError, + onResult, + onDone, + rethrowIfPossible, + onTap = (i, run) => run() + }) { + if (this.options.taps.length <= 1) { + return this.callTapsSeries({ + onError, + onResult, + onDone, + rethrowIfPossible + }); + } + let code = ""; + code += "do {\n"; + code += `var _counter = ${this.options.taps.length};\n`; + if (onDone) { + code += "var _done = (function() {\n"; + code += onDone(); + code += "});\n"; + } + for (let i = 0; i < this.options.taps.length; i++) { + const done = () => { + if (onDone) return "if(--_counter === 0) _done();\n"; + else return "--_counter;"; + }; + const doneBreak = skipDone => { + if (skipDone || !onDone) return "_counter = 0;\n"; + else return "_counter = 0;\n_done();\n"; + }; + code += "if(_counter <= 0) break;\n"; + code += onTap( + i, + () => + this.callTap(i, { + onError: error => { + let code = ""; + code += "if(_counter > 0) {\n"; + code += onError(i, error, done, doneBreak); + code += "}\n"; + return code; + }, + onResult: + onResult && + (result => { + let code = ""; + code += "if(_counter > 0) {\n"; + code += onResult(i, result, done, doneBreak); + code += "}\n"; + return code; + }), + onDone: + !onResult && + (() => { + return done(); + }), + rethrowIfPossible + }), + done, + doneBreak + ); + } + code += "} while(false);\n"; + return code; + } + + args({ before, after } = {}) { + let allArgs = this._args; + if (before) allArgs = [before].concat(allArgs); + if (after) allArgs = allArgs.concat(after); + if (allArgs.length === 0) { + return ""; + } else { + return allArgs.join(", "); } } + + getTapFn(idx) { + return `_x[${idx}]`; + } + + getTap(idx) { + return `_taps[${idx}]`; + } + + getInterceptor(idx) { + return `_interceptors[${idx}]`; + } } -module.exports = LinkResolver; + +module.exports = HookCodeFactory; /***/ }), -/***/ 29539: +/***/ 81647: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; @@ -143269,57 +143807,66 @@ module.exports = LinkResolver; */ -const path = __webpack_require__(85622); -const DirectoryWatcher = __webpack_require__(39144); +const util = __webpack_require__(31669); -class WatcherManager { - constructor(options) { - this.options = options; - this.directoryWatchers = new Map(); +const defaultFactory = (key, hook) => hook; + +class HookMap { + constructor(factory, name = undefined) { + this._map = new Map(); + this.name = name; + this._factory = factory; + this._interceptors = []; } - getDirectoryWatcher(directory) { - const watcher = this.directoryWatchers.get(directory); - if (watcher === undefined) { - const newWatcher = new DirectoryWatcher(this, directory, this.options); - this.directoryWatchers.set(directory, newWatcher); - newWatcher.on("closed", () => { - this.directoryWatchers.delete(directory); - }); - return newWatcher; - } - return watcher; + get(key) { + return this._map.get(key); } - watchFile(p, startTime) { - const directory = path.dirname(p); - if (directory === p) return null; - return this.getDirectoryWatcher(directory).watch(p, startTime); + for(key) { + const hook = this.get(key); + if (hook !== undefined) { + return hook; + } + let newHook = this._factory(key); + const interceptors = this._interceptors; + for (let i = 0; i < interceptors.length; i++) { + newHook = interceptors[i].factory(key, newHook); + } + this._map.set(key, newHook); + return newHook; } - watchDirectory(directory, startTime) { - return this.getDirectoryWatcher(directory).watch(directory, startTime); + intercept(interceptor) { + this._interceptors.push( + Object.assign( + { + factory: defaultFactory + }, + interceptor + ) + ); } } -const watcherManagers = new WeakMap(); -/** - * @param {object} options options - * @returns {WatcherManager} the watcher manager - */ -module.exports = options => { - const watcherManager = watcherManagers.get(options); - if (watcherManager !== undefined) return watcherManager; - const newWatcherManager = new WatcherManager(options); - watcherManagers.set(options, newWatcherManager); - return newWatcherManager; -}; -module.exports.WatcherManager = WatcherManager; +HookMap.prototype.tap = util.deprecate(function(key, options, fn) { + return this.for(key).tap(options, fn); +}, "HookMap#tap(key,…) is deprecated. Use HookMap#for(key).tap(…) instead."); + +HookMap.prototype.tapAsync = util.deprecate(function(key, options, fn) { + return this.for(key).tapAsync(options, fn); +}, "HookMap#tapAsync(key,…) is deprecated. Use HookMap#for(key).tapAsync(…) instead."); + +HookMap.prototype.tapPromise = util.deprecate(function(key, options, fn) { + return this.for(key).tapPromise(options, fn); +}, "HookMap#tapPromise(key,…) is deprecated. Use HookMap#for(key).tapPromise(…) instead."); + +module.exports = HookMap; /***/ }), -/***/ 89946: +/***/ 63708: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; @@ -143329,144 +143876,60 @@ module.exports.WatcherManager = WatcherManager; */ -const path = __webpack_require__(85622); - -/** - * @template T - * @typedef {Object} TreeNode - * @property {string} filePath - * @property {TreeNode} parent - * @property {TreeNode[]} children - * @property {number} entries - * @property {boolean} active - * @property {T[] | T | undefined} value - */ +const Hook = __webpack_require__(36591); -/** - * @template T - * @param {Map>} the new plan - */ -module.exports = (plan, limit) => { - const treeMap = new Map(); - // Convert to tree - for (const [filePath, value] of plan) { - treeMap.set(filePath, { - filePath, - parent: undefined, - children: undefined, - entries: 1, - active: true, - value - }); +class MultiHook { + constructor(hooks, name = undefined) { + this.hooks = hooks; + this.name = name; } - let currentCount = treeMap.size; - // Create parents and calculate sum of entries - for (const node of treeMap.values()) { - const parentPath = path.dirname(node.filePath); - if (parentPath !== node.filePath) { - let parent = treeMap.get(parentPath); - if (parent === undefined) { - parent = { - filePath: parentPath, - parent: undefined, - children: [node], - entries: node.entries, - active: false, - value: undefined - }; - treeMap.set(parentPath, parent); - node.parent = parent; - } else { - node.parent = parent; - if (parent.children === undefined) { - parent.children = [node]; - } else { - parent.children.push(node); - } - do { - parent.entries += node.entries; - parent = parent.parent; - } while (parent); - } + + tap(options, fn) { + for (const hook of this.hooks) { + hook.tap(options, fn); } } - // Reduce until limit reached - while (currentCount > limit) { - // Select node that helps reaching the limit most effectively without overmerging - const overLimit = currentCount - limit; - let bestNode = undefined; - let bestCost = Infinity; - for (const node of treeMap.values()) { - if (node.entries <= 1 || !node.children || !node.parent) continue; - if (node.children.length === 0) continue; - if (node.children.length === 1 && !node.value) continue; - // Try to select the node with has just a bit more entries than we need to reduce - // When just a bit more is over 30% over the limit, - // also consider just a bit less entries then we need to reduce - const cost = - node.entries - 1 >= overLimit - ? node.entries - 1 - overLimit - : overLimit - node.entries + 1 + limit * 0.3; - if (cost < bestCost) { - bestNode = node; - bestCost = cost; - } + + tapAsync(options, fn) { + for (const hook of this.hooks) { + hook.tapAsync(options, fn); } - if (!bestNode) break; - // Merge all children - const reduction = bestNode.entries - 1; - bestNode.active = true; - bestNode.entries = 1; - currentCount -= reduction; - let parent = bestNode.parent; - while (parent) { - parent.entries -= reduction; - parent = parent.parent; + } + + tapPromise(options, fn) { + for (const hook of this.hooks) { + hook.tapPromise(options, fn); } - const queue = new Set(bestNode.children); - for (const node of queue) { - node.active = false; - node.entries = 0; - if (node.children) { - for (const child of node.children) queue.add(child); - } + } + + isUsed() { + for (const hook of this.hooks) { + if (hook.isUsed()) return true; } + return false; } - // Write down new plan - const newPlan = new Map(); - for (const rootNode of treeMap.values()) { - if (!rootNode.active) continue; - const map = new Map(); - const queue = new Set([rootNode]); - for (const node of queue) { - if (node.active && node !== rootNode) continue; - if (node.value) { - if (Array.isArray(node.value)) { - for (const item of node.value) { - map.set(item, node.filePath); - } - } else { - map.set(node.value, node.filePath); - } - } - if (node.children) { - for (const child of node.children) { - queue.add(child); - } - } + + intercept(interceptor) { + for (const hook of this.hooks) { + hook.intercept(interceptor); } - newPlan.set(rootNode.filePath, map); } - return newPlan; -}; + + withOptions(options) { + return new MultiHook( + this.hooks.map(h => h.withOptions(options)), + this.name + ); + } +} + +module.exports = MultiHook; /***/ }), -/***/ 10547: -/***/ (function(__unused_webpack_module, exports, __webpack_require__) { +/***/ 98034: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; /* @@ -143475,340 +143938,164 @@ module.exports = (plan, limit) => { */ -const fs = __webpack_require__(35747); -const path = __webpack_require__(85622); -const { EventEmitter } = __webpack_require__(28614); -const reducePlan = __webpack_require__(89946); - -const IS_OSX = __webpack_require__(12087).platform() === "darwin"; -const IS_WIN = __webpack_require__(12087).platform() === "win32"; -const SUPPORTS_RECURSIVE_WATCHING = IS_OSX || IS_WIN; - -const watcherLimit = - +process.env.WATCHPACK_WATCHER_LIMIT || (IS_OSX ? 2000 : 10000); - -const recursiveWatcherLogging = !!process.env - .WATCHPACK_RECURSIVE_WATCHER_LOGGING; +const Hook = __webpack_require__(36591); +const HookCodeFactory = __webpack_require__(85572); -let isBatch = false; -let watcherCount = 0; +class SyncBailHookCodeFactory extends HookCodeFactory { + content({ onError, onResult, resultReturns, onDone, rethrowIfPossible }) { + return this.callTapsSeries({ + onError: (i, err) => onError(err), + onResult: (i, result, next) => + `if(${result} !== undefined) {\n${onResult( + result + )};\n} else {\n${next()}}\n`, + resultReturns, + onDone, + rethrowIfPossible + }); + } +} -/** @type {Map} */ -const pendingWatchers = new Map(); +const factory = new SyncBailHookCodeFactory(); -/** @type {Map} */ -const recursiveWatchers = new Map(); +const TAP_ASYNC = () => { + throw new Error("tapAsync is not supported on a SyncBailHook"); +}; -/** @type {Map} */ -const directWatchers = new Map(); +const TAP_PROMISE = () => { + throw new Error("tapPromise is not supported on a SyncBailHook"); +}; -/** @type {Map} */ -const underlyingWatcher = new Map(); +const COMPILE = function(options) { + factory.setup(this, options); + return factory.create(options); +}; -class DirectWatcher { - constructor(filePath) { - this.filePath = filePath; - this.watchers = new Set(); - this.watcher = undefined; - try { - const watcher = fs.watch(filePath); - this.watcher = watcher; - watcher.on("change", (type, filename) => { - for (const w of this.watchers) { - w.emit("change", type, filename); - } - }); - watcher.on("error", error => { - for (const w of this.watchers) { - w.emit("error", error); - } - }); - } catch (err) { - process.nextTick(() => { - for (const w of this.watchers) { - w.emit("error", err); - } - }); - } - watcherCount++; - } +function SyncBailHook(args = [], name = undefined) { + const hook = new Hook(args, name); + hook.constructor = SyncBailHook; + hook.tapAsync = TAP_ASYNC; + hook.tapPromise = TAP_PROMISE; + hook.compile = COMPILE; + return hook; +} - add(watcher) { - underlyingWatcher.set(watcher, this); - this.watchers.add(watcher); - } +SyncBailHook.prototype = null; - remove(watcher) { - this.watchers.delete(watcher); - if (this.watchers.size === 0) { - directWatchers.delete(this.filePath); - watcherCount--; - if (this.watcher) this.watcher.close(); - } - } +module.exports = SyncBailHook; - getWatchers() { - return this.watchers; - } -} -class RecursiveWatcher { - constructor(rootPath) { - this.rootPath = rootPath; - /** @type {Map} */ - this.mapWatcherToPath = new Map(); - /** @type {Map>} */ - this.mapPathToWatchers = new Map(); - this.watcher = undefined; - try { - const watcher = fs.watch(rootPath, { - recursive: true - }); - this.watcher = watcher; - watcher.on("change", (type, filename) => { - if (!filename) { - if (recursiveWatcherLogging) { - process.stderr.write( - `[watchpack] dispatch ${type} event in recursive watcher (${ - this.rootPath - }) to all watchers\n` - ); - } - for (const w of this.mapWatcherToPath.keys()) { - w.emit("change", type); - } - } else { - const dir = path.dirname(filename); - const watchers = this.mapPathToWatchers.get(dir); - if (recursiveWatcherLogging) { - process.stderr.write( - `[watchpack] dispatch ${type} event in recursive watcher (${ - this.rootPath - }) for '${filename}' to ${ - watchers ? watchers.size : 0 - } watchers\n` - ); - } - if (watchers === undefined) return; - for (const w of watchers) { - w.emit("change", type, path.basename(filename)); - } - } - }); - watcher.on("error", error => { - for (const w of this.mapWatcherToPath.keys()) { - w.emit("error", error); - } - }); - } catch (err) { - process.nextTick(() => { - for (const w of this.mapWatcherToPath.keys()) { - w.emit("error", err); - } - }); - } - watcherCount++; - if (recursiveWatcherLogging) { - process.stderr.write( - `[watchpack] created recursive watcher at ${rootPath}\n` - ); - } - } +/***/ }), - add(filePath, watcher) { - underlyingWatcher.set(watcher, this); - const subpath = filePath.slice(this.rootPath.length + 1) || "."; - this.mapWatcherToPath.set(watcher, subpath); - const set = this.mapPathToWatchers.get(subpath); - if (set === undefined) { - const newSet = new Set(); - newSet.add(watcher); - this.mapPathToWatchers.set(subpath, newSet); - } else { - set.add(watcher); - } - } +/***/ 35079: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { - remove(watcher) { - const subpath = this.mapWatcherToPath.get(watcher); - if (!subpath) return; - this.mapWatcherToPath.delete(watcher); - const set = this.mapPathToWatchers.get(subpath); - set.delete(watcher); - if (set.size === 0) { - this.mapPathToWatchers.delete(subpath); - } - if (this.mapWatcherToPath.size === 0) { - recursiveWatchers.delete(this.rootPath); - watcherCount--; - if (this.watcher) this.watcher.close(); - if (recursiveWatcherLogging) { - process.stderr.write( - `[watchpack] closed recursive watcher at ${this.rootPath}\n` - ); - } - } - } +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ - getWatchers() { - return this.mapWatcherToPath; - } -} -class Watcher extends EventEmitter { - close() { - if (pendingWatchers.has(this)) { - pendingWatchers.delete(this); - return; - } - const watcher = underlyingWatcher.get(this); - watcher.remove(this); - underlyingWatcher.delete(this); +const Hook = __webpack_require__(36591); +const HookCodeFactory = __webpack_require__(85572); + +class SyncHookCodeFactory extends HookCodeFactory { + content({ onError, onDone, rethrowIfPossible }) { + return this.callTapsSeries({ + onError: (i, err) => onError(err), + onDone, + rethrowIfPossible + }); } } -const createDirectWatcher = filePath => { - const existing = directWatchers.get(filePath); - if (existing !== undefined) return existing; - const w = new DirectWatcher(filePath); - directWatchers.set(filePath, w); - return w; +const factory = new SyncHookCodeFactory(); + +const TAP_ASYNC = () => { + throw new Error("tapAsync is not supported on a SyncHook"); }; -const createRecursiveWatcher = rootPath => { - const existing = recursiveWatchers.get(rootPath); - if (existing !== undefined) return existing; - const w = new RecursiveWatcher(rootPath); - recursiveWatchers.set(rootPath, w); - return w; +const TAP_PROMISE = () => { + throw new Error("tapPromise is not supported on a SyncHook"); }; -const execute = () => { - /** @type {Map} */ - const map = new Map(); - const addWatcher = (watcher, filePath) => { - const entry = map.get(filePath); - if (entry === undefined) { - map.set(filePath, watcher); - } else if (Array.isArray(entry)) { - entry.push(watcher); - } else { - map.set(filePath, [entry, watcher]); - } - }; - for (const [watcher, filePath] of pendingWatchers) { - addWatcher(watcher, filePath); - } - pendingWatchers.clear(); +const COMPILE = function(options) { + factory.setup(this, options); + return factory.create(options); +}; - // Fast case when we are not reaching the limit - if (!SUPPORTS_RECURSIVE_WATCHING || watcherLimit - watcherCount >= map.size) { - // Create watchers for all entries in the map - for (const [filePath, entry] of map) { - const w = createDirectWatcher(filePath); - if (Array.isArray(entry)) { - for (const item of entry) w.add(item); - } else { - w.add(entry); - } - } - return; - } +function SyncHook(args = [], name = undefined) { + const hook = new Hook(args, name); + hook.constructor = SyncHook; + hook.tapAsync = TAP_ASYNC; + hook.tapPromise = TAP_PROMISE; + hook.compile = COMPILE; + return hook; +} - // Reconsider existing watchers to improving watch plan - for (const watcher of recursiveWatchers.values()) { - for (const [w, subpath] of watcher.getWatchers()) { - addWatcher(w, path.join(watcher.rootPath, subpath)); - } - } - for (const watcher of directWatchers.values()) { - for (const w of watcher.getWatchers()) { - addWatcher(w, watcher.filePath); - } - } +SyncHook.prototype = null; - // Merge map entries to keep watcher limit - // Create a 10% buffer to be able to enter fast case more often - const plan = reducePlan(map, watcherLimit * 0.9); +module.exports = SyncHook; - // Update watchers for all entries in the map - for (const [filePath, entry] of plan) { - if (entry.size === 1) { - for (const [watcher, filePath] of entry) { - const w = createDirectWatcher(filePath); - const old = underlyingWatcher.get(watcher); - if (old === w) continue; - w.add(watcher); - if (old !== undefined) old.remove(watcher); - } - } else { - const filePaths = new Set(entry.values()); - if (filePaths.size > 1) { - const w = createRecursiveWatcher(filePath); - for (const [watcher, watcherPath] of entry) { - const old = underlyingWatcher.get(watcher); - if (old === w) continue; - w.add(watcherPath, watcher); - if (old !== undefined) old.remove(watcher); - } - } else { - for (const filePath of filePaths) { - const w = createDirectWatcher(filePath); - for (const watcher of entry.keys()) { - const old = underlyingWatcher.get(watcher); - if (old === w) continue; - w.add(watcher); - if (old !== undefined) old.remove(watcher); - } - } - } - } - } -}; -exports.watch = filePath => { - const watcher = new Watcher(); - // Find an existing watcher - const directWatcher = directWatchers.get(filePath); - if (directWatcher !== undefined) { - directWatcher.add(watcher); - return watcher; - } - let current = filePath; - for (;;) { - const recursiveWatcher = recursiveWatchers.get(current); - if (recursiveWatcher !== undefined) { - recursiveWatcher.add(filePath, watcher); - return watcher; - } - const parent = path.dirname(current); - if (parent === current) break; - current = parent; +/***/ }), + +/***/ 66953: +/***/ (function(module, __unused_webpack_exports, __webpack_require__) { + +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ + + +const Hook = __webpack_require__(36591); +const HookCodeFactory = __webpack_require__(85572); + +class SyncLoopHookCodeFactory extends HookCodeFactory { + content({ onError, onDone, rethrowIfPossible }) { + return this.callTapsLooping({ + onError: (i, err) => onError(err), + onDone, + rethrowIfPossible + }); } - // Queue up watcher for creation - pendingWatchers.set(watcher, filePath); - if (!isBatch) execute(); - return watcher; +} + +const factory = new SyncLoopHookCodeFactory(); + +const TAP_ASYNC = () => { + throw new Error("tapAsync is not supported on a SyncLoopHook"); }; -exports.batch = fn => { - isBatch = true; - try { - fn(); - } finally { - isBatch = false; - execute(); - } +const TAP_PROMISE = () => { + throw new Error("tapPromise is not supported on a SyncLoopHook"); }; -exports.getNumberOfWatchers = () => { - return watcherCount; +const COMPILE = function(options) { + factory.setup(this, options); + return factory.create(options); }; +function SyncLoopHook(args = [], name = undefined) { + const hook = new Hook(args, name); + hook.constructor = SyncLoopHook; + hook.tapAsync = TAP_ASYNC; + hook.tapPromise = TAP_PROMISE; + hook.compile = COMPILE; + return hook; +} + +SyncLoopHook.prototype = null; + +module.exports = SyncLoopHook; + /***/ }), -/***/ 98342: +/***/ 92878: /***/ (function(module, __unused_webpack_exports, __webpack_require__) { "use strict"; @@ -143818,348 +144105,84 @@ exports.getNumberOfWatchers = () => { */ -const getWatcherManager = __webpack_require__(29539); -const LinkResolver = __webpack_require__(56083); -const EventEmitter = __webpack_require__(28614).EventEmitter; -const globToRegExp = __webpack_require__(22797); -const watchEventSource = __webpack_require__(10547); - -let EXISTANCE_ONLY_TIME_ENTRY; // lazy required - -const EMPTY_ARRAY = []; -const EMPTY_OPTIONS = {}; +const Hook = __webpack_require__(36591); +const HookCodeFactory = __webpack_require__(85572); -function addWatchersToSet(watchers, set) { - for (const w of watchers) { - if (w !== true && !set.has(w.directoryWatcher)) { - set.add(w.directoryWatcher); - addWatchersToSet(w.directoryWatcher.directories.values(), set); - } +class SyncWaterfallHookCodeFactory extends HookCodeFactory { + content({ onError, onResult, resultReturns, rethrowIfPossible }) { + return this.callTapsSeries({ + onError: (i, err) => onError(err), + onResult: (i, result, next) => { + let code = ""; + code += `if(${result} !== undefined) {\n`; + code += `${this._args[0]} = ${result};\n`; + code += `}\n`; + code += next(); + return code; + }, + onDone: () => onResult(this._args[0]), + doneReturns: resultReturns, + rethrowIfPossible + }); } } -const stringToRegexp = ignored => { - const source = globToRegExp(ignored, { globstar: true, extended: true }) - .source; - const matchingStart = source.slice(0, source.length - 1) + "(?:$|\\/)"; - return matchingStart; -}; +const factory = new SyncWaterfallHookCodeFactory(); -const ignoredToRegexp = ignored => { - if (Array.isArray(ignored)) { - return new RegExp(ignored.map(i => stringToRegexp(i)).join("|")); - } else if (typeof ignored === "string") { - return new RegExp(stringToRegexp(ignored)); - } else if (ignored instanceof RegExp) { - return ignored; - } else if (ignored) { - throw new Error(`Invalid option for 'ignored': ${ignored}`); - } else { - return undefined; - } +const TAP_ASYNC = () => { + throw new Error("tapAsync is not supported on a SyncWaterfallHook"); }; -const normalizeOptions = options => { - return { - followSymlinks: !!options.followSymlinks, - ignored: ignoredToRegexp(options.ignored), - poll: options.poll - }; +const TAP_PROMISE = () => { + throw new Error("tapPromise is not supported on a SyncWaterfallHook"); }; -const normalizeCache = new WeakMap(); -const cachedNormalizeOptions = options => { - const cacheEntry = normalizeCache.get(options); - if (cacheEntry !== undefined) return cacheEntry; - const normalized = normalizeOptions(options); - normalizeCache.set(options, normalized); - return normalized; +const COMPILE = function(options) { + factory.setup(this, options); + return factory.create(options); }; -class Watchpack extends EventEmitter { - constructor(options) { - super(); - if (!options) options = EMPTY_OPTIONS; - this.options = options; - this.aggregateTimeout = - typeof options.aggregateTimeout === "number" - ? options.aggregateTimeout - : 200; - this.watcherOptions = cachedNormalizeOptions(options); - this.watcherManager = getWatcherManager(this.watcherOptions); - this.fileWatchers = new Map(); - this.directoryWatchers = new Map(); - this.startTime = undefined; - this.paused = false; - this.aggregatedChanges = new Set(); - this.aggregatedRemovals = new Set(); - this.aggregateTimer = undefined; - this._onTimeout = this._onTimeout.bind(this); - } - - watch(arg1, arg2, arg3) { - let files, directories, missing, startTime; - if (!arg2) { - ({ - files = EMPTY_ARRAY, - directories = EMPTY_ARRAY, - missing = EMPTY_ARRAY, - startTime - } = arg1); - } else { - files = arg1; - directories = arg2; - missing = EMPTY_ARRAY; - startTime = arg3; - } - this.paused = false; - const oldFileWatchers = this.fileWatchers; - const oldDirectoryWatchers = this.directoryWatchers; - const ignored = this.watcherOptions.ignored; - const filter = ignored - ? path => !ignored.test(path.replace(/\\/g, "/")) - : () => true; - const addToMap = (map, key, item) => { - const list = map.get(key); - if (list === undefined) { - map.set(key, [item]); - } else { - list.push(item); - } - }; - const fileWatchersNeeded = new Map(); - const directoryWatchersNeeded = new Map(); - const missingFiles = new Set(); - if (this.watcherOptions.followSymlinks) { - const resolver = new LinkResolver(); - for (const file of files) { - if (filter(file)) { - for (const innerFile of resolver.resolve(file)) { - if (file === innerFile || filter(innerFile)) { - addToMap(fileWatchersNeeded, innerFile, file); - } - } - } - } - for (const file of missing) { - if (filter(file)) { - for (const innerFile of resolver.resolve(file)) { - if (file === innerFile || filter(innerFile)) { - missingFiles.add(file); - addToMap(fileWatchersNeeded, innerFile, file); - } - } - } - } - for (const dir of directories) { - if (filter(dir)) { - let first = true; - for (const innerItem of resolver.resolve(dir)) { - if (filter(innerItem)) { - addToMap( - first ? directoryWatchersNeeded : fileWatchersNeeded, - innerItem, - dir - ); - } - first = false; - } - } - } - } else { - for (const file of files) { - if (filter(file)) { - addToMap(fileWatchersNeeded, file, file); - } - } - for (const file of missing) { - if (filter(file)) { - missingFiles.add(file); - addToMap(fileWatchersNeeded, file, file); - } - } - for (const dir of directories) { - if (filter(dir)) { - addToMap(directoryWatchersNeeded, dir, dir); - } - } - } - const newFileWatchers = new Map(); - const newDirectoryWatchers = new Map(); - const setupFileWatcher = (watcher, key, files) => { - watcher.on("initial-missing", type => { - for (const file of files) { - if (!missingFiles.has(file)) this._onRemove(file, file, type); - } - }); - watcher.on("change", (mtime, type) => { - for (const file of files) { - this._onChange(file, mtime, file, type); - } - }); - watcher.on("remove", type => { - for (const file of files) { - this._onRemove(file, file, type); - } - }); - newFileWatchers.set(key, watcher); - }; - const setupDirectoryWatcher = (watcher, key, directories) => { - watcher.on("initial-missing", type => { - for (const item of directories) { - this._onRemove(item, item, type); - } - }); - watcher.on("change", (file, mtime, type) => { - for (const item of directories) { - this._onChange(item, mtime, file, type); - } - }); - watcher.on("remove", type => { - for (const item of directories) { - this._onRemove(item, item, type); - } - }); - newDirectoryWatchers.set(key, watcher); - }; - // Close unneeded old watchers - const fileWatchersToClose = []; - const directoryWatchersToClose = []; - for (const [key, w] of oldFileWatchers) { - if (!fileWatchersNeeded.has(key)) { - w.close(); - } else { - fileWatchersToClose.push(w); - } - } - for (const [key, w] of oldDirectoryWatchers) { - if (!directoryWatchersNeeded.has(key)) { - w.close(); - } else { - directoryWatchersToClose.push(w); - } - } - // Create new watchers and install handlers on these watchers - watchEventSource.batch(() => { - for (const [key, files] of fileWatchersNeeded) { - const watcher = this.watcherManager.watchFile(key, startTime); - if (watcher) { - setupFileWatcher(watcher, key, files); - } - } - for (const [key, directories] of directoryWatchersNeeded) { - const watcher = this.watcherManager.watchDirectory(key, startTime); - if (watcher) { - setupDirectoryWatcher(watcher, key, directories); - } - } - }); - // Close old watchers - for (const w of fileWatchersToClose) w.close(); - for (const w of directoryWatchersToClose) w.close(); - // Store watchers - this.fileWatchers = newFileWatchers; - this.directoryWatchers = newDirectoryWatchers; - this.startTime = startTime; - } - - close() { - this.paused = true; - if (this.aggregateTimer) clearTimeout(this.aggregateTimer); - for (const w of this.fileWatchers.values()) w.close(); - for (const w of this.directoryWatchers.values()) w.close(); - this.fileWatchers.clear(); - this.directoryWatchers.clear(); - } +function SyncWaterfallHook(args = [], name = undefined) { + if (args.length < 1) + throw new Error("Waterfall hooks must have at least one argument"); + const hook = new Hook(args, name); + hook.constructor = SyncWaterfallHook; + hook.tapAsync = TAP_ASYNC; + hook.tapPromise = TAP_PROMISE; + hook.compile = COMPILE; + return hook; +} - pause() { - this.paused = true; - if (this.aggregateTimer) clearTimeout(this.aggregateTimer); - } +SyncWaterfallHook.prototype = null; - getTimes() { - const directoryWatchers = new Set(); - addWatchersToSet(this.fileWatchers.values(), directoryWatchers); - addWatchersToSet(this.directoryWatchers.values(), directoryWatchers); - const obj = Object.create(null); - for (const w of directoryWatchers) { - const times = w.getTimes(); - for (const file of Object.keys(times)) obj[file] = times[file]; - } - return obj; - } +module.exports = SyncWaterfallHook; - getTimeInfoEntries() { - if (EXISTANCE_ONLY_TIME_ENTRY === undefined) { - EXISTANCE_ONLY_TIME_ENTRY = __webpack_require__(39144).EXISTANCE_ONLY_TIME_ENTRY; - } - const directoryWatchers = new Set(); - addWatchersToSet(this.fileWatchers.values(), directoryWatchers); - addWatchersToSet(this.directoryWatchers.values(), directoryWatchers); - const map = new Map(); - for (const w of directoryWatchers) { - const times = w.getTimeInfoEntries(); - for (const [path, entry] of times) { - if (map.has(path)) { - if (entry === EXISTANCE_ONLY_TIME_ENTRY) continue; - const value = map.get(path); - if (value === entry) continue; - if (value !== EXISTANCE_ONLY_TIME_ENTRY) { - map.set(path, Object.assign({}, value, entry)); - continue; - } - } - map.set(path, entry); - } - } - return map; - } - getAggregated() { - if (this.aggregateTimer) { - clearTimeout(this.aggregateTimer); - this.aggregateTimer = undefined; - } - const changes = this.aggregatedChanges; - const removals = this.aggregatedRemovals; - this.aggregatedChanges = new Set(); - this.aggregatedRemovals = new Set(); - return { changes, removals }; - } +/***/ }), - _onChange(item, mtime, file, type) { - file = file || item; - if (!this.paused) { - this.emit("change", file, mtime, type); - if (this.aggregateTimer) clearTimeout(this.aggregateTimer); - this.aggregateTimer = setTimeout(this._onTimeout, this.aggregateTimeout); - } - this.aggregatedRemovals.delete(item); - this.aggregatedChanges.add(item); - } +/***/ 34718: +/***/ (function(__unused_webpack_module, exports, __webpack_require__) { - _onRemove(item, file, type) { - file = file || item; - if (!this.paused) { - this.emit("remove", file, type); - if (this.aggregateTimer) clearTimeout(this.aggregateTimer); - this.aggregateTimer = setTimeout(this._onTimeout, this.aggregateTimeout); - } - this.aggregatedChanges.delete(item); - this.aggregatedRemovals.add(item); - } +"use strict"; +/* + MIT License http://www.opensource.org/licenses/mit-license.php + Author Tobias Koppers @sokra +*/ - _onTimeout() { - this.aggregateTimer = undefined; - const changes = this.aggregatedChanges; - const removals = this.aggregatedRemovals; - this.aggregatedChanges = new Set(); - this.aggregatedRemovals = new Set(); - this.emit("aggregated", changes, removals); - } -} -module.exports = Watchpack; +exports.__esModule = true; +exports.SyncHook = __webpack_require__(35079); +exports.SyncBailHook = __webpack_require__(98034); +exports.SyncWaterfallHook = __webpack_require__(92878); +exports.SyncLoopHook = __webpack_require__(66953); +exports.AsyncParallelHook = __webpack_require__(82890); +exports.AsyncParallelBailHook = __webpack_require__(28339); +exports.AsyncSeriesHook = __webpack_require__(45146); +exports.AsyncSeriesBailHook = __webpack_require__(97681); +exports.AsyncSeriesLoopHook = __webpack_require__(5463); +exports.AsyncSeriesWaterfallHook = __webpack_require__(73448); +exports.HookMap = __webpack_require__(81647); +exports.MultiHook = __webpack_require__(63708); /***/ }),